Completed
Branch master (411689)
by Josh
02:00
created

Encoder::encodeArrayObject()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 13
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 8
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 2
eloc 7
c 1
b 0
f 0
nc 2
nop 1
dl 0
loc 13
ccs 8
cts 8
cp 1
crap 2
rs 10
1
<?php declare(strict_types=1);
2
3
/**
4
* @package   s9e\Bencode
5
* @copyright Copyright (c) 2014-2020 The s9e authors
6
* @license   http://www.opensource.org/licenses/mit-license.php The MIT License
7
*/
8
namespace s9e\Bencode;
9
10
use ArrayObject;
11
use InvalidArgumentException;
12
use stdClass;
13
14
class Encoder
15
{
16 14
	public static function encode($value): string
17
	{
18 14
		if (is_scalar($value))
19
		{
20 11
			return self::encodeScalar($value);
21
		}
22 9
		if (is_array($value))
23
		{
24 5
			return self::encodeArray($value);
25
		}
26 4
		if ($value instanceof stdClass)
27
		{
28 2
			$value = new ArrayObject(get_object_vars($value));
29
		}
30 4
		if ($value instanceof ArrayObject)
31
		{
32 3
			return self::encodeArrayObject($value);
33
		}
34
35 1
		throw new InvalidArgumentException('Unsupported value');
36
	}
37
38
	/**
39
	* Encode an array into either an array of a dictionary
40
	*/
41 5
	protected static function encodeArray(array $value): string
42
	{
43 5
		if (empty($value))
44
		{
45 1
			return 'le';
46
		}
47
48 4
		if (array_keys($value) === range(0, count($value) - 1))
49
		{
50 2
			return 'l' . implode('', array_map([__CLASS__, 'encode'], $value)) . 'e';
51
		}
52
53
		// Encode associative arrays as dictionaries
54 4
		return self::encodeArrayObject(new ArrayObject($value));
55
	}
56
57
	/**
58
	* Encode given ArrayObject instance into a dictionary
59
	*/
60 7
	protected static function encodeArrayObject(ArrayObject $dict): string
61
	{
62 7
		$vars = $dict->getArrayCopy();
63 7
		ksort($vars);
64
65 7
		$str = 'd';
66 7
		foreach ($vars as $k => $v)
67
		{
68 6
			$str .= strlen($k) . ':' . $k . self::encode($v);
69
		}
70 7
		$str .= 'e';
71
72 7
		return $str;
73
	}
74
75
	/**
76
	* Encode a scalar value
77
	*/
78 11
	protected static function encodeScalar($value): string
79
	{
80 11
		if (is_int($value) || is_float($value))
81
		{
82 7
			return sprintf('i%de', round($value));
83
		}
84 4
		if (is_bool($value))
85
		{
86 2
			return ($value) ? 'i1e' : 'i0e';
87
		}
88
89 2
		return strlen($value) . ':' . $value;
90
	}
91
}