*/ if(!defined('AMAZON_APIKEY')) define('AMAZON_APIKEY','0R9FK149P6SYHXZZDZ82'); /** * All DokuWiki plugins to extend the parser/rendering mechanism * need to inherit from this class */ class syntax_plugin_amazon extends DokuWiki_Syntax_Plugin { /** * What kind of syntax are we? */ function getType(){ return 'substition'; } function getPType(){ return 'block'; } /** * Where to sort in? */ function getSort(){ return 160; } /** * Connect pattern to lexer */ function connectTo($mode) { $this->Lexer->addSpecialPattern('\{\{amazon>[\w:\\- =]+\}\}',$mode,'plugin_amazon'); $this->Lexer->addSpecialPattern('\{\{wishlist>[\w:\\- =]+\}\}',$mode,'plugin_amazon'); $this->Lexer->addSpecialPattern('\{\{amazonlist>[\w:\\- =]+\}\}',$mode,'plugin_amazon'); } /** * Do all the API work, fetch the data, parse it and return it for the renderer */ function handle($match, $state, $pos, Doku_Handler $handler){ // check type and remove markup if(substr($match,2,8) == 'wishlist'){ $match = substr($match,11,-2); $type = 'wishlist'; }elseif(substr($match,2,10) == 'amazonlist'){ $match = substr($match,13,-2); $type = 'amazonlist'; }else{ $match = substr($match,9,-2); $type = 'product'; } list($ctry,$asin) = explode(':',$match,2); // default parameters... $params = array( 'type' => $type, 'imgw' => $this->getConf('imgw'), 'imgh' => $this->getConf('imgh'), 'maxlen' => $this->getConf('maxlen'), 'price' => $this->getConf('showprice'), 'purchased' => $this->getConf('showpurchased'), 'sort' => $this->getConf('sort'), ); // ...can be overridden list($asin,$more) = explode(' ',$asin,2); if(preg_match('/(\d+)x(\d+)/i',$more,$match)){ $params['imgw'] = $match[1]; $params['imgh'] = $match[2]; } if(preg_match('/=(\d+)/',$more,$match)){ $params['maxlen'] = $match[1]; } if(preg_match('/noprice/i',$more,$match)){ $params['price'] = false; }elseif(preg_match('/(show)?price/i',$more,$match)){ $params['price'] = true; } if(preg_match('/nopurchased/i',$more,$match)){ $params['purchased'] = false; }elseif(preg_match('/(show)?purchased/i',$more,$match)){ $params['purchased'] = true; } if(preg_match('/sortprice/i',$more,$match)){ $params['sort'] = 'Price'; }elseif(preg_match('/sortpriority/i',$more,$match)){ $params['sort'] = 'Priority'; }elseif(preg_match('/sortadded/i',$more,$match)){ $params['sort'] = 'DateAdded'; } // no country given? if(empty($asin)){ $asin = $ctry; $ctry = 'us'; } // correct country given? if(!preg_match('/^(us|uk|jp|de|fr|ca)$/',$ctry)){ $ctry = 'us'; } // get partner id $partner = $this->getConf('partner_'.$ctry); // correct domains if($ctry == 'us') $ctry = 'com'; if($ctry == 'uk') $ctry = 'co.uk'; // basic API parameters $opts = array(); $opts['Service'] = 'AWSECommerceService'; $opts['AWSAccessKeyId'] = AMAZON_APIKEY; $opts['AssociateTag'] = $partner; if($type == 'product'){ // parameters for querying a single product $opts['Operation'] = 'ItemLookup'; $opts['ResponseGroup'] = 'Medium,OfferSummary'; if(strlen($asin)<13){ $opts['IdType'] = 'ASIN'; $opts['ItemId'] = $asin; }else{ $opts['SearchIndex'] = 'Books'; $opts['IdType'] = 'ISBN'; $opts['ItemId'] = $asin; } }else{ // parameters to query a wishlist $opts['Operation'] = 'ListLookup'; $opts['ResponseGroup'] = 'ListItems,Medium,OfferSummary'; $opts['ListId'] = $asin; $opts['Sort'] = $params['sort']; $opts['IsIncludeUniversal'] = 'True'; $opts['IsOmitPurchasedItems'] = ($params['purchased'] ? 'False' : 'True'); if($type == 'wishlist'){ $opts['ListType'] = 'WishList'; }else{ $opts['ListType'] = 'Listmania'; } } // support paged results $result = array(); $pages = 1; for($page=1; $page <= $pages; $page++){ $opts['ProductPage'] = $page; // fetch it $http = new DokuHTTPClient(); $url = $this->_signedRequestURI($ctry,$opts,$this->getConf('publickey'),$this->getConf('privatekey')); $xml = $http->get($url); if(empty($xml)){ if($http->error) return $http->error; if($http->status == 403) return 'Signature check failed, did you set your Access Keys in config?'; return 'unkown error'; } // parse it require_once(dirname(__FILE__).'/XMLParser.php'); $xmlp = new XMLParser($xml); $data = $xmlp->getTree(); //dbg($data); // check for errors and return the item(s) if($type == 'product'){ // error? if($data['ITEMLOOKUPRESPONSE'][0]['ITEMS'][0]['REQUEST'][0]['ERRORS']){ return $data['ITEMLOOKUPRESPONSE'][0]['ITEMS'][0]['REQUEST'][0] ['ERRORS'][0]['ERROR'][0]['MESSAGE'][0]['VALUE']; } // return item $result = array_merge($result, (array) $data['ITEMLOOKUPRESPONSE'][0]['ITEMS'][0]['ITEM']); }else{ // error? if($data['LISTLOOKUPRESPONSE'][0]['LISTS'][0]['REQUEST'][0]['ERRORS']){ return $data['LISTLOOKUPRESPONSE'][0]['LISTS'][0]['REQUEST'][0] ['ERRORS'][0]['ERROR'][0]['MESSAGE'][0]['VALUE']; } // multiple pages? $pages = (int) $data['LISTLOOKUPRESPONSE'][0]['LISTS'][0]['LIST'][0] ['TOTALPAGES'][0]['VALUE']; // return items $result = array_merge($result, (array) $data['LISTLOOKUPRESPONSE'][0]['LISTS'][0]['LIST'][0]['LISTITEM']); } } return array($result,$params); } /** * Create output */ function render($mode, Doku_Renderer $renderer, $data) { if($mode != 'xhtml') return false; if(is_array($data)){ foreach($data[0] as $item){ $renderer->doc .= $this->_format($item,$data[1]); } }else{ $renderer->doc .= '
failed to fetch data: '.hsc($data).'