예제 #1
0
 /**
  * takes a simple list of item ids and pushes those items to the top of the list
  * starting with the first item id. doesn't need to be every item in the inventory.
  * just the ones you want sorted to the top of the list.
  * makes sense from an api standpoint but may not be perfect from an app standpoint.
  */
 public function sort(array $item_ids)
 {
     if (count($item_ids) < 1) {
         return FALSE;
     }
     rsort($item_ids);
     $user_id = $this->user();
     $pos = $this->maxPos();
     $min = $this->minCustomPos();
     if (bccomp($pos, $min) < 0) {
         $pos = $min;
     }
     if ($this->cacher) {
         $timeout = $this->cacheTimeout();
         foreach ($item_ids as $item_id) {
             $pos = bcadd($pos, 1);
             $this->cacher->set($item_id, $pos, 0, $timeout);
             if ($this->inTran()) {
                 Transaction::onRollback(array($this->cacher, 'delete'), array($item_id));
             }
         }
     }
     try {
         $this->storage('sorter')->sort($pos, $item_ids);
     } catch (Exception $e) {
         throw $this->handle($e);
     }
     return TRUE;
 }
예제 #2
0
 protected function create($table)
 {
     $cache = \Gaia\Souk\Storage::cacher();
     $key = 'souk/storage/__create/' . md5($this->dsn . '/' . get_class($this) . '/' . $table);
     if ($cache->get($key)) {
         return;
     }
     if (!$cache->add($key, 1, 60)) {
         return;
     }
     $rs = $rs = $this->execute("SELECT `name` FROM `sqlite_master` WHERE `type` = 'table' and `name` = %s", $table);
     $row = $rs->fetch();
     $rs->free();
     if (!$row) {
         Transaction::onRollback(array($cache, 'delete'), array($key));
         $rs = $this->execute("CREATE TABLE IF NOT EXISTS {$table} (\n              `row_id` INTEGER PRIMARY KEY AUTOINCREMENT,\n              `seller` BIGINT NOT NULL,\n              `buyer` BIGINT NOT NULL DEFAULT '0',\n              `item_id` INTEGER NOT NULL DEFAULT '0',\n              `quantity` BIGINT NOT NULL DEFAULT '0',\n              `price` BIGINT default '0',\n              `pricesort` BIGINT default '0',\n              `step` BIGINT default '0',\n              `bid` BIGINT default '0',\n              `proxybid` BIGINT default '0',\n              `bidcount` INTEGER default '0',\n              `bidder` BIGINT default '0',\n              `reserve` BIGINT default NULL,\n              `closed` INTEGER NOT NULL DEFAULT '0',\n              `created` INTEGER,\n              `expires` INTEGER,\n              `touch` INTEGER\n            )");
         foreach (array('closed', 'created', 'expires', 'pricesort', 'item_id', 'step', 'seller', 'bidder', 'buyer') as $idx) {
             $idx_name = $table . '_idx_' . $idx;
             $this->execute("CREATE INDEX IF NOT EXISTS `{$idx_name}` ON `{$table}` (`{$idx}`)");
         }
     }
     $table_attr = $table . '_attr';
     $rs = $this->execute("SELECT `name` FROM `sqlite_master` WHERE `type` = 'table' and `name` = %s", $table_attr);
     $row = $rs->fetch();
     $rs->free();
     if (!$row) {
         Transaction::onRollback(array($cache, 'delete'), array($key));
         $this->execute("CREATE TABLE IF NOT EXISTS {$table_attr} (\n              `row_id` INTEGER NOT NULL,\n              `attributes` TEXT,\n              PRIMARY KEY  (`row_id`)\n            )");
     }
 }
 /**
  * @see Stockpile_Interface::add();
  * on insert, set the pos column of the sort table to match current time.
  * on dupe key violation, update the pos column to match current time
  */
 public function add($item_id, $quantity = 1, array $data = NULL)
 {
     $res = $this->core->add($item_id, $quantity, $data);
     try {
         $this->storage('sorter')->sort(Base::time(), array($item_id));
     } catch (Exception $e) {
         throw $this->handle($e);
     }
     if ($this->cacher) {
         $this->cacher->set($item_id, $now, $this->cacheTimeout());
         Transaction::onRollback(array($this->cacher, 'delete'), array($item_id));
     }
     return $res;
 }
