Completed
Push — master ( 1fdfe0...cc2a69 )
by Evstati
13s
created

Kohana_Group_Shipping_Items   B

Complexity

Total Complexity 37

Size/Duplication

Total Lines 262
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 4

Test Coverage

Coverage 98.88%

Importance

Changes 0
Metric Value
wmc 37
lcom 1
cbo 4
dl 0
loc 262
ccs 88
cts 89
cp 0.9888
rs 8.6
c 0
b 0
f 0

10 Methods

Rating   Name   Duplication   Size   Complexity  
D arr_path() 0 103 14
A parse_form_values() 0 21 4
A set_array_values() 0 11 2
A __construct() 0 8 1
A shipping() 0 10 2
A existing_shipping_items() 0 9 2
A total_price() 0 4 1
A total_delivery_time() 0 4 1
B form_value() 0 28 4
B is_active() 0 22 6
1
<?php defined('SYSPATH') OR die('No direct script access.');
2
3
/**
4
 * @package    openbuildings\shipping
5
 * @author     Ivan Kerin <[email protected]>
6
 * @copyright  (c) 2013 OpenBuildings Ltd.
7
 * @license    http://spdx.org/licenses/BSD-3-Clause
8
 */
9
class Kohana_Group_Shipping_Items {
10
11
	public $shipping_method;
12
	public $brand_purchase_shipping;
13
	public $purchase_items;
14
15
	protected $_shipping_for_method;
16
	protected $_existing_shipping_items;
17
18
	/**
19
	 * Modified to take wildcard positions into account.
20
	 *
21
	 * Gets a value from an array using a dot separated path.
22
	 *
23
	 *     // Get the value of $array['foo']['bar']
24
	 *     $value = Arr::path($array, 'foo.bar');
25
	 *
26
	 * Using a wildcard "*" will search intermediate arrays and return an array.
27
	 *
28
	 *     // Get the values of "color" in theme
29
	 *     $colors = Arr::path($array, 'theme.*.color');
30
	 *
31
	 *     // Using an array of keys
32
	 *     $colors = Arr::path($array, array('theme', '*', 'color'));
33
	 *
34
	 * @param   array   $array      array to search
35
	 * @param   mixed   $path       key path string (delimiter separated) or array of keys
36
	 * @param   mixed   $default    default value if the path is not set
37
	 * @param   string  $delimiter  key path delimiter
38
	 * @return  mixed
39
	 */
40 16
	public static function arr_path($array, $path, $default = NULL, $delimiter = NULL)
41
	{
42 16
		if ( ! Arr::is_array($array))
43
		{
44
			// This is not an array!
45 1
			return $default;
46
		}
47
48 15
		if (is_array($path))
49
		{
50
			// The path has already been separated into keys
51 1
			$keys = $path;
52
		}
53
		else
54
		{
55 14
			if (array_key_exists($path, $array))
56
			{
57
				// No need to do extra processing
58 2
				return $array[$path];
59
			}
60
61 12
			if ($delimiter === NULL)
62
			{
63
				// Use the default delimiter
64 11
				$delimiter = Arr::$delimiter;
65
			}
66
67
			// Remove starting delimiters and spaces
68 12
			$path = ltrim($path, "{$delimiter} ");
69
70
			// Remove ending delimiters, spaces, and wildcards
71 12
			$path = rtrim($path, "{$delimiter} *");
72
73
			// Split the keys by delimiter
74 12
			$keys = explode($delimiter, $path);
75
		}
76
77
		do
78
		{
79 13
			$key = array_shift($keys);
80
81 13
			if (ctype_digit($key))
82
			{
83
				// Make the key an integer
84 1
				$key = (int) $key;
85
			}
86
87 13
			if (isset($array[$key]))
88
			{
89 11
				if ($keys)
0 ignored issues
show
Bug Best Practice introduced by
The expression $keys of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
90
				{
91 10
					if (Arr::is_array($array[$key]))
92
					{
93
						// Dig down into the next part of the path
94 8
						$array = $array[$key];
95
					}
96
					else
97
					{
98
						// Unable to dig deeper
99 10
						break;
100
					}
101
				}
102
				else
103
				{
104
					// Found the path requested
105 9
					return $array[$key];
106
				}
107
			}
108 5
			elseif ($key === '*')
109
			{
110
				// Handle wildcards
111
112 3
				$values = array();
113 3
				foreach ($array as $index => $arr)
114
				{
115 3
					if ($value = Arr::path($arr, implode('.', $keys)))
116
					{
117 3
						$values[$index] = $value;
118
					}
119
				}
120
121 3
				if ($values)
0 ignored issues
show
Bug Best Practice introduced by
The expression $values of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
122
				{
123
					// Found the values requested
124 2
					return $values;
125
				}
126
				else
127
				{
128
					// Unable to dig deeper
129 1
					break;
130
				}
131
			}
132
			else
133
			{
134
				// Unable to dig deeper
135 2
				break;
136
			}
137
		}
138 8
		while ($keys);
0 ignored issues
show
Bug Best Practice introduced by
The expression $keys of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
139
140
		// Unable to find the value requested
141 5
		return $default;
142
	}
143
144 4
	public static function parse_form_values(array $array, $path)
145
	{
146 4
		if (strpos($path, '*') !== FALSE)
147
		{
148 3
			$paths = self::arr_path($array, $path);
149
150 3
			if ($paths)
151
			{
152 2
				foreach ($paths as $i => $items)
153
				{
154 3
					Group_Shipping_Items::set_array_values($array, str_replace('*', $i, $path), $items);
155
				}
156
			}
157
		}
158
		else
159
		{
160 1
			Group_Shipping_Items::set_array_values($array, $path, self::arr_path($array, $path));
161
		}
162
163 4
		return $array;
164
	}
165
166 3
	private static function set_array_values( & $array, $path, $values)
167
	{
168 3
		$new = array();
169 3
		foreach ($values as $item)
170
		{
171 3
			parse_str($item, $item);
172 3
			$new = Arr::merge($new, $item);
173
		}
174
175 3
		Arr::set_path($array, $path, $new);
176 3
	}
177
178 2
	function __construct(Model_Brand_Purchase_Shipping $brand_purchase_shipping, $purchase_items, $shipping_method)
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
179
	{
180 2
		Array_Util::validate_instance_of($purchase_items, 'Model_Purchase_Item');
181
182 2
		$this->brand_purchase_shipping = $brand_purchase_shipping;
183 2
		$this->purchase_items = $purchase_items;
184 2
		$this->shipping_method = $shipping_method;
185 2
	}
186
187 1
	public function shipping()
188
	{
189 1
		if ( ! $this->_shipping_for_method)
190
		{
191 1
			$this->_shipping_for_method = $this->brand_purchase_shipping
192 1
				->duplicate()
193 1
				->build_items_from($this->purchase_items, $this->shipping_method);
194
		}
195 1
		return $this->_shipping_for_method;
196
	}
197
198 1
	public function existing_shipping_items()
199
	{
200 1
		if ($this->_existing_shipping_items === NULL)
201
		{
202 1
			$this->_existing_shipping_items = $this->brand_purchase_shipping->items_from($this->purchase_items);
203
		}
204
205 1
		return $this->_existing_shipping_items;
206
	}
207
208 1
	public function is_active()
209
	{
210 1
		if ( ! ($items = $this->existing_shipping_items()))
211 1
			return FALSE;
212
213 1
		if ( ! $this->shipping_method)
214
			return FALSE;
215
216 1
		foreach ($items as $item)
217
		{
218 1
			if ($item->shipping_method() === NULL) {
219 1
				return FALSE;
220
			}
221
222 1
			if ($item->shipping_method()->id() != $this->shipping_method->id())
223
			{
224 1
				return FALSE;
225
			}
226
		}
227
228 1
		return TRUE;
229
	}
230
231 1
	public function total_price()
232
	{
233 1
		return $this->shipping()->total_price();
234
	}
235
236 1
	public function total_delivery_time()
237
	{
238 1
		return $this->shipping()->total_delivery_time();
239
	}
240
241 1
	public function form_value()
242
	{
243 1
		$items = $this->shipping()->items->as_array('purchase_item_id');
244
245 1
		$array = array();
246 1
		foreach ($this->existing_shipping_items() as $item)
247
		{
248 1
			if (isset($items[$item->purchase_item_id]))
249
			{
250
				$item_attributes = array(
251 1
					'shipping_group_id' => $items[$item->purchase_item_id]->shipping_group_id,
252
				);
253
254 1
				if ($item->loaded())
255
				{
256 1
					$item_attributes['id'] = $item->id();
257
				}
258
				else
259
				{
260 1
					$item_attributes['purchase_item_id'] = $item->purchase_item_id;
261
				}
262
263 1
				$array []= $item_attributes;
264
			}
265
		}
266
267 1
		return http_build_query($array);
268
	}
269
270
}
271