1: <?php
2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
26:
27: 28: 29: 30: 31: 32: 33:
34: class Mage_Catalog_Model_Api2_Product_Rest_Admin_V1 extends Mage_Catalog_Model_Api2_Product_Rest
35: {
36: 37: 38:
39: const MAX_DECIMAL_VALUE = 99999999.9999;
40:
41: 42: 43: 44: 45:
46: protected function _prepareProductForResponse(Mage_Catalog_Model_Product $product)
47: {
48: $pricesFilterKeys = array('price_id', 'all_groups', 'website_price');
49: $groupPrice = $product->getData('group_price');
50: $product->setData('group_price', $this->_filterOutArrayKeys($groupPrice, $pricesFilterKeys, true));
51: $tierPrice = $product->getData('tier_price');
52: $product->setData('tier_price', $this->_filterOutArrayKeys($tierPrice, $pricesFilterKeys, true));
53:
54: $stockData = $product->getStockItem()->getData();
55: $stockDataFilterKeys = array('item_id', 'product_id', 'stock_id', 'low_stock_date', 'type_id',
56: 'stock_status_changed_auto', 'stock_status_changed_automatically', 'product_name', 'store_id',
57: 'product_type_id', 'product_status_changed', 'product_changed_websites',
58: 'use_config_enable_qty_increments');
59: $product->setData('stock_data', $this->_filterOutArrayKeys($stockData, $stockDataFilterKeys));
60: $product->setData('product_type_name', $product->getTypeId());
61: }
62:
63: 64: 65: 66: 67: 68: 69: 70:
71: protected function _filterOutArrayKeys(array $array, array $keys, $dropOrigKeys = false)
72: {
73: $isIndexedArray = is_array(reset($array));
74: if ($isIndexedArray) {
75: foreach ($array as &$value) {
76: if (is_array($value)) {
77: $value = array_diff_key($value, array_flip($keys));
78: }
79: }
80: if ($dropOrigKeys) {
81: $array = array_values($array);
82: }
83: unset($value);
84: } else {
85: $array = array_diff_key($array, array_flip($keys));
86: }
87:
88: return $array;
89: }
90:
91: 92: 93: 94: 95:
96: protected function _retrieveCollection()
97: {
98:
99: $collection = Mage::getResourceModel('catalog/product_collection');
100: $store = $this->_getStore();
101: $collection->setStoreId($store->getId());
102: $collection->addAttributeToSelect(array_keys(
103: $this->getAvailableAttributes($this->getUserType(), Mage_Api2_Model_Resource::OPERATION_ATTRIBUTE_READ)
104: ));
105: $this->_applyCategoryFilter($collection);
106: $this->_applyCollectionModifiers($collection);
107: $products = $collection->load()->toArray();
108: return $products;
109: }
110:
111: 112: 113: 114: 115:
116: protected function _delete()
117: {
118: $product = $this->_getProduct();
119: try {
120: $product->delete();
121: } catch (Mage_Core_Exception $e) {
122: $this->_critical($e->getMessage(), Mage_Api2_Model_Server::HTTP_INTERNAL_ERROR);
123: } catch (Exception $e) {
124: $this->_critical(self::RESOURCE_INTERNAL_ERROR);
125: }
126: }
127:
128: 129: 130: 131: 132: 133:
134: protected function _create(array $data)
135: {
136:
137: $validator = Mage::getModel('catalog/api2_product_validator_product', array(
138: 'operation' => self::OPERATION_CREATE
139: ));
140:
141: if (!$validator->isValidData($data)) {
142: foreach ($validator->getErrors() as $error) {
143: $this->_error($error, Mage_Api2_Model_Server::HTTP_BAD_REQUEST);
144: }
145: $this->_critical(self::RESOURCE_DATA_PRE_VALIDATION_ERROR);
146: }
147:
148: $type = $data['type_id'];
149: if ($type !== 'simple') {
150: $this->_critical("Creation of products with type '$type' is not implemented",
151: Mage_Api2_Model_Server::HTTP_METHOD_NOT_ALLOWED);
152: }
153: $set = $data['attribute_set_id'];
154: $sku = $data['sku'];
155:
156:
157: $product = Mage::getModel('catalog/product')
158: ->setStoreId(Mage_Catalog_Model_Abstract::DEFAULT_STORE_ID)
159: ->setAttributeSetId($set)
160: ->setTypeId($type)
161: ->setSku($sku);
162:
163: foreach ($product->getMediaAttributes() as $mediaAttribute) {
164: $mediaAttrCode = $mediaAttribute->getAttributeCode();
165: $product->setData($mediaAttrCode, 'no_selection');
166: }
167:
168: $this->_prepareDataForSave($product, $data);
169: try {
170: $product->validate();
171: $product->save();
172: $this->_multicall($product->getId());
173: } catch (Mage_Eav_Model_Entity_Attribute_Exception $e) {
174: $this->_critical(sprintf('Invalid attribute "%s": %s', $e->getAttributeCode(), $e->getMessage()),
175: Mage_Api2_Model_Server::HTTP_BAD_REQUEST);
176: } catch (Mage_Core_Exception $e) {
177: $this->_critical($e->getMessage(), Mage_Api2_Model_Server::HTTP_INTERNAL_ERROR);
178: } catch (Exception $e) {
179: $this->_critical(self::RESOURCE_UNKNOWN_ERROR);
180: }
181:
182: return $this->_getLocation($product);
183: }
184:
185: 186: 187: 188: 189:
190: protected function _update(array $data)
191: {
192:
193: $product = $this->_getProduct();
194:
195: $validator = Mage::getModel('catalog/api2_product_validator_product', array(
196: 'operation' => self::OPERATION_UPDATE,
197: 'product' => $product
198: ));
199:
200: if (!$validator->isValidData($data)) {
201: foreach ($validator->getErrors() as $error) {
202: $this->_error($error, Mage_Api2_Model_Server::HTTP_BAD_REQUEST);
203: }
204: $this->_critical(self::RESOURCE_DATA_PRE_VALIDATION_ERROR);
205: }
206: if (isset($data['sku'])) {
207: $product->setSku($data['sku']);
208: }
209:
210: unset($data['attribute_set_id']);
211: unset($data['type_id']);
212: $this->_prepareDataForSave($product, $data);
213: try {
214: $product->validate();
215: $product->save();
216: } catch (Mage_Eav_Model_Entity_Attribute_Exception $e) {
217: $this->_critical(sprintf('Invalid attribute "%s": %s', $e->getAttributeCode(), $e->getMessage()),
218: Mage_Api2_Model_Server::HTTP_BAD_REQUEST);
219: } catch (Mage_Core_Exception $e) {
220: $this->_critical($e->getMessage(), Mage_Api2_Model_Server::HTTP_INTERNAL_ERROR);
221: } catch (Exception $e) {
222: $this->_critical(self::RESOURCE_UNKNOWN_ERROR);
223: }
224: }
225:
226: 227: 228: 229: 230: 231:
232: protected function _isManageStockEnabled($stockData)
233: {
234: if (!(isset($stockData['use_config_manage_stock']) && $stockData['use_config_manage_stock'])) {
235: $manageStock = isset($stockData['manage_stock']) && $stockData['manage_stock'];
236: } else {
237: $manageStock = Mage::getStoreConfig(
238: Mage_CatalogInventory_Model_Stock_Item::XML_PATH_ITEM . 'manage_stock');
239: }
240: return (bool) $manageStock;
241: }
242:
243: 244: 245: 246: 247: 248: 249:
250: protected function _isConfigValueUsed($data, $field)
251: {
252: return isset($data["use_config_$field"]) && $data["use_config_$field"];
253: }
254:
255: 256: 257: 258: 259: 260:
261: protected function _prepareDataForSave($product, $productData)
262: {
263: if (isset($productData['stock_data'])) {
264: if (!$product->isObjectNew() && !isset($productData['stock_data']['manage_stock'])) {
265: $productData['stock_data']['manage_stock'] = $product->getStockItem()->getManageStock();
266: }
267: $this->_filterStockData($productData['stock_data']);
268: } else {
269: $productData['stock_data'] = array(
270: 'use_config_manage_stock' => 1,
271: 'use_config_min_sale_qty' => 1,
272: 'use_config_max_sale_qty' => 1,
273: );
274: }
275: $product->setStockData($productData['stock_data']);
276:
277: $this->_filterConfigValueUsed($productData, array('gift_message_available', 'gift_wrapping_available'));
278: if (isset($productData['use_config_gift_message_available'])) {
279: $product->setData('use_config_gift_message_available', $productData['use_config_gift_message_available']);
280: if (!$productData['use_config_gift_message_available']
281: && ($product->getData('gift_message_available') === null)) {
282: $product->setData('gift_message_available', (int) Mage::getStoreConfig(
283: Mage_GiftMessage_Helper_Message::XPATH_CONFIG_GIFT_MESSAGE_ALLOW_ITEMS, $product->getStoreId()));
284: }
285: }
286: if (isset($productData['use_config_gift_wrapping_available'])) {
287: $product->setData('use_config_gift_wrapping_available', $productData['use_config_gift_wrapping_available']);
288: if (!$productData['use_config_gift_wrapping_available']
289: && ($product->getData('gift_wrapping_available') === null)
290: ) {
291: $xmlPathGiftWrappingAvailable = 'sales/gift_options/wrapping_allow_items';
292: $product->setData('gift_wrapping_available', (int)Mage::getStoreConfig(
293: $xmlPathGiftWrappingAvailable, $product->getStoreId()));
294: }
295: }
296:
297: if (isset($productData['website_ids']) && is_array($productData['website_ids'])) {
298: $product->setWebsiteIds($productData['website_ids']);
299: }
300:
301: if (!$product->isObjectNew() && isset($productData['url_key'])
302: && isset($productData['url_key_create_redirect'])
303: ) {
304: $product->setData('save_rewrites_history', (bool)$productData['url_key_create_redirect']);
305: }
306:
307: foreach ($product->getTypeInstance(true)->getEditableAttributes($product) as $attribute) {
308:
309: if (Mage_Catalog_Model_Abstract::DEFAULT_STORE_ID !== (int)$product->getStoreId()
310: && !$product->getExistsStoreValueFlag($attribute->getAttributeCode())
311: && !$attribute->isScopeGlobal()
312: ) {
313: $product->setData($attribute->getAttributeCode(), false);
314: }
315:
316: if ($this->_isAllowedAttribute($attribute)) {
317: if (isset($productData[$attribute->getAttributeCode()])) {
318: $product->setData(
319: $attribute->getAttributeCode(),
320: $productData[$attribute->getAttributeCode()]
321: );
322: }
323: }
324: }
325: }
326:
327: 328: 329: 330: 331:
332: protected function _filterStockData(&$stockData)
333: {
334: $fieldsWithPossibleDefautlValuesInConfig = array('manage_stock', 'min_sale_qty', 'max_sale_qty', 'backorders',
335: 'qty_increments', 'notify_stock_qty', 'min_qty', 'enable_qty_increments');
336: $this->_filterConfigValueUsed($stockData, $fieldsWithPossibleDefautlValuesInConfig);
337:
338: if ($this->_isManageStockEnabled($stockData)) {
339: if (isset($stockData['qty']) && (float)$stockData['qty'] > self::MAX_DECIMAL_VALUE) {
340: $stockData['qty'] = self::MAX_DECIMAL_VALUE;
341: }
342: if (isset($stockData['min_qty']) && (int)$stockData['min_qty'] < 0) {
343: $stockData['min_qty'] = 0;
344: }
345: if (!isset($stockData['is_decimal_divided']) || $stockData['is_qty_decimal'] == 0) {
346: $stockData['is_decimal_divided'] = 0;
347: }
348: } else {
349: $nonManageStockFields = array('manage_stock', 'use_config_manage_stock', 'min_sale_qty',
350: 'use_config_min_sale_qty', 'max_sale_qty', 'use_config_max_sale_qty');
351: foreach ($stockData as $field => $value) {
352: if (!in_array($field, $nonManageStockFields)) {
353: unset($stockData[$field]);
354: }
355: }
356: }
357: }
358:
359: 360: 361: 362: 363: 364:
365: protected function _filterConfigValueUsed(&$data, $fields) {
366: foreach($fields as $field) {
367: if ($this->_isConfigValueUsed($data, $field)) {
368: unset($data[$field]);
369: }
370: }
371: }
372:
373: 374: 375: 376: 377: 378: 379:
380: protected function _isAllowedAttribute($attribute, $attributes = null)
381: {
382: $isAllowed = true;
383: if (is_array($attributes)
384: && !(in_array($attribute->getAttributeCode(), $attributes)
385: || in_array($attribute->getAttributeId(), $attributes))
386: ) {
387: $isAllowed = false;
388: }
389: return $isAllowed;
390: }
391: }
392: