| Server IP : 85.158.181.41 / Your IP : 216.73.217.12 Web Server : Apache System : Linux cloud9-vm129 6.1.178+1-ph #ph SMP PREEMPT_DYNAMIC Wed Jul 29 09:00:54 UTC 2026 x86_64 User : moncbefd ( 1024) PHP Version : 7.3.33 Disable Function : NONE MySQL : OFF | cURL : ON | WGET : ON | Perl : ON | Python : ON | Sudo : OFF | Pkexec : OFF Directory : /home/moncbefd/www.moneta.at/system/classes/gambio_xml/ |
Upload File : |
<?php
/* --------------------------------------------------------------
GxmlProducts.inc.php 2018-10-29
Gambio GmbH
http://www.gambio.de
Copyright (c) 2018 Gambio GmbH
Released under the GNU General Public License (Version 2)
[http://www.gnu.org/licenses/gpl-2.0.html]
--------------------------------------------------------------
*/
/**
* Class GxmlProducts
*
* Handles the API requests that concern the products section of the shop system.
*
* Supported API Functions:
* - "upload_products"
* - "download_products"
*
* Refactored by A.Tselegidis
*
* @category System
* @package GambioAPI
* @version 1.0
*/
class GxmlProducts extends GxmlMaster
{
/**
* Class Constructor
*/
public function __construct()
{
parent::__construct();
$this->_setPluralName('products');
$this->_setSingularName('product');
$this->_setupMapperArray();
$this->_setupTableMapperArray();
}
/**
* Download Products API Method
*
* This method handles the download product function requests done by the
* API clients.
*
* @param SimpleXMLElement $requestXml Contains the request information sent by the client.
*
* @return SimpleXMLElement Returns the response XML object.
*/
public function downloadProducts(SimpleXMLElement $requestXml)
{
try {
$parameters = $this->_generateSqlStrings($requestXml->parameters, array('limit', 'where'));
$this->responseXml->addChild('request');
$this->responseXml->request->addChild('success', 1);
$this->_includeNode(array('languages', 'customer_groups', 'shipping_times', 'tax_classes', 'base_price_units', 'quantity_units'));
$this->_addProductsNode($parameters);
return $this->responseXml;
}
catch(Exception $ex)
{
return $this->handleApiException($ex);
}
}
/**
* Upload Products API Method
*
* This method handles the upload product function requests done by the
* API clients.
*
* @param SimpleXMLElement $requestXml Contains the request information sent by the client.
*
* @return SimpleXMLElement Returns the response XML object.
*/
public function uploadProducts(SimpleXMLElement $requestXml)
{
try
{
$responseData = array();
$combisXmlArray = array();
$productCombis = MainFactory::create_object('GxmlProductCombis');
// Validate the request XML for property data.
if(!property_exists($requestXml->parameters, 'products'))
{
throw new InvalidArgumentException('Request XML is invalid: Missing parameters->products element.');
}
foreach($requestXml->parameters->products->children() as $productXml)
{
// update tax_class_id by given tax_rate
$isValid = $this->_validateTax($productXml, $responseData);
if($isValid === true)
{
if(isset($productXml->product_id) == false
&& (isset($productXml->categories) == false || isset($productXml->categories->category) == false))
{
$this->addXmlChild($productXml, simplexml_load_string('<categories>
<category>
<category_id>0</category_id>
</category>
</categories>'), false);
}
$this->_upload($productXml, $responseData);
$actualProductId = !empty($responseData) && isset($responseData[count($responseData) - 1]['product_id'])
? $responseData[count($responseData) - 1]['product_id']
: false;
if ($actualProductId != false && isset($productXml->product_combis))
{
$combisXmlArray[] = $productCombis->uploadProductCombis($productXml, $actualProductId);
}
}
}
$responseXml = $this->generateResponseXml($responseData);
if(strlen((string)$this->responseXmlBuffer) > 0)
{
$additionalImages = $responseXml->addChild('additional_images');
foreach($this->responseXmlBuffer as $imageData)
{
$image = $additionalImages->addChild('image');
foreach($imageData as $name => $value)
{
$image->addChild($name, $value);
}
}
}
foreach($combisXmlArray as $productCombisXml)
{
$productCombiArray = $productCombisXml->product_combis->children();
if(isset($responseXml->product_combis) === false)
{
$responseProductCombisXml = $responseXml->addChild('product_combis');
}
foreach($productCombiArray as $productCombiXml)
{
$this->addXmlChild($responseProductCombisXml, $productCombiXml);
$responseXml->request->success &= $productCombiXml->success;
}
}
return $responseXml;
}
catch(Exception $ex)
{
return $this->handleApiException($ex);
}
}
/**
* Add node to the response XML object.
*
* @param array $data Contains the data to be included within the XML response object.
* @param string $tableColumn Table column will point the value that we need from the $data.
* @param string $nodeName This is the name of the node to be inserted.
* @param SimpleXMLElement $xml The xml object that will be edited.
*/
protected function _addNode(array $data, $tableColumn, $nodeName, SimpleXMLElement $xml)
{
switch($nodeName)
{
case 'tax_rate':
if($this->nodeExists($xml, $nodeName) === false)
{
// Check whether the product has a tax class
if(isset($data['products_tax_class_id']) && $data['products_tax_class_id'] != 0)
{
$xml->{$nodeName} = $this->taxArray[$data['products_tax_class_id']]['tax_rate'];
}
}
break;
case 'name':
case 'description':
case 'short_description':
case 'keywords':
case 'meta_title':
case 'meta_description':
case 'meta_keywords':
case 'url':
case 'viewed':
case 'image_alt_text':
case 'url_keywords':
$xmlName = $nodeName;
// Check that the current category language exists in the database.
$languageIso = (isset($this->languageArray[$data['language_id']]))
? $this->languageArray[$data['language_id']]['iso']
: '';
$attributes = array(
'language_id' => $data['language_id'],
'language_iso' => $languageIso
);
if($this->nodeExists($xml, $xmlName, $attributes, 'or') === false)
{
$xml->addChild($nodeName);
$xml->{$nodeName}[count($xml->{$nodeName}) - 1] = $this->wrapValue($data[$tableColumn]);
$childNode = $xml->{$nodeName}[count($xml->{$nodeName}) - 1];
$childNode['language_id'] = $data['language_id'];
$childNode['language_iso'] =$languageIso;
if($xmlName == 'description' ||
$xmlName == 'short_description')
{
$childNode['type'] = 2;
}
}
break;
case 'customer_group_permission':
if($this->nodeExists($xml, $nodeName) === false)
{
foreach($data AS $column => $value)
{
if(strpos($column, 'group_permission_') !== false)
{
$xml->addChild($nodeName);
$xml->{$nodeName}[count($xml->{$nodeName}) - 1] = $value;
$childNode = $xml->{$nodeName}[count($xml->{$nodeName}) - 1];
$childNode['customer_group_id'] = str_replace('group_permission_', '', $column);
}
}
}
break;
case 'image':
$xmlName = $nodeName;
if($this->nodeExists($xml, $xmlName) === false)
{
$xml->{$xmlName} = $this->wrapValue($data[$tableColumn]);
$xml->{$xmlName}['width'] = $data['products_image_w'];
$xml->{$xmlName}['height'] = $data['products_image_h'];
}
break;
case 'image_url':
$xmlName = $nodeName;
if($this->nodeExists($xml, $xmlName) === false)
{
$productImageUrl = '';
if(empty($data[$tableColumn]) === false)
{
$productImageUrl = $this->wrapValue(HTTP_SERVER . DIR_WS_CATALOG . DIR_WS_IMAGES . 'product_images/original_images/' . $data[$tableColumn]);
}
$xml->{$xmlName} = $productImageUrl;
}
break;
case 'personal_offers':
$dataArray = array();
foreach($data AS $column=>$value)
{
if(strpos($column, 'personal_offers_quantity_') !== false)
{
$customersStatusId = str_replace('personal_offers_quantity_', '', $column);
$dataArray[$customersStatusId][(string) $value] = (string)$data['personal_offers_price_' . $customersStatusId];
}
}
if(!empty($dataArray))
{
foreach($dataArray AS $customersStatusId => $t_personal_offers_array)
{
foreach($t_personal_offers_array AS $quantity => $price)
{
$t_quantity_value = (double)$quantity;
if(!empty($t_quantity_value))
{
if($this->nodeExists($xml, $nodeName) === false)
{
$childNode = $xml->addChild($nodeName);
}
else
{
$childNode = $xml->personal_offers;
}
if($this->nodeValueExists($childNode, 'personal_offer', 'quantity', $quantity, array('customer_group_id' => $customersStatusId)) === false)
{
$personalOfferNode = $childNode->addChild('personal_offer');
$personalOfferNode['customer_group_id'] = $customersStatusId;
$personalOfferNode->quantity = $quantity;
$personalOfferNode->price = $price;
}
}
}
}
}
break;
case 'additional_images/image/image_id':
case 'additional_images/image/filename':
case 'additional_images/image/sort_order':
case 'additional_images/image/visible':
case 'additional_images/image/image_alt_text':
case 'additional_images/image/image_url':
break;
case 'special/special_id':
case 'special/quantity':
case 'special/price':
case 'special/date_added':
case 'special/last_modified':
case 'special/expiring_date':
case 'special/date_status_change':
case 'special/status':
$xmlName = str_replace('special/', '', $nodeName);
if(!empty($data[$this->mapperArray['special/special_id']]))
{
if($this->nodeExists($xml, 'special') === false)
{
$specialNode = $xml->addChild('special');
}
else
{
$specialNode = $xml->special;
}
if($this->nodeExists($specialNode, $xmlName) === false)
{
$specialNode->{$xmlName} = $data[$tableColumn];
}
}
break;
case 'categories/category/category_id':
$xmlName = substr($nodeName, strrpos($nodeName, '/') + 1);
if(!empty($data[$this->mapperArray['categories/category/category_id']]))
{
if($this->nodeExists($xml, 'categories') === false)
{
$categoriesNode = $xml->addChild('categories');
}
else
{
$categoriesNode = $xml->categories;
}
foreach ($data[$tableColumn] as $t_category_id)
{
if($this->nodeValueExists($categoriesNode, 'category', $xmlName, $t_category_id) === false)
{
$categoryNode = $categoriesNode->addChild('category');
$categoryNode->{$xmlName} = $t_category_id;
}
}
}
break;
case 'cross_selling_products/cross_selling_product/product_id':
case 'cross_selling_products/cross_selling_product/sort_order':
break;
case 'ean':
case 'model':
case 'template':
case 'attributes_template':
case 'attributes_listing_template':
case 'filename':
$xmlName = $nodeName;
if($this->nodeExists($xml, $xmlName) === false)
{
$xml->{$xmlName} = $this->wrapValue($data[$tableColumn]);
}
break;
default:
$xmlName = $nodeName;
if($this->nodeExists($xml, $xmlName) === false && isset($data[$tableColumn]))
{
$xml->{$xmlName} = $data[$tableColumn];
}
break;
}
}
/**
* Abstract Method Implementation: Delete Object
*
* This is an implementation of the abstract method declared in the GxmlMaster class. It
* removes an object from the database.
*
* @param SimpleXMLElement $requestXml Contains the information of the request sent by the client.
*
* @return bool Returns the operation result.
*/
protected function _deleteObject(SimpleXMLElement $requestXml)
{
$productData = $this->_parseXmlData($requestXml);
$productData = $this->convertToLatin1($productData);
$productsId = (string) $requestXml->product_id;
$deletedRecords = array();
$result = true;
// Select all "product_ids"
if(empty($productsId))
{
$query = '
SELECT products_id
FROM products
WHERE';
foreach($productData['products'] as $key=>$value)
{
$query .= $key . ' LIKE \'' . $value . '\' AND ';
}
$query = substr($query, 0, strlen($query) - 5);
$results = xtc_db_query($query);
if(xtc_db_num_rows(($results)))
{
while($row = xtc_db_fetch_array($results))
{
$deletedRecords[] = $row['products_id'];
}
}
}
else
{
$deletedRecords[] = $productsId;
}
// Delete Product
// Product data are located into many tables in the database. The quickest way to delete them
// at once is to include as many tables as possible in one DELETE query and remove the records
// that have are relevant to the specified product.
if(!empty($deletedRecords))
{
foreach($deletedRecords as $recordId)
{
$query = '
DELETE products, products_attributes, products_attributes_download, products_content, products_description,
products_google_categories, products_graduated_prices, products_hermesoptions, products_images, products_item_codes,
products_notifications, products_properties_admin_select, products_properties_combis,
products_properties_combis_defaults, products_properties_combis_values, products_properties_index, products_quantity_unit,
products_to_categories, products_xsell, customers_basket, customers_basket_attributes,
gm_prd_img_alt, gm_gmotion, gm_gmotion_products, categories_index, feature_set_to_products, feature_set,
feature_set_values, reviews
FROM products
LEFT JOIN products_attributes ON products_attributes.products_id = products.products_id
LEFT JOIN products_attributes_download ON products_attributes_download.products_attributes_id = products_attributes.products_attributes_id
LEFT JOIN products_content ON products_content.products_id = products.products_id
LEFT JOIN products_description ON products_description.products_id = products.products_id
LEFT JOIN products_google_categories ON products_google_categories.products_id = products.products_id
LEFT JOIN products_graduated_prices ON products_graduated_prices.products_id = products.products_id
LEFT JOIN products_hermesoptions ON products_hermesoptions.products_id = products.products_id
LEFT JOIN products_images ON products_images.products_id = products.products_id
LEFT JOIN products_item_codes ON products_item_codes.products_id = products.products_id
LEFT JOIN products_notifications ON products_notifications.products_id = products.products_id
LEFT JOIN products_properties_admin_select ON products_properties_admin_select.products_id = products.products_id
LEFT JOIN products_properties_combis ON products_properties_combis.products_id = products.products_id
LEFT JOIN products_properties_combis_defaults ON products_properties_combis_defaults.products_id = products.products_id
LEFT JOIN products_properties_combis_values ON products_properties_combis_values.products_properties_combis_id = products_properties_combis.products_properties_combis_id
LEFT JOIN products_properties_index ON products_properties_index.products_id = products.products_id
LEFT JOIN products_quantity_unit ON products_quantity_unit.products_id = products.products_id
LEFT JOIN products_to_categories ON products_to_categories.products_id = products.products_id
LEFT JOIN products_xsell ON products_xsell.products_id = products.products_id
LEFT JOIN customers_basket ON customers_basket.products_id = products.products_id
LEFT JOIN customers_basket_attributes ON customers_basket_attributes.products_id = products.products_id
LEFT JOIN gm_prd_img_alt ON gm_prd_img_alt.products_id = products.products_id
LEFT JOIN gm_gmotion ON gm_gmotion.products_id = products.products_id
LEFT JOIN gm_gmotion_products ON gm_gmotion_products.products_id = products.products_id
LEFT JOIN categories_index ON categories_index.products_id = products.products_id
LEFT JOIN feature_set_to_products ON feature_set_to_products.products_id = products.products_id
LEFT JOIN feature_set ON feature_set.feature_set_id = feature_set_to_products.feature_set_id
LEFT JOIN feature_set_values ON feature_set_values.feature_set_id = feature_set.feature_set_id
LEFT JOIN reviews ON reviews.products_id = products.products_id
WHERE products.products_id = "' . (int)$recordId . '";
';
$result &= xtc_db_query($query);
}
}
return $result;
}
/**
* Setup the mapper array that will map XML string names to the actual
* DB names.
*/
protected function _setupMapperArray()
{
$this->mapperArray = array();
$this->mapperArray['product_id'] = 'products_id';
$this->mapperArray['ean'] = 'products_ean';
$this->mapperArray['quantity'] = 'products_quantity';
$this->mapperArray['shipping_time_id'] = 'products_shippingtime';
$this->mapperArray['model'] = 'products_model';
$this->mapperArray['sort_order'] = 'products_sort';
$this->mapperArray['image'] = 'products_image';
$this->mapperArray['image_url'] = 'products_image';
$this->mapperArray['price'] = 'products_price';
$this->mapperArray['discount_allowed'] = 'products_discount_allowed';
$this->mapperArray['date_added'] = 'products_date_added';
$this->mapperArray['last_modified'] = 'products_last_modified';
$this->mapperArray['date_available'] = 'products_date_available';
$this->mapperArray['weight'] = 'products_weight';
$this->mapperArray['status'] = 'products_status';
$this->mapperArray['tax_class_id'] = 'products_tax_class_id';
$this->mapperArray['tax_rate'] = 'tax_rate';
$this->mapperArray['template'] = 'product_template';
$this->mapperArray['attributes_template'] = 'options_template';
$this->mapperArray['attributes_listing_template'] = 'gm_options_template';
$this->mapperArray['products_ordered'] = 'products_ordered';
$this->mapperArray['price_status'] = 'gm_price_status';
$this->mapperArray['min_order'] = 'gm_min_order';
$this->mapperArray['graduated_quantity'] = 'gm_graduated_qty';
$this->mapperArray['startpage_sort'] = 'products_startpage_sort';
$this->mapperArray['shipping_costs'] = 'nc_ultra_shipping_costs';
$this->mapperArray['priority'] = 'gm_priority';
$this->mapperArray['change_frequency'] = 'gm_changefreq';
$this->mapperArray['fsk18'] = 'products_fsk18';
$this->mapperArray['name'] = 'products_name';
$this->mapperArray['description'] = 'products_description';
$this->mapperArray['short_description'] = 'products_short_description';
$this->mapperArray['keywords'] = 'products_keywords';
$this->mapperArray['meta_title'] = 'products_meta_title';
$this->mapperArray['meta_description'] = 'products_meta_description';
$this->mapperArray['meta_keywords'] = 'products_meta_keywords';
$this->mapperArray['url'] = 'products_url';
$this->mapperArray['viewed'] = 'products_viewed';
$this->mapperArray['image_alt_text'] = 'gm_alt_text';
$this->mapperArray['url_keywords'] = 'gm_url_keywords';
$this->mapperArray['quantity_unit_id'] = 'quantity_unit_id';
$this->mapperArray['base_price_unit_id'] = 'products_vpe';
$this->mapperArray['base_price_unit_status'] = 'products_vpe_status';
$this->mapperArray['base_price_unit_value'] = 'products_vpe_value';
$this->mapperArray['show_date_added'] = 'gm_show_date_added';
$this->mapperArray['show_price_offer'] = 'gm_show_price_offer';
$this->mapperArray['show_weight'] = 'gm_show_weight';
$this->mapperArray['show_quantity_info'] = 'gm_show_qty_info';
$this->mapperArray['show_image'] = 'gm_show_image';
$this->mapperArray['show_on_startpage'] = 'products_startpage';
$this->mapperArray['sitemap_entry'] = 'gm_sitemap_entry';
$this->mapperArray['properties_dropdown_mode'] = 'properties_dropdown_mode';
$this->mapperArray['properties_show_price'] = 'properties_show_price';
$this->mapperArray['use_properties_combis_weight'] = 'use_properties_combis_weight';
$this->mapperArray['use_properties_combis_quantity'] = 'use_properties_combis_quantity';
$this->mapperArray['use_properties_combis_shipping_time'] = 'use_properties_combis_shipping_time';
$this->mapperArray['customer_group_permission'] = 'group_permission_';
$this->mapperArray['personal_offers'] = 'personal_offers_by_customers_status_';
$this->mapperArray['additional_images/image/image_id'] = 'image_id';
$this->mapperArray['additional_images/image/external_image_id'] = 'external_image_id';
$this->mapperArray['additional_images/image/filename'] = 'image_name';
$this->mapperArray['additional_images/image/image_url'] = 'image_name';
$this->mapperArray['additional_images/image/sort_order'] = 'image_nr';
$this->mapperArray['additional_images/image/visible'] = 'gm_show_image';
$this->mapperArray['additional_images/image/image_alt_text'] = 'gm_alt_text';
$this->mapperArray['special/special_id'] = 'specials_id';
$this->mapperArray['special/quantity'] = 'specials_quantity';
$this->mapperArray['special/price'] = 'specials_new_products_price';
$this->mapperArray['special/date_added'] = 'specials_date_added';
$this->mapperArray['special/last_modified'] = 'specials_last_modified';
$this->mapperArray['special/expiring_date'] = 'expires_date';
$this->mapperArray['special/date_status_change'] = 'date_status_change';
$this->mapperArray['special/status'] = 'status';
$this->mapperArray['categories/category/category_id'] = 'categories_id';
$this->mapperArray['cross_selling_products/cross_selling_product/product_id'] = 'xsell_id';
$this->mapperArray['cross_selling_products/cross_selling_product/sort_order'] = 'sort_order';
}
/**
* Setup the mapper array that will map XML string names to the actual
* DB table names.
*/
protected function _setupTableMapperArray()
{
$this->tableMapperArray = array();
$this->tableMapperArray['product_id'] = TABLE_PRODUCTS;
$this->tableMapperArray['ean'] = TABLE_PRODUCTS;
$this->tableMapperArray['quantity'] = TABLE_PRODUCTS;
$this->tableMapperArray['shipping_time_id'] = TABLE_PRODUCTS;
$this->tableMapperArray['model'] = TABLE_PRODUCTS;
$this->tableMapperArray['sort_order'] = TABLE_PRODUCTS;
$this->tableMapperArray['image'] = TABLE_PRODUCTS;
$this->tableMapperArray['image_url'] = TABLE_PRODUCTS;
$this->tableMapperArray['price'] = TABLE_PRODUCTS;
$this->tableMapperArray['discount_allowed'] = TABLE_PRODUCTS;
$this->tableMapperArray['date_added'] = TABLE_PRODUCTS;
$this->tableMapperArray['last_modified'] = TABLE_PRODUCTS;
$this->tableMapperArray['date_available'] = TABLE_PRODUCTS;
$this->tableMapperArray['weight'] = TABLE_PRODUCTS;
$this->tableMapperArray['status'] = TABLE_PRODUCTS;
$this->tableMapperArray['tax_class_id'] = TABLE_PRODUCTS;
$this->tableMapperArray['tax_rate'] = TABLE_PRODUCTS;
$this->tableMapperArray['template'] = TABLE_PRODUCTS;
$this->tableMapperArray['attributes_template'] = TABLE_PRODUCTS;
$this->tableMapperArray['attributes_listing_template'] = TABLE_PRODUCTS;
$this->tableMapperArray['products_ordered'] = TABLE_PRODUCTS;
$this->tableMapperArray['price_status'] = TABLE_PRODUCTS;
$this->tableMapperArray['min_order'] = TABLE_PRODUCTS;
$this->tableMapperArray['graduated_quantity'] = TABLE_PRODUCTS;
$this->tableMapperArray['startpage_sort'] = TABLE_PRODUCTS;
$this->tableMapperArray['shipping_costs'] = TABLE_PRODUCTS;
$this->tableMapperArray['priority'] = TABLE_PRODUCTS;
$this->tableMapperArray['change_frequency'] = TABLE_PRODUCTS;
$this->tableMapperArray['fsk18'] = TABLE_PRODUCTS;
$this->tableMapperArray['name'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['description'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['short_description'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['keywords'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['meta_title'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['meta_description'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['meta_keywords'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['url'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['viewed'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['image_alt_text'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['url_keywords'] = TABLE_PRODUCTS_DESCRIPTION;
$this->tableMapperArray['quantity_unit_id'] = 'products_quantity_unit';
$this->tableMapperArray['base_price_unit_id'] = TABLE_PRODUCTS;
$this->tableMapperArray['base_price_unit_status'] = TABLE_PRODUCTS;
$this->tableMapperArray['base_price_unit_value'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_date_added'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_price_offer'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_weight'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_quantity_info'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_image'] = TABLE_PRODUCTS;
$this->tableMapperArray['show_on_startpage'] = TABLE_PRODUCTS;
$this->tableMapperArray['sitemap_entry'] = TABLE_PRODUCTS;
$this->tableMapperArray['properties_dropdown_mode'] = TABLE_PRODUCTS;
$this->tableMapperArray['properties_show_price'] = TABLE_PRODUCTS;
$this->tableMapperArray['use_properties_combis_weight'] = TABLE_PRODUCTS;
$this->tableMapperArray['use_properties_combis_quantity'] = TABLE_PRODUCTS;
$this->tableMapperArray['use_properties_combis_shipping_time'] = TABLE_PRODUCTS;
$this->tableMapperArray['customer_group_permission'] = TABLE_PRODUCTS;
$this->tableMapperArray['personal_offers'] = TABLE_PERSONAL_OFFERS_BY;
$this->tableMapperArray['personal_offer'] = TABLE_PERSONAL_OFFERS_BY;
$this->tableMapperArray['additional_images/image/image_id'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/external_image_id'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/filename'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/image_url'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/sort_order'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/visible'] = TABLE_PRODUCTS_IMAGES;
$this->tableMapperArray['additional_images/image/image_alt_text'] = 'gm_prd_img_alt';
$this->tableMapperArray['special/special_id'] = TABLE_SPECIALS;
$this->tableMapperArray['special/quantity'] = TABLE_SPECIALS;
$this->tableMapperArray['special/price'] = TABLE_SPECIALS;
$this->tableMapperArray['special/date_added'] = TABLE_SPECIALS;
$this->tableMapperArray['special/last_modified'] = TABLE_SPECIALS;
$this->tableMapperArray['special/expiring_date'] = TABLE_SPECIALS;
$this->tableMapperArray['special/date_status_change'] = TABLE_SPECIALS;
$this->tableMapperArray['special/status'] = TABLE_SPECIALS;
$this->tableMapperArray['categories/category/category_id'] = TABLE_PRODUCTS_TO_CATEGORIES;
$this->tableMapperArray['cross_selling_products/cross_selling_product/product_id'] = TABLE_PRODUCTS_XSELL;
$this->tableMapperArray['cross_selling_products/cross_selling_product/sort_order'] = TABLE_PRODUCTS_XSELL;
$this->languageDependentMapperArray = array(TABLE_PRODUCTS_DESCRIPTION, 'gm_prd_img_alt');
}
/**
* Generate Personal Offers query clauses.
*
* This method will generate the query parts for the personal offers.
*
* @return array Returns an array that contains the query parts of the personal offers
* SQL query.
*/
protected function _generatePersonalOffersQuery()
{
$queryClauses = array();
$selectClause = '';
$joinClause = '';
$query = "SELECT customers_status_id
FROM " . TABLE_CUSTOMERS_STATUS . "
WHERE customers_status_id > 0
GROUP BY customers_status_id
ORDER BY customers_status_id ASC";
$results = xtc_db_query($query);
while($row = xtc_db_fetch_array($results))
{
$selectClause .= ', p' . $row['customers_status_id'] . '.quantity AS personal_offers_quantity_' . $row['customers_status_id'] . ',
p' . $row['customers_status_id'] . '.personal_offer AS personal_offers_price_' . $row['customers_status_id'];
$joinClause .= ' LEFT JOIN personal_offers_by_customers_status_' . $row['customers_status_id'] . ' AS p' . $row['customers_status_id'] . ' ON (p' . $row['customers_status_id'] . '.products_id = ' . TABLE_PRODUCTS . '.products_id) ';
}
$queryClauses['select'] = $selectClause;
$queryClauses['join'] = $joinClause;
return $queryClauses;
}
/**
* Add products node to the response XML object.
*
* This method will edit the private property response XML object.
*
* @param array $parameters Parameters include information about filtering the results.
*/
protected function _addProductsNode(array $parameters = array())
{
$this->responseXml->addChild('products');
$productIds = true;
$productsToCategories = array();
if(count($parameters) === 0)
{
$query = 'SELECT * FROM ' . TABLE_PRODUCTS_TO_CATEGORIES;
$results = xtc_db_query($query);
while($row = xtc_db_fetch_array($results))
{
if(isset($productsToCategories[$row['products_id']]) === false)
{
$productsToCategories[$row['products_id']] = array();
}
$productsToCategories[$row['products_id']][] = $row['categories_id'];
}
}
$whereClause = $this->_generateWhereClause($parameters);
$personalOffersClause = $this->_generatePersonalOffersQuery();
$limitation = '';
if(count($parameters) > 0)
{
$productIds = array();
$limitClause = ' GROUP BY ' . TABLE_PRODUCTS . '.products_id' . $this->_generateLimitClause($parameters);
$query = "
SELECT " . TABLE_PRODUCTS . ".products_id
FROM " . TABLE_PRODUCTS . "
LEFT JOIN " . TABLE_SPECIALS . " ON (" . TABLE_SPECIALS . ".products_id = " . TABLE_PRODUCTS . ".products_id)
" . $personalOffersClause['join'] . "
LEFT JOIN " . TABLE_PRODUCTS_DESCRIPTION . " ON (" . TABLE_PRODUCTS_DESCRIPTION . ".products_id = " . TABLE_PRODUCTS . ".products_id)
LEFT JOIN products_quantity_unit ON (products_quantity_unit.products_id = " . TABLE_PRODUCTS . ".products_id)
LEFT JOIN " . TABLE_PRODUCTS_TO_CATEGORIES . " ON (" . TABLE_PRODUCTS_TO_CATEGORIES . ".products_id = " . TABLE_PRODUCTS . ".products_id)
" . $whereClause . "
" . $limitClause;
$results = xtc_db_query($query);
while($row = xtc_db_fetch_array($results))
{
$productIds[] = $row['products_id'];
}
$limit = 0;
$offset = 0;
if(isset($parameters['offset']) && !empty($parameters['offset']))
{
$offset = (int) $parameters['offset'];
}
if(isset($parameters['limit']) && !empty($parameters['limit']))
{
$limit = (int) $parameters['limit'];
if(!empty($productIds))
{
if($whereClause == '' )
{
$limitation = ' WHERE ' . TABLE_PRODUCTS . '.products_id IN (' . implode(',', $productIds) . ') ';
}
else
{
$limitation .= ' AND ' . TABLE_PRODUCTS . '.products_id IN (' . implode(',', $productIds) . ') ';
}
}
}
if(!empty($productIds))
{
$query = 'SELECT * FROM ' . TABLE_PRODUCTS_TO_CATEGORIES . ' WHERE products_id IN (' . implode(',', $productIds) . ')';
$results = xtc_db_query($query);
while ($row = xtc_db_fetch_array($results))
{
if(isset($productsToCategories[$row['products_id']]) === false)
{
$productsToCategories[$row['products_id']] = array();
}
$productsToCategories[$row['products_id']][] = $row['categories_id'];
}
}
}
if(empty($productIds) == false)
{
$query = "
SELECT
" . TABLE_SPECIALS . ".*,
" . TABLE_PRODUCTS_DESCRIPTION . ".*,
" . TABLE_PRODUCTS . ".*,
products_quantity_unit.quantity_unit_id
" . $personalOffersClause['select'] . "
FROM " . TABLE_PRODUCTS . "
LEFT JOIN " . TABLE_SPECIALS . " ON (" . TABLE_SPECIALS . ".products_id = " . TABLE_PRODUCTS . ".products_id)
" . $personalOffersClause['join'] . "
LEFT JOIN " . TABLE_PRODUCTS_DESCRIPTION . " ON (" . TABLE_PRODUCTS_DESCRIPTION . ".products_id = " . TABLE_PRODUCTS . ".products_id)
LEFT JOIN products_quantity_unit ON (products_quantity_unit.products_id = " . TABLE_PRODUCTS . ".products_id)
LEFT JOIN " . TABLE_PRODUCTS_TO_CATEGORIES . " ON (" . TABLE_PRODUCTS_TO_CATEGORIES . ".products_id = " . TABLE_PRODUCTS . ".products_id)
" . $whereClause . "
" . $limitation;
$results = xtc_db_query($query);
$currRecordId = 0;
$gxmlPropertyValues = MainFactory::create_object('GxmlProductCombis');
while ($row = xtc_db_fetch_array($results))
{
if ($currRecordId != $row['products_id'])
{
$productChildNode = $this->responseXml->products->addChild('product');
}
$categoriesIdArray = array(0);
if(isset($productsToCategories[$row['products_id']]))
{
$categoriesIdArray = $productsToCategories[$row['products_id']];
}
$row['categories_id'] = $categoriesIdArray;
$this->add($row, $productChildNode);
if ($currRecordId != $row['products_id'])
{
//add additional images
$this->_addImagesBlock($productChildNode, $row['products_id']);
// add combis
$gxmlPropertyValues->addProductsCombisNode( array( 'product_child' => $productChildNode, 'product_id' => $row['products_id'] ) );
// add xselling
$this->_addXsellingNode($productChildNode, $row['products_id']);
}
$currRecordId = $row['products_id'];
}
}
}
private function _addImagesBlock(SimpleXMLElement $productXml, $p_productsId)
{
$products_id = (int)$p_productsId;
$sql = "SELECT pi.*, ia.* FROM " . TABLE_PRODUCTS_IMAGES . " pi LEFT JOIN `gm_prd_img_alt` ia USING (image_id) WHERE pi.products_id = " . $products_id . " ORDER BY image_nr";
$result = xtc_db_query($sql);
if(xtc_db_num_rows($result) > 0)
{
$additionalImages = $productXml->addChild('additional_images');
$imageId = -1;
while($row = xtc_db_fetch_array($result))
{
if($imageId != $row['image_id'])
{
$image = $additionalImages->addChild('image');
$this->_addNode($row, 'image_id', 'image_id', $image);
$this->_addNode($row, 'image_name', 'filename', $image);
$this->_addNode($row, 'image_name', 'image_url', $image);
$this->_addNode($row, 'image_nr', 'sort_order', $image);
$this->_addNode($row, 'gm_show_image', 'visible', $image);
$imageId = $row['image_id'];
}
$this->_addNode($row, 'gm_alt_text', 'image_alt_text', $image);
}
}
}
/**
* Add an XSelling node to the response XML.
*
* @param SimpleXMLElement $productXml
* @param numeric $p_productsId
*/
protected function _addXsellingNode(SimpleXMLElement $productXml, $p_productsId)
{
$productsId = (int) $p_productsId;
$query = "SELECT xsell_id, sort_order FROM " . TABLE_PRODUCTS_XSELL . " WHERE products_id = " . $productsId . " ORDER BY sort_order";
$results = xtc_db_query($query);
if(xtc_db_num_rows($results) > 0)
{
$xsellingNode = $productXml->addChild('cross_selling_products');
while($row = xtc_db_fetch_array($results))
{
$xsellingProductNode = $xsellingNode->addChild('cross_selling_product');
$this->_addNode($row, 'xsell_id', 'product_id', $xsellingProductNode);
$this->_addNode($row, 'sort_order', 'sort_order', $xsellingProductNode);
}
}
}
/**
* Validate tax in a product XML node object.
*
* @param SimpleXMLElement $productXml Product node XML object to be validated.
* @param array $response (ByRef) Contains the response data.
*
* @return bool Returns the validation result.
*/
protected function _validateTax(SimpleXMLElement $productXml, array &$response)
{
$productsId = (string)$productXml->product_id;
$isMatched = false;
if(isset($productXml->tax_class_id) && !in_array((int)$productXml->tax_class_id, array_keys($this->taxArray)))
{
$response[] = array(
'external_' . $this->singularName . '_id' => '',
$this->singularName . '_id' => $productsId,
'success' => '0',
'errormessage' => 'given tax_class_id does not exist',
'action_performed' => 'error'
);
return false;
}
if(isset($productXml->tax_rate))
{
foreach($this->taxArray as $t_tax_class)
{
if((string)$productXml->tax_rate == $t_tax_class['tax_rate'])
{
if(isset($productXml->tax_class_id) && (int)$productXml->tax_class_id != $t_tax_class['tax_class_id'])
{
$response[] = array(
'external_' . $this->singularName . '_id' => '',
$this->singularName . '_id' => $productsId,
'success' => '0',
'errormessage' => 'tax_class_id and tax_rate are in conflict',
'action_performed' => 'error'
);
return false;
}
$isMatched = true;
$productXml->tax_class_id = $t_tax_class['tax_class_id'];
}
}
if(!$isMatched)
{
$response[] = array(
'external_' . $this->singularName . '_id' => '',
$this->singularName . '_id' => $productsId,
'success' => '0',
'errormessage' => 'no matching tax_class_id for given tax_rate found',
'action_performed' => 'error'
);
return false;
}
unset($productXml->tax_rate);
}
return true;
}
}