예제 #4
0
 public function store($id, $name, $strict = FALSE)
 {
     Transaction::onRollback(array($this, 'clearCache'), array($id, $name));
     $namecheck = $this->cacher('id')->get($id);
     $idcheck = $this->cacher('name')->get($name);
     $res = parent::store($id, $name, $strict);
     $this->cacher('id')->set($id, $name, $this->ttl);
     $this->cacher('name')->set($name, $id, $this->ttl);
     if ($namecheck != $name && $namecheck !== null) {
         $this->cacher('name')->delete($namecheck);
     }
     if ($id != $idcheck && $idcheck !== null) {
         $this->cacher('id')->delete($idcheck);
     }
     return $res;
 }
 /**
  * @see Stockpile_Interface::add();
  * only bump up to the top the first time we add this item id to the inventory.
  * after that, just let it slide.
  */
 public function add($item_id, $quantity = 1, array $data = NULL)
 {
     $res = $this->core->add($item_id, $quantity, $data);
     $now = Base::time();
     try {
         $ct = $this->storage('sorter')->sort($now, array($item_id), $ignore = TRUE);
     } catch (\Exception $e) {
         throw $this->handle($e);
     }
     if ($ct < 1 || !$this->cacher) {
         return $res;
     }
     $this->cacher->set($item_id, $now, 0, $this->cacheTimeout());
     if ($this->inTran()) {
         Transaction::onRollback(array($cache, 'delete'), array($item_id));
     }
     return $res;
 }
예제 #6
0
 /**
  * Write the item_id => total quantity pairing into the cache.
  * @param int        item id
  * @param int        total count, after db write
  * if the total is less than zero, write it in as undefined in the cache so it doesn't hit the 
  * db again. With tally, the total is a number, but the serial total will be a quantity object.
  * no matter. we can get it's total value easily enough by just getting strval of it.
  * if there is a transaction attached, set up a callback to delete this key if the transaction doesn't work.
  * can't delete the cache key for history since variations are endless, but we can bust the key
  * using last touch. if we aren't in a transaction, just bust last touch right away.
  * check the id index so we can update it in the cache.
  * if nothing left of a given item, remove it from the index.
  * if the item id is in the index, no more work needed.
  * make sure the index is sorted the way it is supposed to be.
  * always sorted in numeric order of item id.
  */
 protected function writeToCache($item_id, $total)
 {
     $cache = $this->cacher;
     $timeout = $this->cacheTimeout();
     $cache->set($item_id, Base::quantify($total) > 0 ? $total : Store\Callback::UNDEF, $timeout);
     if ($this->inTran()) {
         Transaction::onRollback(array($cache, 'delete'), array($item_id));
         Transaction::onRollback(array($this, 'lastTouch'), array(TRUE));
         Transaction::onCommit(array($this, 'lastTouch'), array(TRUE));
     } else {
         $this->lastTouch(TRUE);
     }
     $index = $cache->get(self::INDEX_CACHEKEY);
     if (!is_array($index)) {
         return;
     }
     if (Base::quantify($total) > 0) {
         if (in_array($item_id, $index)) {
             return;
         }
         $index[] = $item_id;
         sort($index, SORT_NUMERIC);
     } else {
         $found = array_keys($index, $item_id);
         if (count($found) < 1) {
             return;
         }
         foreach ($found as $k) {
             unset($index[$k]);
         }
     }
     $cache->set(self::INDEX_CACHEKEY, $index, $timeout);
 }
예제 #7
0
 /**
  * write the record into the cache.
  */
 protected function writeToCache(Listing $listing)
 {
     $cache = $this->cache();
     $timeout = $this->cacheTimeout();
     $cache->set($listing->id, $listing, 0, $timeout);
     if (!Transaction::atStart()) {
         Transaction::onRollback(array($cache, 'delete'), array($listing->id));
     }
     $this->updateListingSearchVectors($listing);
     return $listing;
 }