Version Notes
This version has a number of major updates, including:
- Reducing payload on unchanged products
- Enhanced support for configurable products, providing child products as variants
- Updated attribute support to enable attribute mapping in ShoppingFeeder
Features include:
- One-click feed export to numerous channels
- Built-in order tracking
- Click & referral tracking
- Historical order importing for reporting and ROI analysis
Download this release
Release Info
Developer | ShoppingFeeder |
Extension | shoppingfeeder |
Version | 1.2.0 |
Comparing to | |
See all releases |
Version 1.2.0
- app/code/community/ShoppingFeeder/Service/Block/Adminhtml/Service.php +34 -0
- app/code/community/ShoppingFeeder/Service/Block/Service.php +33 -0
- app/code/community/ShoppingFeeder/Service/Controller/FrontAuth.php +56 -0
- app/code/community/ShoppingFeeder/Service/Helper/Data.php +10 -0
- app/code/community/ShoppingFeeder/Service/Model/Auth.php +103 -0
- app/code/community/ShoppingFeeder/Service/Model/Observer.php +67 -0
- app/code/community/ShoppingFeeder/Service/Model/Offers.php +366 -0
- app/code/community/ShoppingFeeder/Service/Model/Orders.php +75 -0
- app/code/community/ShoppingFeeder/Service/controllers/AttributesController.php +31 -0
- app/code/community/ShoppingFeeder/Service/controllers/FeedController.php +98 -0
- app/code/community/ShoppingFeeder/Service/controllers/OrdersController.php +74 -0
- app/code/community/ShoppingFeeder/Service/controllers/TestController.php +274 -0
- app/code/community/ShoppingFeeder/Service/controllers/VersionController.php +23 -0
- app/code/community/ShoppingFeeder/Service/etc/config.xml +119 -0
- app/code/community/ShoppingFeeder/Service/etc/system.xml +74 -0
- app/etc/modules/ShoppingFeeder_Service.xml +20 -0
- package.xml +35 -0
app/code/community/ShoppingFeeder/Service/Block/Adminhtml/Service.php
ADDED
@@ -0,0 +1,34 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Admin grid container
|
4 |
+
*
|
5 |
+
* @author ShoppingFeeder
|
6 |
+
*/
|
7 |
+
class ShoppingFeeder_Service_Block_Adminhtml_Service extends
|
8 |
+
Mage_adminhtml_Block_Widget_Grid_Container
|
9 |
+
{
|
10 |
+
/**
|
11 |
+
* Block constructor
|
12 |
+
*/
|
13 |
+
public function __construct()
|
14 |
+
{
|
15 |
+
$this->_blockGroup = 'shoppingfeeder_service';
|
16 |
+
$this->_controller = 'adminhtml_service';
|
17 |
+
$this->_headerText = Mage::helper('shoppingfeeder_service')->__('Manage Service');
|
18 |
+
parent::__construct();
|
19 |
+
if (Mage::helper('shoppingfeeder_service/Admin')->isActionAllowed('save'))
|
20 |
+
{
|
21 |
+
$this->_updateButton('add', 'label',
|
22 |
+
Mage::helper('shoppingfeeder_service')->__('Add New News'));
|
23 |
+
} else {
|
24 |
+
$this->_removeButton('add');
|
25 |
+
}
|
26 |
+
$this->addButton(
|
27 |
+
'news_flush_images_cache',
|
28 |
+
array(
|
29 |
+
'label' => Mage::helper('shoppingfeeder_service')->__('Flush Images Cache'),
|
30 |
+
'onclick' => 'setLocation(\'' . $this->getUrl('*/*/flush') . '\')',
|
31 |
+
)
|
32 |
+
);
|
33 |
+
}
|
34 |
+
}
|
app/code/community/ShoppingFeeder/Service/Block/Service.php
ADDED
@@ -0,0 +1,33 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
*
|
4 |
+
* ShoppingFeeder XML generation code
|
5 |
+
*
|
6 |
+
* @category ShoppingFeeder
|
7 |
+
* @package ShoppingFeeder_Service
|
8 |
+
* @copyright Copyright (c) 2014 Kevin Tucker (http://www.shoppingfeeder.com)
|
9 |
+
*
|
10 |
+
*/
|
11 |
+
|
12 |
+
class ShoppingFeeder_Service_Block_Service extends Mage_Core_Block_Template
|
13 |
+
{
|
14 |
+
|
15 |
+
/**
|
16 |
+
* Block constructor
|
17 |
+
*/
|
18 |
+
public function __construct()
|
19 |
+
{
|
20 |
+
parent::__construct();
|
21 |
+
}
|
22 |
+
|
23 |
+
/**
|
24 |
+
* Get the offers
|
25 |
+
*
|
26 |
+
* @return collection|null
|
27 |
+
*/
|
28 |
+
public function getOffers()
|
29 |
+
{
|
30 |
+
return $this->_getData('offers');
|
31 |
+
}
|
32 |
+
|
33 |
+
}
|
app/code/community/ShoppingFeeder/Service/Controller/FrontAuth.php
ADDED
@@ -0,0 +1,56 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class ShoppingFeeder_Service_Controller_FrontAuth extends Mage_Core_Controller_Front_Action
|
4 |
+
{
|
5 |
+
public function preDispatch()
|
6 |
+
{
|
7 |
+
parent::preDispatch();
|
8 |
+
|
9 |
+
//DEBUG
|
10 |
+
// return $this;
|
11 |
+
|
12 |
+
//check Auth
|
13 |
+
if (!function_exists('getallheaders'))
|
14 |
+
{
|
15 |
+
function getallheaders()
|
16 |
+
{
|
17 |
+
$headers = '';
|
18 |
+
foreach ($_SERVER as $name => $value)
|
19 |
+
{
|
20 |
+
if (substr($name, 0, 5) == 'HTTP_')
|
21 |
+
{
|
22 |
+
$headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value;
|
23 |
+
}
|
24 |
+
}
|
25 |
+
return $headers;
|
26 |
+
}
|
27 |
+
}
|
28 |
+
|
29 |
+
$headers = getallheaders();
|
30 |
+
|
31 |
+
/** @var ShoppingFeeder_Service_Model_Auth $authModel */
|
32 |
+
$authModel = Mage::getModel('shoppingfeeder_service/auth');
|
33 |
+
|
34 |
+
$authResult = $authModel->auth(
|
35 |
+
$headers,
|
36 |
+
$this->getRequest()->getScheme(),
|
37 |
+
$this->getRequest()->getMethod()
|
38 |
+
);
|
39 |
+
|
40 |
+
if ($authResult !== true)
|
41 |
+
{
|
42 |
+
$responseData = array(
|
43 |
+
'status' => 'fail',
|
44 |
+
'data' => array (
|
45 |
+
'message' => $authResult
|
46 |
+
)
|
47 |
+
);
|
48 |
+
|
49 |
+
header('Content-type: application/json; charset=UTF-8');
|
50 |
+
echo json_encode($responseData);
|
51 |
+
exit();
|
52 |
+
}
|
53 |
+
|
54 |
+
return $this;
|
55 |
+
}
|
56 |
+
}
|
app/code/community/ShoppingFeeder/Service/Helper/Data.php
ADDED
@@ -0,0 +1,10 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Service Data Helper
|
4 |
+
*
|
5 |
+
* @author ShoppingFeeder
|
6 |
+
*/
|
7 |
+
class ShoppingFeeder_Service_Helper_Data extends Mage_Core_Helper_Data
|
8 |
+
{
|
9 |
+
|
10 |
+
}
|
app/code/community/ShoppingFeeder/Service/Model/Auth.php
ADDED
@@ -0,0 +1,103 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class ShoppingFeeder_Service_Model_Auth extends Mage_Core_Model_Abstract
|
4 |
+
{
|
5 |
+
const RANDOM_STRING = 'The mice all ate cheese together.';
|
6 |
+
const MAX_TIMEOUT = 300; //5 minutes
|
7 |
+
|
8 |
+
public function __construct()
|
9 |
+
{
|
10 |
+
$this->_init('shoppingfeeder_service/auth');
|
11 |
+
}
|
12 |
+
|
13 |
+
public static function auth(array $headers, $incomingScheme, $incomingMethod)
|
14 |
+
{
|
15 |
+
//check the API key
|
16 |
+
$incomingApiKey = '';
|
17 |
+
$incomingAuthTimestamp = strtotime('1970-00-00');
|
18 |
+
$incomingSignature = '';
|
19 |
+
foreach ($headers as $key => $value)
|
20 |
+
{
|
21 |
+
if (strtolower('X-SFApiKey') == strtolower($key))
|
22 |
+
{
|
23 |
+
$incomingApiKey = $value;
|
24 |
+
}
|
25 |
+
if (strtolower('X-SFTimestamp') == strtolower($key))
|
26 |
+
{
|
27 |
+
$incomingAuthTimestamp = $value;
|
28 |
+
}
|
29 |
+
if (strtolower('X-SFSignature') == strtolower($key))
|
30 |
+
{
|
31 |
+
$incomingSignature = $value;
|
32 |
+
}
|
33 |
+
}
|
34 |
+
|
35 |
+
//$sslInFront = Mage::getStoreConfig('web/secure/use_in_frontend');
|
36 |
+
//$useSsl = ($sslInFront == null) ? false : boolval($sslInFront);
|
37 |
+
$useSsl = false;
|
38 |
+
|
39 |
+
$apiKeys = self::getApiKeys();
|
40 |
+
|
41 |
+
if (!$useSsl || ($useSsl && $incomingScheme == 'https'))
|
42 |
+
{
|
43 |
+
//check the timestamp
|
44 |
+
if (time() - $incomingAuthTimestamp <= self::MAX_TIMEOUT)
|
45 |
+
{
|
46 |
+
$localApiKey = $apiKeys['api_key'];
|
47 |
+
if ($localApiKey == $incomingApiKey)
|
48 |
+
{
|
49 |
+
$localApiSecret = $apiKeys['api_secret'];
|
50 |
+
|
51 |
+
$stringToSign = $incomingMethod . "\n" .
|
52 |
+
$incomingAuthTimestamp . "\n" .
|
53 |
+
self::RANDOM_STRING;
|
54 |
+
|
55 |
+
if (function_exists('hash_hmac'))
|
56 |
+
{
|
57 |
+
$signature = hash_hmac('sha256', $stringToSign, $localApiSecret);
|
58 |
+
}
|
59 |
+
elseif (function_exists('mhash'))
|
60 |
+
{
|
61 |
+
$signature = bin2hex(mhash(MHASH_SHA256, $stringToSign, $localApiSecret));
|
62 |
+
}
|
63 |
+
else
|
64 |
+
{
|
65 |
+
return 'Authentication failed: Appropriate hashing function does not exist.';
|
66 |
+
}
|
67 |
+
|
68 |
+
if ($incomingSignature == $signature)
|
69 |
+
{
|
70 |
+
return true;
|
71 |
+
}
|
72 |
+
else
|
73 |
+
{
|
74 |
+
return 'Authentication failed: invalid credentials.';
|
75 |
+
}
|
76 |
+
}
|
77 |
+
else
|
78 |
+
{
|
79 |
+
return 'Authentication failed: invalid API key.';
|
80 |
+
}
|
81 |
+
}
|
82 |
+
else
|
83 |
+
{
|
84 |
+
return 'Authentication failed: timeout exceeded.';
|
85 |
+
}
|
86 |
+
}
|
87 |
+
else
|
88 |
+
{
|
89 |
+
return 'Authentication failed: non-secure connection';
|
90 |
+
}
|
91 |
+
}
|
92 |
+
|
93 |
+
public static function getApiKeys()
|
94 |
+
{
|
95 |
+
$localApiKey = Mage::getStoreConfig('shoppingfeeder/service/apikey');
|
96 |
+
$localApiSecret = Mage::getStoreConfig('shoppingfeeder/service/apisecret');
|
97 |
+
|
98 |
+
return array(
|
99 |
+
'api_key' => $localApiKey,
|
100 |
+
'api_secret' => $localApiSecret
|
101 |
+
);
|
102 |
+
}
|
103 |
+
}
|
app/code/community/ShoppingFeeder/Service/Model/Observer.php
ADDED
@@ -0,0 +1,67 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
class ShoppingFeeder_Service_Model_Observer extends Varien_Object
|
3 |
+
{
|
4 |
+
const SF_URL = 'https://www.shoppingfeeder.com/webhook/magento-orders/';
|
5 |
+
//const SF_URL = 'http://dev.shoppingfeeder.com/webhook/magento-orders/';
|
6 |
+
|
7 |
+
public function salesOrderPlaceAfter($observer)
|
8 |
+
{
|
9 |
+
try{
|
10 |
+
//if order tracking is set
|
11 |
+
//$sfEnabled = Mage::getStoreConfig('shoppingfeeder/service/enable');
|
12 |
+
$sfEnabled = true;
|
13 |
+
$sfTracking = Mage::getStoreConfig('shoppingfeeder/service/tracking');
|
14 |
+
if ($sfEnabled && $sfTracking)
|
15 |
+
{
|
16 |
+
/* @var Mage_Sales_Model_Order $order */
|
17 |
+
$order = $observer->getEvent()->getOrder();
|
18 |
+
|
19 |
+
Mage::log('salesOrderPlaceAfter Order ID: '.$order->getRealOrderId());
|
20 |
+
|
21 |
+
$this->_notifyShoppingFeeder($order);
|
22 |
+
}
|
23 |
+
}
|
24 |
+
catch (Exception $e)
|
25 |
+
{
|
26 |
+
Mage::log('_notifyShoppingFeeder Order ID: '.$order->getRealOrderId().' FAILED');
|
27 |
+
}
|
28 |
+
}
|
29 |
+
|
30 |
+
public function productView($observer)
|
31 |
+
{
|
32 |
+
try{
|
33 |
+
//here we're going to create the referral cookie for the visitor if they came from ShoppingFeeder
|
34 |
+
if (isset($_GET['SFDRREF']))
|
35 |
+
{
|
36 |
+
setcookie('SFDRREF', $_GET['SFDRREF'], time() + (60*60*24*30), '/');
|
37 |
+
$_COOKIE['SFDRREF']= $_GET['SFDRREF'];
|
38 |
+
}
|
39 |
+
}
|
40 |
+
catch (Exception $e)
|
41 |
+
{
|
42 |
+
|
43 |
+
}
|
44 |
+
}
|
45 |
+
|
46 |
+
protected function _notifyShoppingFeeder(Mage_Sales_Model_Order $order)
|
47 |
+
{
|
48 |
+
Mage::log('_notifyShoppingFeeder Order ID: '.$order->getRealOrderId());
|
49 |
+
|
50 |
+
//get API key value from admin settings
|
51 |
+
$apiKey = $sfTracking = Mage::getStoreConfig('shoppingfeeder/service/apikey');
|
52 |
+
|
53 |
+
$http = new Zend_Http_Client(self::SF_URL);
|
54 |
+
|
55 |
+
$http->setHeaders('X-SFApiKey', $apiKey);
|
56 |
+
|
57 |
+
$data = $order->toArray();
|
58 |
+
foreach ($order->getAllItems() as $lineItem)
|
59 |
+
{
|
60 |
+
$data['line_items'][] = $lineItem->toArray();
|
61 |
+
}
|
62 |
+
$data['landing_site_ref'] = isset($_COOKIE['SFDRREF']) ? $_COOKIE['SFDRREF'] : '';
|
63 |
+
|
64 |
+
$http->setRawData(Mage::helper('core')->jsonEncode($data));
|
65 |
+
$http->request(Zend_Http_Client::POST);
|
66 |
+
}
|
67 |
+
}
|
app/code/community/ShoppingFeeder/Service/Model/Offers.php
ADDED
@@ -0,0 +1,366 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class ShoppingFeeder_Service_Model_Offers extends Mage_Core_Model_Abstract
|
4 |
+
{
|
5 |
+
public function __construct()
|
6 |
+
{
|
7 |
+
$this->_init('shoppingfeeder_service/offers');
|
8 |
+
}
|
9 |
+
|
10 |
+
private function hasParent($product)
|
11 |
+
{
|
12 |
+
$parents = Mage::getModel('catalog/product_type_configurable')->getParentIdsByChild($product->getId());
|
13 |
+
return !empty($parents);
|
14 |
+
}
|
15 |
+
|
16 |
+
private function getProductInfo(Mage_Catalog_Model_Product $product, Mage_Catalog_Model_Product $parent = null, $variantOptions = null, $lastUpdate = null)
|
17 |
+
{
|
18 |
+
/** @var Mage_Catalog_Model_Product_Type_Configurable $configModel */
|
19 |
+
$configModel = Mage::getModel('catalog/product_type_configurable');
|
20 |
+
|
21 |
+
$p = array();
|
22 |
+
|
23 |
+
$isVariant = !is_null($parent);
|
24 |
+
|
25 |
+
/**
|
26 |
+
* We only want to pull variants (children of configurable products) that are children, not as standalone products
|
27 |
+
*/
|
28 |
+
//if this product's parent is visible in catalog and search, Mage_Catalog_Model_Product_Visibility::VISIBILITY_BOTH,
|
29 |
+
//we will find this product when we fetch all the children of this parent through a normal iteration, so return nothing
|
30 |
+
if (!$isVariant && $this->hasParent($product))
|
31 |
+
{
|
32 |
+
return array();
|
33 |
+
}
|
34 |
+
|
35 |
+
if ($isVariant)
|
36 |
+
{
|
37 |
+
$variant = $product;
|
38 |
+
$product = $parent;
|
39 |
+
}
|
40 |
+
|
41 |
+
$data = $product->getData();
|
42 |
+
|
43 |
+
/* @var Mage_CatalogInventory_Model_Stock_Item $stockItem */
|
44 |
+
$stockItem = Mage::getModel('cataloginventory/stock_item')->loadByProduct($product);
|
45 |
+
|
46 |
+
$attributes = $product->getAttributes();
|
47 |
+
$manufacturer = '';
|
48 |
+
$brand = '';
|
49 |
+
|
50 |
+
$usefulAttributes = array();
|
51 |
+
|
52 |
+
/**
|
53 |
+
* @var Mage_Eav_Model_Entity_Attribute_Abstract $attribute
|
54 |
+
*/
|
55 |
+
// var_dump("");
|
56 |
+
// var_dump("");
|
57 |
+
// var_dump("");
|
58 |
+
foreach ($attributes as $attribute)
|
59 |
+
{
|
60 |
+
$attributeCode = $attribute->getAttributeCode();
|
61 |
+
$attributeLabel = $attribute->getData('frontend_label');
|
62 |
+
$value = $attribute->getFrontend()->getValue($product);
|
63 |
+
|
64 |
+
// var_dump($attributeCode. ' : '.print_r($value, true));
|
65 |
+
// var_dump($attributeLabel. ' : '.print_r($value, true));
|
66 |
+
|
67 |
+
if (preg_match('/^manufacturer$/i', $attributeCode) || preg_match('/^manufacturer$/i', $attributeLabel))
|
68 |
+
{
|
69 |
+
$manufacturer = $value;
|
70 |
+
}
|
71 |
+
|
72 |
+
if (preg_match('/^brand$/i', $attributeCode) || preg_match('/^brand$/i', $attributeLabel))
|
73 |
+
{
|
74 |
+
$brand = $value;
|
75 |
+
}
|
76 |
+
|
77 |
+
/*
|
78 |
+
if (preg_match('/age/i', $attributeCode) || preg_match('/age/i', $attributeLabel))
|
79 |
+
{
|
80 |
+
$usefulAttributes['age'] = $value;
|
81 |
+
}
|
82 |
+
if (preg_match('/color|colour/i', $attributeCode) || preg_match('/color|colour/i', $attributeLabel))
|
83 |
+
{
|
84 |
+
$usefulAttributes['colour'] = $value;
|
85 |
+
}
|
86 |
+
if (preg_match('/size/i', $attributeCode) || preg_match('/size/i', $attributeLabel))
|
87 |
+
{
|
88 |
+
$usefulAttributes['size'] = $value;
|
89 |
+
}
|
90 |
+
if (preg_match('/gender|sex/i', $attributeCode) || preg_match('/gender|sex/i', $attributeLabel))
|
91 |
+
{
|
92 |
+
$usefulAttributes['gender'] = $value;
|
93 |
+
}
|
94 |
+
if (preg_match('/material/i', $attributeCode) || preg_match('/material/i', $attributeLabel))
|
95 |
+
{
|
96 |
+
$usefulAttributes['material'] = $value;
|
97 |
+
}
|
98 |
+
if (preg_match('/pattern/i', $attributeCode) || preg_match('/pattern/i', $attributeLabel))
|
99 |
+
{
|
100 |
+
$usefulAttributes['pattern'] = $value;
|
101 |
+
}
|
102 |
+
*/
|
103 |
+
$usefulAttributes[$attributeCode] = $value;
|
104 |
+
}
|
105 |
+
// exit();
|
106 |
+
|
107 |
+
//category path
|
108 |
+
$categories = $product->getCategoryIds();
|
109 |
+
|
110 |
+
$categoryPathsToEvaluate = array();
|
111 |
+
$maxDepth = 0;
|
112 |
+
$categoryPathToUse = '';
|
113 |
+
|
114 |
+
if (!empty($categories))
|
115 |
+
{
|
116 |
+
//we will get all the category paths and then use the most refined, deepest one
|
117 |
+
foreach ($categories as $rootCategoryId)
|
118 |
+
{
|
119 |
+
$depth = 0;
|
120 |
+
$category_path = '';
|
121 |
+
|
122 |
+
$mageCategoryPath = Mage::getModel('catalog/category')->load($rootCategoryId)->getPath();
|
123 |
+
$allCategoryIds = explode('/', $mageCategoryPath);
|
124 |
+
unset($allCategoryIds[0]);
|
125 |
+
|
126 |
+
$categoryPath = '';
|
127 |
+
/**
|
128 |
+
* @var Mage_Catalog_Model_Category $category
|
129 |
+
*/
|
130 |
+
foreach ($allCategoryIds as $categoryId)
|
131 |
+
{
|
132 |
+
$depth++;
|
133 |
+
$category = Mage::getModel('catalog/category')->load($categoryId);
|
134 |
+
$category_name = $category->getName();
|
135 |
+
if ($category_name != 'Root Catalog' && $category_name != 'Default Category')
|
136 |
+
{
|
137 |
+
if (!empty($categoryPath))
|
138 |
+
{
|
139 |
+
$categoryPath.= ' > ';
|
140 |
+
}
|
141 |
+
$categoryPath.= $category_name;
|
142 |
+
}
|
143 |
+
}
|
144 |
+
|
145 |
+
$categoryPathsToEvaluate[$rootCategoryId]['path'] = $categoryPath;
|
146 |
+
$categoryPathsToEvaluate[$rootCategoryId]['depth'] = $depth;
|
147 |
+
|
148 |
+
if ($maxDepth < $depth)
|
149 |
+
{
|
150 |
+
$maxDepth = $depth;
|
151 |
+
$categoryPathToUse = $categoryPath;
|
152 |
+
}
|
153 |
+
}
|
154 |
+
}
|
155 |
+
|
156 |
+
if ($isVariant && isset($variant))
|
157 |
+
{
|
158 |
+
$p['internal_variant_id'] = $variant->getId();
|
159 |
+
|
160 |
+
$variantOptionsTitle = array();
|
161 |
+
$variantPrice = $variantOptions['basePrice'];
|
162 |
+
|
163 |
+
$urlHashParts = array();
|
164 |
+
|
165 |
+
// Collect options applicable to the configurable product
|
166 |
+
foreach ($variantOptions['refactoredOptions'][$variant->getId()] as $attributeCode => $option) {
|
167 |
+
$variantOptionsTitle[] = $option['value'];
|
168 |
+
|
169 |
+
//add these configured attributes to the set of parent's attributes
|
170 |
+
$usefulAttributes[$attributeCode] = $option['value'];
|
171 |
+
|
172 |
+
$variantPrice += $option['price'];
|
173 |
+
|
174 |
+
$urlHashParts[] = $option['attributeId'].'='.$option['valueId'];
|
175 |
+
}
|
176 |
+
|
177 |
+
$variantOptionsTitle = implode(' / ', $variantOptionsTitle);
|
178 |
+
$title = $data['name'] . ' - ' . $variantOptionsTitle;
|
179 |
+
$sku = $variant->getData('sku');
|
180 |
+
$price = $variantPrice;
|
181 |
+
$imageUrl = $p['image_url'] = Mage::getBaseUrl(Mage_Core_Model_Store::URL_TYPE_MEDIA).
|
182 |
+
'catalog/product'.$variant->getImage();
|
183 |
+
$productUrl = $product->getProductUrl().'#'.implode('&', $urlHashParts);
|
184 |
+
|
185 |
+
// var_dump($variantOptionsTitle);
|
186 |
+
// var_dump($variantPrice);
|
187 |
+
// exit();
|
188 |
+
}
|
189 |
+
else
|
190 |
+
{
|
191 |
+
$p['internal_variant_id'] = '';
|
192 |
+
$title = $data['name'];
|
193 |
+
$sku = $data['sku'];
|
194 |
+
$price = $product->getPrice();
|
195 |
+
$imageUrl = $p['image_url'] = Mage::getBaseUrl(Mage_Core_Model_Store::URL_TYPE_MEDIA).
|
196 |
+
'catalog/product'.$product->getImage();
|
197 |
+
$productUrl = $product->getProductUrl();
|
198 |
+
}
|
199 |
+
|
200 |
+
//if we have previously captured this product and it hasn't changed, don't send through full payload
|
201 |
+
$wasPreviouslyCaptured = !is_null($lastUpdate) && isset($usefulAttributes['updated_at']) && strtotime($usefulAttributes['updated_at']) < $lastUpdate;
|
202 |
+
if ($wasPreviouslyCaptured)
|
203 |
+
{
|
204 |
+
$p['internal_id'] = $product->getId();
|
205 |
+
$p['internal_update_time'] = $usefulAttributes['updated_at'];
|
206 |
+
}
|
207 |
+
else
|
208 |
+
{
|
209 |
+
$p['category'] = $categoryPathToUse;
|
210 |
+
$p['title'] = $title;
|
211 |
+
$p['brand'] = ($brand=='No') ? (($manufacturer == 'No') ? '' : $manufacturer) : $brand;
|
212 |
+
$p['manufacturer'] = ($manufacturer=='No') ? $brand : $manufacturer;
|
213 |
+
$p['mpn'] = isset($data['model']) ? $data['model'] : $data['sku'];
|
214 |
+
$p['internal_id'] = $product->getId();
|
215 |
+
$p['description'] = $data['description'];
|
216 |
+
$p['short_description'] = $data['short_description'];
|
217 |
+
$p['weight'] = isset($data['weight']) ? $data['weight'] : 0.00;
|
218 |
+
$p['sku'] = $sku;
|
219 |
+
$p['gtin'] = '';
|
220 |
+
|
221 |
+
//$priceModel = $product->getPriceModel();
|
222 |
+
|
223 |
+
$p['price'] = $price;// Mage::helper('checkout')->convertPrice($priceModel->getPrice($product), false);
|
224 |
+
$salePrice = $product->getSpecialPrice();// Mage::helper('checkout')->convertPrice($priceModel->getFinalPrice(null, $product), false);
|
225 |
+
$p['sale_price'] = '';
|
226 |
+
$p['sale_price_effective_date'] = '';
|
227 |
+
if ($salePrice != $p['price'])
|
228 |
+
{
|
229 |
+
$p['sale_price'] = $salePrice;
|
230 |
+
if ($product->getSpecialFromDate()!=null && $product->getSpecialToDate()!=null)
|
231 |
+
{
|
232 |
+
$p['sale_price_effective_date'] = date("c", strtotime($product->getSpecialFromDate())).'/'.date("c", strtotime($product->getSpecialToDate()));
|
233 |
+
}
|
234 |
+
}
|
235 |
+
|
236 |
+
$p['delivery_cost'] = 0.00;
|
237 |
+
$p['tax'] = 0.00;
|
238 |
+
$p['url'] = $productUrl;
|
239 |
+
$p['internal_update_time'] = isset($usefulAttributes['updated_at']) ? $usefulAttributes['updated_at'] : '';
|
240 |
+
|
241 |
+
$p['image_url'] = $imageUrl;
|
242 |
+
$p['image_modified_time'] = date("c", filemtime($product->getMediaConfig()->getMediaPath($product->getImage())));
|
243 |
+
$p['availability'] = ($stockItem->getIsInStock())?'in stock':'out of stock';
|
244 |
+
$p['quantity'] = $stockItem->getQty();
|
245 |
+
$p['condition'] = '';
|
246 |
+
$p['availability_date'] = '';
|
247 |
+
$p['attributes'] = $usefulAttributes;
|
248 |
+
$imageGallery = array();
|
249 |
+
foreach ($product->getMediaGalleryImages() as $image)
|
250 |
+
{
|
251 |
+
$galleryImage = array();
|
252 |
+
$galleryImage['url'] = $image['url'];
|
253 |
+
$galleryImage['image_modified_time'] = date("c", filemtime($image['path']));
|
254 |
+
$imageGallery[] = $galleryImage;
|
255 |
+
}
|
256 |
+
$p['extra_images'] = $imageGallery;
|
257 |
+
}
|
258 |
+
|
259 |
+
return $p;
|
260 |
+
}
|
261 |
+
|
262 |
+
public function getItems($page = null, $numPerPage = 1000, $lastUpdate = null)
|
263 |
+
{
|
264 |
+
/* @var Mage_Catalog_Model_Resource_Eav_Mysql4_Product_Collection $collection */
|
265 |
+
$collection = Mage::getModel('catalog/product')->getCollection()
|
266 |
+
->addAttributeToSelect('*')
|
267 |
+
->addAttributeToFilter('status', Mage_Catalog_Model_Product_Status::STATUS_ENABLED)
|
268 |
+
->addAttributeToFilter('visibility', Mage_Catalog_Model_Product_Visibility::VISIBILITY_BOTH);
|
269 |
+
|
270 |
+
if (!is_null($page))
|
271 |
+
{
|
272 |
+
$offset = ($page * $numPerPage) - $numPerPage;
|
273 |
+
$productIds = $collection->getAllIds($numPerPage, $offset);
|
274 |
+
}
|
275 |
+
else
|
276 |
+
{
|
277 |
+
$productIds = $collection->getAllIds();
|
278 |
+
}
|
279 |
+
|
280 |
+
$products = array();
|
281 |
+
foreach ($productIds as $productId)
|
282 |
+
{
|
283 |
+
Mage::getModel('catalog/product')->reset();
|
284 |
+
$product = Mage::getModel('catalog/product')->load($productId);
|
285 |
+
|
286 |
+
/**
|
287 |
+
* Get variants, if there are any
|
288 |
+
* If there are variants that are visible in the catalog, we will skip them when we iterate normally
|
289 |
+
*/
|
290 |
+
|
291 |
+
//if we have a configurable product, capture the variants
|
292 |
+
if ($product->getTypeId() == 'configurable')
|
293 |
+
{
|
294 |
+
/** @var Mage_Catalog_Model_Product_Type_Configurable $configModel */
|
295 |
+
$configModel = Mage::getModel('catalog/product_type_configurable');
|
296 |
+
|
297 |
+
$variants = array_pop($configModel->getChildrenIds($product->getId()));
|
298 |
+
|
299 |
+
if (count($variants) > 0)
|
300 |
+
{
|
301 |
+
$parent = $product;
|
302 |
+
|
303 |
+
//get variant options
|
304 |
+
$layout = Mage::getSingleton('core/layout');
|
305 |
+
$block = $layout->createBlock('catalog/product_view_type_configurable');
|
306 |
+
$block->setProduct($parent);
|
307 |
+
$variantOptions = Mage::helper('core')->jsonDecode($block->getJsonConfig());
|
308 |
+
|
309 |
+
$variantAttributes = array();
|
310 |
+
foreach ($variantOptions['attributes'] as $attributeId => $options)
|
311 |
+
{
|
312 |
+
$code = $options['code'];
|
313 |
+
foreach ($options['options'] as $option)
|
314 |
+
{
|
315 |
+
$value = $option['label'];
|
316 |
+
$price = $option['price'];
|
317 |
+
$valueId = $option['id'];
|
318 |
+
foreach ($option['products'] as $productId)
|
319 |
+
{
|
320 |
+
$variantAttributes[$productId][$code]['value'] = $value;
|
321 |
+
$variantAttributes[$productId][$code]['price'] = $price;
|
322 |
+
$variantAttributes[$productId][$code]['valueId'] = $valueId;
|
323 |
+
$variantAttributes[$productId][$code]['attributeId'] = $attributeId;
|
324 |
+
}
|
325 |
+
}
|
326 |
+
}
|
327 |
+
$variantOptions['refactoredOptions'] = $variantAttributes;
|
328 |
+
|
329 |
+
|
330 |
+
foreach ($variants as $variantId)
|
331 |
+
{
|
332 |
+
/** @var Mage_Catalog_Model_Product $variant */
|
333 |
+
$variant = Mage::getModel('catalog/product')->load($variantId);
|
334 |
+
|
335 |
+
$productData = $this->getProductInfo($variant, $parent, $variantOptions, $lastUpdate);
|
336 |
+
if (!empty($productData))
|
337 |
+
{
|
338 |
+
$products[] = $productData;
|
339 |
+
}
|
340 |
+
}
|
341 |
+
}
|
342 |
+
}
|
343 |
+
else
|
344 |
+
{
|
345 |
+
$productData = $this->getProductInfo($product, null, null, $lastUpdate);
|
346 |
+
if (!empty($productData))
|
347 |
+
{
|
348 |
+
$products[] = $productData;
|
349 |
+
}
|
350 |
+
}
|
351 |
+
}
|
352 |
+
|
353 |
+
return $products;
|
354 |
+
}
|
355 |
+
|
356 |
+
public function getItem($itemId)
|
357 |
+
{
|
358 |
+
$products = array();
|
359 |
+
|
360 |
+
$product = Mage::getModel('catalog/product')->load($itemId);
|
361 |
+
|
362 |
+
$products[] = $this->getProductInfo($product);
|
363 |
+
|
364 |
+
return $products;
|
365 |
+
}
|
366 |
+
}
|
app/code/community/ShoppingFeeder/Service/Model/Orders.php
ADDED
@@ -0,0 +1,75 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class ShoppingFeeder_Service_Model_Orders extends Mage_Core_Model_Abstract
|
4 |
+
{
|
5 |
+
public function __construct()
|
6 |
+
{
|
7 |
+
$this->_init('shoppingfeeder_service/orders');
|
8 |
+
}
|
9 |
+
|
10 |
+
private function getOrderInfo(Mage_Sales_Model_Order $order)
|
11 |
+
{
|
12 |
+
$data = array();
|
13 |
+
|
14 |
+
$orderData = $order->getData();
|
15 |
+
|
16 |
+
//normalise order data for ShoppingFeeder
|
17 |
+
$data['order_id'] = $orderData['entity_id'];
|
18 |
+
$data['order_date'] = $orderData['created_at'];
|
19 |
+
$data['store_order_number'] = $orderData['increment_id'];
|
20 |
+
$data['store_order_user_id'] = $orderData['customer_id'];
|
21 |
+
$data['store_order_currency'] = $orderData['order_currency_code'];
|
22 |
+
$data['store_total_price'] = $orderData['grand_total'];
|
23 |
+
$data['store_total_line_items_price'] = $orderData['subtotal_incl_tax'];
|
24 |
+
$data['store_total_tax'] = $orderData['tax_amount'];
|
25 |
+
$data['store_order_total_discount'] = $orderData['discount_amount'];
|
26 |
+
$data['store_shipping_price'] = $orderData['shipping_incl_tax'];
|
27 |
+
|
28 |
+
$lineItems = array();
|
29 |
+
foreach($order->getAllItems() as $item)
|
30 |
+
{
|
31 |
+
$lineItems[] = $item->toArray();
|
32 |
+
}
|
33 |
+
$data['line_items'] = $lineItems;
|
34 |
+
|
35 |
+
return $data;
|
36 |
+
}
|
37 |
+
|
38 |
+
public function getItems($page = null, $numPerPage = 1000)
|
39 |
+
{
|
40 |
+
/* @var Mage_Catalog_Model_Resource_Eav_Mysql4_Product_Collection $collection */
|
41 |
+
$collection = Mage::getModel('sales/order')->getCollection()
|
42 |
+
->addAttributeToSelect('*')
|
43 |
+
->addAttributeToFilter('status', Mage_Sales_Model_Order::STATE_COMPLETE);
|
44 |
+
|
45 |
+
if (!is_null($page))
|
46 |
+
{
|
47 |
+
$offset = ($page * $numPerPage) - $numPerPage;
|
48 |
+
$orderIds = $collection->getAllIds($numPerPage, $offset);
|
49 |
+
}
|
50 |
+
else
|
51 |
+
{
|
52 |
+
$orderIds = $collection->getAllIds();
|
53 |
+
}
|
54 |
+
|
55 |
+
$orders = array();
|
56 |
+
/* @var Mage_Sales_Model_Order $order */
|
57 |
+
foreach ($orderIds as $orderId)
|
58 |
+
{
|
59 |
+
$order = Mage::getModel('sales/order')->load($orderId);
|
60 |
+
|
61 |
+
$orders[$order->getId()] = $this->getOrderInfo($order);
|
62 |
+
}
|
63 |
+
return $orders;
|
64 |
+
}
|
65 |
+
|
66 |
+
public function getItem($itemId)
|
67 |
+
{
|
68 |
+
$orders = array();
|
69 |
+
|
70 |
+
$order = Mage::getModel('sales/order')->load($itemId);
|
71 |
+
$orders[$order->getId()] = $this->getOrderInfo($order);
|
72 |
+
|
73 |
+
return $orders;
|
74 |
+
}
|
75 |
+
}
|
app/code/community/ShoppingFeeder/Service/controllers/AttributesController.php
ADDED
@@ -0,0 +1,31 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
//IMPORTANT - "Controller" directory is not autoloaded
|
4 |
+
require_once(Mage::getModuleDir('Controller','ShoppingFeeder_Service').DS.'Controller'.DS.'FrontAuth.php');
|
5 |
+
|
6 |
+
class ShoppingFeeder_Service_AttributesController extends ShoppingFeeder_Service_Controller_FrontAuth
|
7 |
+
{
|
8 |
+
public function indexAction()
|
9 |
+
{
|
10 |
+
set_time_limit(0);
|
11 |
+
|
12 |
+
$internalAttributes = Mage::getResourceModel('catalog/product_attribute_collection')
|
13 |
+
->getItems();
|
14 |
+
|
15 |
+
$attributes = array();
|
16 |
+
foreach ($internalAttributes as $attribute){
|
17 |
+
$attributes[$attribute->getAttributecode()] = $attribute->getFrontendLabel();
|
18 |
+
}
|
19 |
+
|
20 |
+
$responseData = array(
|
21 |
+
'status' => 'success',
|
22 |
+
'data' => array(
|
23 |
+
'attributes' => $attributes
|
24 |
+
)
|
25 |
+
);
|
26 |
+
|
27 |
+
header('Content-type: application/json; charset=UTF-8');
|
28 |
+
echo json_encode($responseData);
|
29 |
+
exit();
|
30 |
+
}
|
31 |
+
}
|
app/code/community/ShoppingFeeder/Service/controllers/FeedController.php
ADDED
@@ -0,0 +1,98 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
//IMPORTANT - "Controller" directory is not autoloaded
|
4 |
+
require_once(Mage::getModuleDir('Controller','ShoppingFeeder_Service').DS.'Controller'.DS.'FrontAuth.php');
|
5 |
+
|
6 |
+
class ShoppingFeeder_Service_FeedController extends ShoppingFeeder_Service_Controller_FrontAuth
|
7 |
+
{
|
8 |
+
public function indexAction()
|
9 |
+
{
|
10 |
+
set_time_limit(0);
|
11 |
+
|
12 |
+
/** @var ShoppingFeeder_Service_Model_Offers $offersModel */
|
13 |
+
$offersModel = Mage::getSingleton('shoppingfeeder_service/offers');
|
14 |
+
|
15 |
+
$page = $this->getRequest()->getParam('page', null);
|
16 |
+
$numPerPage = $this->getRequest()->getParam('num_per_page', 1000);
|
17 |
+
$offerId = $this->getRequest()->getParam('offer_id', null);
|
18 |
+
$lastUpdate = $this->getRequest()->getParam('last_update', null);
|
19 |
+
|
20 |
+
if (is_null($offerId))
|
21 |
+
{
|
22 |
+
$offers = $offersModel->getItems($page, $numPerPage, $lastUpdate);
|
23 |
+
}
|
24 |
+
else
|
25 |
+
{
|
26 |
+
$offers = $offersModel->getItem($offerId);
|
27 |
+
}
|
28 |
+
|
29 |
+
$responseData = array(
|
30 |
+
'status' => 'success',
|
31 |
+
'data' => array(
|
32 |
+
'page' => $page,
|
33 |
+
'num_per_page' => $numPerPage,
|
34 |
+
'offers' => $offers
|
35 |
+
)
|
36 |
+
);
|
37 |
+
|
38 |
+
header('Content-type: application/json; charset=UTF-8');
|
39 |
+
echo json_encode($responseData);
|
40 |
+
exit();
|
41 |
+
}
|
42 |
+
|
43 |
+
/** Old XML version */
|
44 |
+
/*
|
45 |
+
public function indexAction()
|
46 |
+
{
|
47 |
+
set_time_limit(0);
|
48 |
+
|
49 |
+
$offersModel = Mage::getSingleton('shoppingfeeder_service/offers');
|
50 |
+
|
51 |
+
$page = $this->getRequest()->getParam('page', null);
|
52 |
+
$numPerPage = $this->getRequest()->getParam('num_per_page', 1000);
|
53 |
+
|
54 |
+
$offers = $offersModel->getItems($page, $numPerPage);
|
55 |
+
header('Content-type: text/xml; charset=UTF-8');
|
56 |
+
echo '<?xml version="1.0" encoding="UTF-8"?>';
|
57 |
+
echo "\n".'<offers>';
|
58 |
+
foreach ($offers as $offer) {
|
59 |
+
echo "\n".'<offer>';
|
60 |
+
echo "\n".'<category><![CDATA['.$offer['category'].']]></category>';
|
61 |
+
echo "\n".'<title><![CDATA['.$offer['title'].']]></title>';
|
62 |
+
echo "\n".'<brand><![CDATA['.$offer['manufacturer'].']]></brand>';
|
63 |
+
echo "\n".'<manufacturer><![CDATA['.$offer['manufacturer'].']]></manufacturer>';
|
64 |
+
echo "\n".'<mpn><![CDATA['.$offer['mpn'].']]></mpn>';
|
65 |
+
echo "\n".'<sku><![CDATA['.$offer['sku'].']]></sku>';
|
66 |
+
echo "\n".'<gtin>'.$offer['gtin'].'</gtin>';
|
67 |
+
echo "\n".'<weight>'.$offer['weight'].'</weight>';
|
68 |
+
echo "\n".'<internal_id><![CDATA['.$offer['internal_id'].']]></internal_id>';
|
69 |
+
echo "\n".'<internal_variant_id><![CDATA['.$offer['internal_variant_id'].']]></internal_variant_id>';
|
70 |
+
echo "\n".'<description><![CDATA['.$offer['description'].']]></description>';
|
71 |
+
echo "\n".'<price>'.$offer['price'].'</price>';
|
72 |
+
echo "\n".'<sale_price>'.$offer['sale_price'].'</sale_price>';
|
73 |
+
echo "\n".'<sale_price_effective_date>'.$offer['sale_price_effective_date'].'</sale_price_effective_date>';
|
74 |
+
echo "\n".'<delivery_cost>'.$offer['delivery_cost'].'</delivery_cost>';
|
75 |
+
echo "\n".'<tax>'.$offer['tax'].'</tax>';
|
76 |
+
echo "\n".'<url><![CDATA['.$offer['url'].']]></url>';
|
77 |
+
echo "\n".'<image_url><![CDATA['.$offer['image_url'].']]></image_url>';
|
78 |
+
echo "\n".'<quantity>'.$offer['quantity'].'</quantity>';
|
79 |
+
echo "\n".'<condition>'.$offer['condition'].'</condition>';
|
80 |
+
echo "\n".'<availability>'.$offer['availability'].'</availability>';
|
81 |
+
echo "\n".'<availability_date>'.$offer['availability_date'].'</availability_date>';
|
82 |
+
foreach ($offer['attributes'] as $attributeName => $attributeValue) {
|
83 |
+
echo "\n".' <attribute name="'.htmlspecialchars($attributeName).'"><![CDATA['.$attributeValue.']]></attribute>';
|
84 |
+
}
|
85 |
+
foreach ($offer['extra_images'] as $imageUrl){
|
86 |
+
echo "\n".' <additional_image_link><![CDATA['.$imageUrl.']]></additional_image_link>';
|
87 |
+
}
|
88 |
+
echo "\n".'</offer>';
|
89 |
+
|
90 |
+
flush();
|
91 |
+
ob_flush();
|
92 |
+
}
|
93 |
+
echo "\n".'</offers>';
|
94 |
+
|
95 |
+
exit();
|
96 |
+
}
|
97 |
+
*/
|
98 |
+
}
|
app/code/community/ShoppingFeeder/Service/controllers/OrdersController.php
ADDED
@@ -0,0 +1,74 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
//IMPORTANT - "Controller" directory is not autoloaded
|
4 |
+
require_once(Mage::getModuleDir('Controller','ShoppingFeeder_Service').DS.'Controller'.DS.'FrontAuth.php');
|
5 |
+
|
6 |
+
class ShoppingFeeder_Service_OrdersController extends ShoppingFeeder_Service_Controller_FrontAuth
|
7 |
+
{
|
8 |
+
public function indexAction()
|
9 |
+
{
|
10 |
+
set_time_limit(0);
|
11 |
+
|
12 |
+
/** @var ShoppingFeeder_Service_Model_Orders $ordersModel */
|
13 |
+
$ordersModel = Mage::getSingleton('shoppingfeeder_service/orders');
|
14 |
+
|
15 |
+
$page = $this->getRequest()->getParam('page', null);
|
16 |
+
$numPerPage = $this->getRequest()->getParam('num_per_page', 1000);
|
17 |
+
$orderId = $this->getRequest()->getParam('order_id', null);
|
18 |
+
|
19 |
+
if (is_null($orderId))
|
20 |
+
{
|
21 |
+
$orders = $ordersModel->getItems($page, $numPerPage);
|
22 |
+
}
|
23 |
+
else
|
24 |
+
{
|
25 |
+
$orders = $ordersModel->getItem($orderId);
|
26 |
+
}
|
27 |
+
|
28 |
+
$responseData = array(
|
29 |
+
'status' => 'success',
|
30 |
+
'data' => array(
|
31 |
+
'page' => $page,
|
32 |
+
'num_per_page' => $numPerPage,
|
33 |
+
'orders' => $orders
|
34 |
+
)
|
35 |
+
);
|
36 |
+
|
37 |
+
header('Content-type: application/json; charset=UTF-8');
|
38 |
+
echo json_encode($responseData);
|
39 |
+
exit();
|
40 |
+
}
|
41 |
+
|
42 |
+
// public function createAction()
|
43 |
+
// {
|
44 |
+
// /** @var ShoppingFeeder_Service_Model_Orders $ordersModel */
|
45 |
+
// $ordersModel = Mage::getSingleton('shoppingfeeder_service/orders');
|
46 |
+
//
|
47 |
+
// if ($this->getRequest()->getMethod() == Zend_Http_Client::POST)
|
48 |
+
// {
|
49 |
+
// //create the order
|
50 |
+
// $order = $ordersModel->create();
|
51 |
+
//
|
52 |
+
//
|
53 |
+
// $responseData = array(
|
54 |
+
// 'status' => 'success',
|
55 |
+
// 'data' => array(
|
56 |
+
// 'order' => $order
|
57 |
+
// )
|
58 |
+
// );
|
59 |
+
// }
|
60 |
+
// else
|
61 |
+
// {
|
62 |
+
// $responseData = array(
|
63 |
+
// 'status' => 'fail',
|
64 |
+
// 'data' => array(
|
65 |
+
// 'message' => 'HTTP method incorrect, must be POST'
|
66 |
+
// )
|
67 |
+
// );
|
68 |
+
// }
|
69 |
+
//
|
70 |
+
// header('Content-type: application/json; charset=UTF-8');
|
71 |
+
// echo json_encode($responseData);
|
72 |
+
// exit();
|
73 |
+
// }
|
74 |
+
}
|
app/code/community/ShoppingFeeder/Service/controllers/TestController.php
ADDED
@@ -0,0 +1,274 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
//IMPORTANT - "Controller" directory is not autoloaded
|
4 |
+
require_once(Mage::getModuleDir('Controller','ShoppingFeeder_Service').DS.'Controller'.DS.'FrontAuth.php');
|
5 |
+
|
6 |
+
class ShoppingFeeder_Service_TestController extends Mage_Core_Controller_Front_Action
|
7 |
+
{
|
8 |
+
public function indexAction()
|
9 |
+
{
|
10 |
+
if (!function_exists('getallheaders'))
|
11 |
+
{
|
12 |
+
function getallheaders()
|
13 |
+
{
|
14 |
+
$headers = '';
|
15 |
+
foreach ($_SERVER as $name => $value)
|
16 |
+
{
|
17 |
+
if (substr($name, 0, 5) == 'HTTP_')
|
18 |
+
{
|
19 |
+
$headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value;
|
20 |
+
}
|
21 |
+
}
|
22 |
+
return $headers;
|
23 |
+
}
|
24 |
+
}
|
25 |
+
|
26 |
+
$requiresSsl = false;
|
27 |
+
|
28 |
+
try
|
29 |
+
{
|
30 |
+
/** @var ShoppingFeeder_Service_Model_Auth $authModel */
|
31 |
+
$authModel = Mage::getModel('shoppingfeeder_service/auth');
|
32 |
+
//check if this setup requires SSL
|
33 |
+
$sslInFront = Mage::getStoreConfig('web/secure/use_in_frontend');
|
34 |
+
$requiresSsl = ($sslInFront == null) ? false : $sslInFront;
|
35 |
+
|
36 |
+
$apiKeys = $authModel->getApiKeys();
|
37 |
+
|
38 |
+
if (!isset($apiKeys['api_key']) || empty($apiKeys['api_key']))
|
39 |
+
{
|
40 |
+
throw new Exception('API key not setup.');
|
41 |
+
}
|
42 |
+
|
43 |
+
if (!isset($apiKeys['api_secret']) || empty($apiKeys['api_secret']))
|
44 |
+
{
|
45 |
+
throw new Exception('API secret not setup.');
|
46 |
+
}
|
47 |
+
|
48 |
+
$headers = getallheaders();
|
49 |
+
|
50 |
+
$authResult = $authModel->auth(
|
51 |
+
$headers,
|
52 |
+
$this->getRequest()->getScheme(),
|
53 |
+
$this->getRequest()->getMethod()
|
54 |
+
);
|
55 |
+
|
56 |
+
if ($authResult === true)
|
57 |
+
{
|
58 |
+
set_time_limit(0);
|
59 |
+
|
60 |
+
$responseData = array(
|
61 |
+
'status' => 'success',
|
62 |
+
'data' => array(
|
63 |
+
'message' => 'Authorization OK',
|
64 |
+
'requires_ssl' => $requiresSsl
|
65 |
+
)
|
66 |
+
);
|
67 |
+
}
|
68 |
+
else
|
69 |
+
{
|
70 |
+
$responseData = array(
|
71 |
+
'status' => 'fail',
|
72 |
+
'data' => array (
|
73 |
+
'message' => 'Authorization failed: ['.$authResult.']',
|
74 |
+
'requires_ssl' => $requiresSsl
|
75 |
+
)
|
76 |
+
);
|
77 |
+
}
|
78 |
+
}
|
79 |
+
catch (Exception $e)
|
80 |
+
{
|
81 |
+
$responseData = array(
|
82 |
+
'status' => 'fail',
|
83 |
+
'data' => array (
|
84 |
+
'message' => $e->getMessage(),
|
85 |
+
'requires_ssl' => $requiresSsl
|
86 |
+
)
|
87 |
+
);
|
88 |
+
}
|
89 |
+
|
90 |
+
header('Content-type: application/json; charset=UTF-8');
|
91 |
+
echo json_encode($responseData);
|
92 |
+
exit();
|
93 |
+
}
|
94 |
+
|
95 |
+
public function debugAction()
|
96 |
+
{
|
97 |
+
if (function_exists('getallheaders'))
|
98 |
+
{
|
99 |
+
echo 'Function <b>getallheaders</b> <span style="color:green;">exists</span>'."<br>\n";
|
100 |
+
try
|
101 |
+
{
|
102 |
+
$headers = getallheaders();
|
103 |
+
echo 'Get headers succeeded: '.print_r($headers,true)."<br>\n";
|
104 |
+
}
|
105 |
+
catch (Exception $e)
|
106 |
+
{
|
107 |
+
echo 'Get headers failed: ['.$e->getMessage().']'."<br>\n";
|
108 |
+
}
|
109 |
+
}
|
110 |
+
else
|
111 |
+
{
|
112 |
+
try
|
113 |
+
{
|
114 |
+
function getallheaders()
|
115 |
+
{
|
116 |
+
$headers = '';
|
117 |
+
foreach ($_SERVER as $name => $value)
|
118 |
+
{
|
119 |
+
if (substr($name, 0, 5) == 'HTTP_')
|
120 |
+
{
|
121 |
+
$headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value;
|
122 |
+
}
|
123 |
+
}
|
124 |
+
return $headers;
|
125 |
+
}
|
126 |
+
echo 'Function <b>getallheaders</b> created'."<br>\n";
|
127 |
+
|
128 |
+
try
|
129 |
+
{
|
130 |
+
$headers = getallheaders();
|
131 |
+
echo 'Get headers succeeded: '.print_r($headers,true)."<br>\n";
|
132 |
+
}
|
133 |
+
catch (Exception $e)
|
134 |
+
{
|
135 |
+
echo 'Get headers failed: ['.$e->getMessage().']'."<br>\n";
|
136 |
+
}
|
137 |
+
}
|
138 |
+
catch (Exception $e)
|
139 |
+
{
|
140 |
+
echo 'Function <b>getallheaders</b> could not be created'."<br>\n";
|
141 |
+
}
|
142 |
+
}
|
143 |
+
|
144 |
+
if (function_exists('hash_hmac'))
|
145 |
+
{
|
146 |
+
echo 'Function <b>hash_hmac</b> <span style="color:green;">exists</span>'."<br>\n";
|
147 |
+
}
|
148 |
+
else
|
149 |
+
{
|
150 |
+
echo 'Function <b>hash_hmac</b> <span style="color:red;">does not exist</span>'."<br>\n";
|
151 |
+
}
|
152 |
+
|
153 |
+
if (function_exists('mhash'))
|
154 |
+
{
|
155 |
+
echo 'Function <b>mhash</b> <span style="color:green;">exists</span>'."<br>\n";
|
156 |
+
}
|
157 |
+
else
|
158 |
+
{
|
159 |
+
echo 'Function <b>mhash</b> <span style="color:red;">does not exist</span>'."<br>\n";
|
160 |
+
}
|
161 |
+
|
162 |
+
try
|
163 |
+
{
|
164 |
+
/** @var ShoppingFeeder_Service_Model_Auth $authModel */
|
165 |
+
$authModel = Mage::getModel('shoppingfeeder_service/auth');
|
166 |
+
echo '$authModel successfully instantiated'."<br>\n";
|
167 |
+
}
|
168 |
+
catch (Exception $e)
|
169 |
+
{
|
170 |
+
echo '$authModel could not be instantiated: ['.$e->getMessage().']'."<br>\n";
|
171 |
+
}
|
172 |
+
|
173 |
+
|
174 |
+
if (isset($authModel))
|
175 |
+
{
|
176 |
+
try
|
177 |
+
{
|
178 |
+
$apiKeys = $authModel->getApiKeys();
|
179 |
+
//hide from view
|
180 |
+
unset($apiKeys['api_secret']);
|
181 |
+
echo 'API Keys successfully fetched: '.print_r($apiKeys, true)."<br>\n";
|
182 |
+
|
183 |
+
try
|
184 |
+
{
|
185 |
+
$headers = getallheaders();
|
186 |
+
$authResult = $authModel->auth(
|
187 |
+
$headers,
|
188 |
+
$this->getRequest()->getScheme(),
|
189 |
+
$this->getRequest()->getMethod()
|
190 |
+
);
|
191 |
+
echo '$authresult successfully called: '.print_r($authResult,true)."<br>\n";
|
192 |
+
}
|
193 |
+
catch (Exception $e)
|
194 |
+
{
|
195 |
+
echo '$authresult could not be called: ['.$e->getMessage().']'."<br>\n";
|
196 |
+
}
|
197 |
+
}
|
198 |
+
catch (Exception $e)
|
199 |
+
{
|
200 |
+
echo 'API Keys could not be fetched: ['.$e->getMessage().']'."<br>\n";
|
201 |
+
}
|
202 |
+
}
|
203 |
+
|
204 |
+
$offersModel = false;
|
205 |
+
try {
|
206 |
+
$offersModel = Mage::getSingleton('shoppingfeeder_service/offers');
|
207 |
+
echo '$offersModel <span style="color:green;">successfully instantiated</span>'."<br>\n";
|
208 |
+
}
|
209 |
+
catch (Exception $e)
|
210 |
+
{
|
211 |
+
echo '$offersModel <span style="color:red;">could not</span> be instantiated: ['.$e->getMessage().']'."<br>\n";
|
212 |
+
|
213 |
+
}
|
214 |
+
|
215 |
+
$page = 1;
|
216 |
+
$numPerPage = 1;
|
217 |
+
$offers = false;
|
218 |
+
if ($offersModel)
|
219 |
+
{
|
220 |
+
try {
|
221 |
+
$page = 1;
|
222 |
+
$numPerPage = 1;
|
223 |
+
|
224 |
+
$offers = $offersModel->getItems($page, $numPerPage);
|
225 |
+
echo 'Fetch 1 product successful'."<br>\n";
|
226 |
+
}
|
227 |
+
catch (Exception $e)
|
228 |
+
{
|
229 |
+
echo 'Fetch 1 product <span style="color:red;">NOT</span> successful: ['.$e->getMessage().']'."<br>\n";
|
230 |
+
|
231 |
+
try {
|
232 |
+
echo 'Trying to get $collection'."<br>\n";
|
233 |
+
$collection = Mage::getModel('catalog/product')->getCollection()
|
234 |
+
->addAttributeToSelect('*')
|
235 |
+
->addAttributeToFilter('status', Mage_Catalog_Model_Product_Status::STATUS_ENABLED)
|
236 |
+
->addAttributeToFilter('visibility', 4);
|
237 |
+
echo '$collection <span style="color:green;">successfully instantiated</span>'."<br>\n";
|
238 |
+
}
|
239 |
+
catch (Exception $e)
|
240 |
+
{
|
241 |
+
echo '$collection <span style="color:red;">NOT</span> successful: ['.$e->getMessage().']'."<br>\n";
|
242 |
+
}
|
243 |
+
}
|
244 |
+
}
|
245 |
+
|
246 |
+
if ($offers)
|
247 |
+
{
|
248 |
+
try {
|
249 |
+
$responseData = array(
|
250 |
+
'status' => 'success',
|
251 |
+
'data' => array(
|
252 |
+
'page' => $page,
|
253 |
+
'num_per_page' => $numPerPage,
|
254 |
+
'offers' => $offers
|
255 |
+
)
|
256 |
+
);
|
257 |
+
|
258 |
+
echo json_encode($responseData);
|
259 |
+
}
|
260 |
+
catch (Exception $e)
|
261 |
+
{
|
262 |
+
echo 'Could not output JSON: ['.$e->getMessage().']'."<br>\n";
|
263 |
+
}
|
264 |
+
}
|
265 |
+
|
266 |
+
exit();
|
267 |
+
}
|
268 |
+
|
269 |
+
public function debug2Action()
|
270 |
+
{
|
271 |
+
echo("DEBUG-DEBUG");
|
272 |
+
exit();
|
273 |
+
}
|
274 |
+
}
|
app/code/community/ShoppingFeeder/Service/controllers/VersionController.php
ADDED
@@ -0,0 +1,23 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
//IMPORTANT - "Controller" directory is not autoloaded
|
4 |
+
require_once(Mage::getModuleDir('Controller','ShoppingFeeder_Service').DS.'Controller'.DS.'FrontAuth.php');
|
5 |
+
|
6 |
+
class ShoppingFeeder_Service_VersionController extends Mage_Core_Controller_Front_Action
|
7 |
+
{
|
8 |
+
protected static $_version = '1.1.6';
|
9 |
+
|
10 |
+
public function indexAction()
|
11 |
+
{
|
12 |
+
$responseData = array(
|
13 |
+
'status' => 'success',
|
14 |
+
'data' => array(
|
15 |
+
'version' => self::$_version
|
16 |
+
)
|
17 |
+
);
|
18 |
+
|
19 |
+
header('Content-type: application/json; charset=UTF-8');
|
20 |
+
echo json_encode($responseData);
|
21 |
+
exit();
|
22 |
+
}
|
23 |
+
}
|
app/code/community/ShoppingFeeder/Service/etc/config.xml
ADDED
@@ -0,0 +1,119 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?xml version="1.0"?>
|
2 |
+
<!--
|
3 |
+
/**
|
4 |
+
* Module config
|
5 |
+
*
|
6 |
+
* @author ShoppingFeeder
|
7 |
+
*/
|
8 |
+
-->
|
9 |
+
<config>
|
10 |
+
<modules>
|
11 |
+
<ShoppingFeeder_Service>
|
12 |
+
<version>1.0.0</version>
|
13 |
+
</ShoppingFeeder_Service>
|
14 |
+
</modules>
|
15 |
+
<global>
|
16 |
+
<models>
|
17 |
+
<shoppingfeeder_service>
|
18 |
+
<class>ShoppingFeeder_Service_Model</class>
|
19 |
+
</shoppingfeeder_service>
|
20 |
+
</models>
|
21 |
+
<helpers>
|
22 |
+
<shoppingfeeder_service>
|
23 |
+
<class>ShoppingFeeder_Service_Helper</class>
|
24 |
+
</shoppingfeeder_service>
|
25 |
+
</helpers>
|
26 |
+
<blocks>
|
27 |
+
<shoppingfeeder_service>
|
28 |
+
<class>ShoppingFeeder_Service_Block</class>
|
29 |
+
</shoppingfeeder_service>
|
30 |
+
</blocks>
|
31 |
+
<resources>
|
32 |
+
<shoppingfeeder_setup>
|
33 |
+
<setup>
|
34 |
+
<module>ShoppingFeeder_Service</module>
|
35 |
+
<class>Mage_Core_Model_Resource_Setup</class>
|
36 |
+
</setup>
|
37 |
+
</shoppingfeeder_setup>
|
38 |
+
</resources>
|
39 |
+
<events>
|
40 |
+
<sales_order_place_after>
|
41 |
+
<observers>
|
42 |
+
<shoppingfeeder_notify_sales_order_place_after>
|
43 |
+
<class>shoppingfeeder_service/observer</class>
|
44 |
+
<method>salesOrderPlaceAfter</method>
|
45 |
+
</shoppingfeeder_notify_sales_order_place_after>
|
46 |
+
</observers>
|
47 |
+
</sales_order_place_after>
|
48 |
+
<!--<before_service_item_display>-->
|
49 |
+
<!--<observers>-->
|
50 |
+
<!--<shoppingfeeder_service>-->
|
51 |
+
<!--<class>shoppingfeeder_service/observer</class>-->
|
52 |
+
<!--<method>beforeServiceDisplayed</method>-->
|
53 |
+
<!--</shoppingfeeder_service>-->
|
54 |
+
<!--</observers>-->
|
55 |
+
<!--</before_service_item_display>-->
|
56 |
+
</events>
|
57 |
+
</global>
|
58 |
+
<frontend>
|
59 |
+
<routers>
|
60 |
+
<shoppingfeeder>
|
61 |
+
<use>standard</use>
|
62 |
+
<args>
|
63 |
+
<module>ShoppingFeeder_Service</module>
|
64 |
+
<frontName>shoppingfeeder</frontName>
|
65 |
+
</args>
|
66 |
+
</shoppingfeeder>
|
67 |
+
</routers>
|
68 |
+
<events>
|
69 |
+
<catalog_controller_product_view>
|
70 |
+
<observers>
|
71 |
+
<shoppingfeeder_notify_catalog_controller_product_view>
|
72 |
+
<class>shoppingfeeder_service/observer</class>
|
73 |
+
<method>productView</method>
|
74 |
+
</shoppingfeeder_notify_catalog_controller_product_view>
|
75 |
+
</observers>
|
76 |
+
</catalog_controller_product_view>
|
77 |
+
</events>
|
78 |
+
</frontend>
|
79 |
+
<admin>
|
80 |
+
<routers>
|
81 |
+
<adminhtml>
|
82 |
+
<args>
|
83 |
+
<modules>
|
84 |
+
<ShoppingFeeder_Service before="Mage_adminhtml">Shoppingfeeder_Service_Adminhtml</ShoppingFeeder_Service>
|
85 |
+
</modules>
|
86 |
+
</args>
|
87 |
+
</adminhtml>
|
88 |
+
</routers>
|
89 |
+
</admin>
|
90 |
+
<adminhtml>
|
91 |
+
<acl>
|
92 |
+
<resources>
|
93 |
+
<admin>
|
94 |
+
<children>
|
95 |
+
<system>
|
96 |
+
<children>
|
97 |
+
<config>
|
98 |
+
<children>
|
99 |
+
<shoppingfeeder>
|
100 |
+
<title>ShoppingFeeder Section</title>
|
101 |
+
</shoppingfeeder>
|
102 |
+
</children>
|
103 |
+
</config>
|
104 |
+
</children>
|
105 |
+
</system>
|
106 |
+
</children>
|
107 |
+
</admin>
|
108 |
+
</resources>
|
109 |
+
</acl>
|
110 |
+
</adminhtml>
|
111 |
+
<default>
|
112 |
+
<shoppingfeeder>
|
113 |
+
<service>
|
114 |
+
<enable>1</enable>
|
115 |
+
<tracking>1</tracking>
|
116 |
+
</service>
|
117 |
+
</shoppingfeeder>
|
118 |
+
</default>
|
119 |
+
</config>
|
app/code/community/ShoppingFeeder/Service/etc/system.xml
ADDED
@@ -0,0 +1,74 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?xml version="1.0"?>
|
2 |
+
<!--
|
3 |
+
/**
|
4 |
+
* Admin menu config
|
5 |
+
*
|
6 |
+
* @author ShoppingFeeder
|
7 |
+
*/
|
8 |
+
-->
|
9 |
+
<config>
|
10 |
+
<sections>
|
11 |
+
<shoppingfeeder translate="label">
|
12 |
+
<class>separator-top</class>
|
13 |
+
<label>ShoppingFeeder</label>
|
14 |
+
<tab>catalog</tab>
|
15 |
+
<frontend_type>text</frontend_type>
|
16 |
+
<sort_order>500</sort_order>
|
17 |
+
<show_in_default>1</show_in_default>
|
18 |
+
<show_in_website>1</show_in_website>
|
19 |
+
<show_in_store>1</show_in_store>
|
20 |
+
|
21 |
+
<groups>
|
22 |
+
<service translate="label">
|
23 |
+
<label>Configuration</label>
|
24 |
+
<frontend_type>text</frontend_type>
|
25 |
+
<sort_order>10</sort_order>
|
26 |
+
<show_in_default>1</show_in_default>
|
27 |
+
<show_in_website>1</show_in_website>
|
28 |
+
<show_in_store>1</show_in_store>
|
29 |
+
<expanded>1</expanded>
|
30 |
+
<fields>
|
31 |
+
<!--<enable translate="label">-->
|
32 |
+
<!--<label>Enable ShoppingFeeder</label>-->
|
33 |
+
<!--<frontend_type>select</frontend_type>-->
|
34 |
+
<!--<source_model>adminhtml/system_config_source_yesno</source_model>-->
|
35 |
+
<!--<sort_order>1</sort_order>-->
|
36 |
+
<!--<show_in_default>1</show_in_default>-->
|
37 |
+
<!--<show_in_website>1</show_in_website>-->
|
38 |
+
<!--<show_in_store>1</show_in_store>-->
|
39 |
+
<!--</enable>-->
|
40 |
+
<apikey translate="label">
|
41 |
+
<label>ShoppingFeeder API Key</label>
|
42 |
+
<frontend_type>text</frontend_type>
|
43 |
+
<source_model>adminhtml/system_config_source_yesno</source_model>
|
44 |
+
<sort_order>1</sort_order>
|
45 |
+
<show_in_default>1</show_in_default>
|
46 |
+
<show_in_website>1</show_in_website>
|
47 |
+
<show_in_store>1</show_in_store>
|
48 |
+
<validate>required-entry</validate>
|
49 |
+
</apikey>
|
50 |
+
<apisecret translate="label">
|
51 |
+
<label>ShoppingFeeder API Secret</label>
|
52 |
+
<frontend_type>text</frontend_type>
|
53 |
+
<source_model>adminhtml/system_config_source_yesno</source_model>
|
54 |
+
<sort_order>1</sort_order>
|
55 |
+
<show_in_default>1</show_in_default>
|
56 |
+
<show_in_website>1</show_in_website>
|
57 |
+
<show_in_store>1</show_in_store>
|
58 |
+
<validate>required-entry</validate>
|
59 |
+
</apisecret>
|
60 |
+
<tracking translate="label">
|
61 |
+
<label>Enable Order Tracking</label>
|
62 |
+
<frontend_type>select</frontend_type>
|
63 |
+
<source_model>adminhtml/system_config_source_yesno</source_model>
|
64 |
+
<sort_order>2</sort_order>
|
65 |
+
<show_in_default>1</show_in_default>
|
66 |
+
<show_in_website>1</show_in_website>
|
67 |
+
<show_in_store>1</show_in_store>
|
68 |
+
</tracking>
|
69 |
+
</fields>
|
70 |
+
</service>
|
71 |
+
</groups>
|
72 |
+
</shoppingfeeder>
|
73 |
+
</sections>
|
74 |
+
</config>
|
app/etc/modules/ShoppingFeeder_Service.xml
ADDED
@@ -0,0 +1,20 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?xml version="1.0"?>
|
2 |
+
<!--
|
3 |
+
/**
|
4 |
+
* Module initial config
|
5 |
+
*
|
6 |
+
* @author ShoppingFeeder
|
7 |
+
*/
|
8 |
+
-->
|
9 |
+
<config>
|
10 |
+
<modules>
|
11 |
+
<ShoppingFeeder_Service>
|
12 |
+
<active>true</active>
|
13 |
+
<codePool>community</codePool>
|
14 |
+
<depends>
|
15 |
+
<Mage_Core/>
|
16 |
+
<Mage_Adminhtml />
|
17 |
+
</depends>
|
18 |
+
</ShoppingFeeder_Service>
|
19 |
+
</modules>
|
20 |
+
</config>
|
package.xml
ADDED
@@ -0,0 +1,35 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?xml version="1.0"?>
|
2 |
+
<package>
|
3 |
+
<name>shoppingfeeder</name>
|
4 |
+
<version>1.2.0</version>
|
5 |
+
<stability>stable</stability>
|
6 |
+
<license>GNU General Public License (GPL)</license>
|
7 |
+
<channel>community</channel>
|
8 |
+
<extends/>
|
9 |
+
<summary>ShoppingFeeder allows you to manage product feeds for any kind of channel, and track everything.</summary>
|
10 |
+
<description>ShoppingFeeder allows you to manage product feeds for any kind of channel - and get a holistic view of traffic, conversions and ROI.
|
11 |
+

|
12 |
+
<b>By far the best value extension out there!</b>
|
13 |
+

|
14 |
+
Use ShoppingFeeder to import your Shopify product catalogue, export it to numerous channels that have various feed specifications and requirements and then track all the clicks, referrals, conversions that result from the distribution of your product date.
|
15 |
+

|
16 |
+
Export to Google, Shopping.com, Nextag, kelkoo, PriceCheck, Shopmania, Fruugo and more!
|
17 |
+

|
18 |
+
To set up your ShoppingFeeder account and install this extension seamlessly, create an account at: <a href="http://www.shoppingfeeder.com/register">http://www.shoppingfeeder.com/register</a></description>
|
19 |
+
<notes>This version has a number of major updates, including:
|
20 |
+
- Reducing payload on unchanged products
|
21 |
+
- Enhanced support for configurable products, providing child products as variants
|
22 |
+
- Updated attribute support to enable attribute mapping in ShoppingFeeder
|
23 |
+

|
24 |
+
Features include:
|
25 |
+
- One-click feed export to numerous channels
|
26 |
+
- Built-in order tracking
|
27 |
+
- Click & referral tracking
|
28 |
+
- Historical order importing for reporting and ROI analysis</notes>
|
29 |
+
<authors><author><name>ShoppingFeeder</name><user>shoppingfeeder</user><email>support@shoppingfeeder.com</email></author></authors>
|
30 |
+
<date>2015-04-13</date>
|
31 |
+
<time>08:25:15</time>
|
32 |
+
<contents><target name="mageetc"><dir name="modules"><file name="ShoppingFeeder_Service.xml" hash="90b374109c2d1281ddf527f24fa7d914"/></dir></target><target name="magecommunity"><dir name="ShoppingFeeder"><dir name="Service"><dir name="Block"><dir name="Adminhtml"><file name="Service.php" hash="e94d54bc342dc2941753ad635c0454a3"/></dir><file name="Service.php" hash="48874f0e80ce70686b81eb5380e9f498"/></dir><dir name="Controller"><file name="FrontAuth.php" hash="2dc20fec996f1c02ad8b9374af432ec0"/></dir><dir name="Helper"><file name="Data.php" hash="17589bd08352e497806bef9884972300"/></dir><dir name="Model"><file name="Auth.php" hash="2cff17b0750ff70695b32524627b2aaf"/><file name="Observer.php" hash="79c5aa286d8bfacbe5b4c759b8b0c5f1"/><file name="Offers.php" hash="45ca08e63a13a46795d8e3025cfa47e7"/><file name="Orders.php" hash="682845c908726831937d648ec966db9f"/></dir><dir name="controllers"><file name="AttributesController.php" hash="163472c6ed07a2d9fea4c933a5b6f446"/><file name="FeedController.php" hash="6d469ec267e6e03c6d3a66821bd24848"/><file name="OrdersController.php" hash="07d47f30b9740c9dbb3cebbc54ca915f"/><file name="TestController.php" hash="77604f9f9660c4bcd8ad166160945c85"/><file name="VersionController.php" hash="af8303ea5297a3499f183ae1787f6d2b"/></dir><dir name="etc"><file name="config.xml" hash="51fe66a6abd05e684e66c8b90241a9dc"/><file name="system.xml" hash="9681c74fa8886143197932690616e2dd"/></dir></dir></dir></target></contents>
|
33 |
+
<compatible/>
|
34 |
+
<dependencies><required><php><min>5.1.0</min><max>6.0.0</max></php></required></dependencies>
|
35 |
+
</package>
|