Created
December 20, 2015 14:53
-
-
Save iamcsharper/1d4dd46ee8ab56e68adf to your computer and use it in GitHub Desktop.
This will let you parse all the items from Steam inventory very fast!
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
abstract class BaseCollection | |
{ | |
/** | |
* rgDescriptions array | |
* @var array | |
*/ | |
protected $items = []; | |
/** | |
* Each element is implementing ItemCollectionFilter! | |
* @see ItemCollectionFilter | |
* @var array | |
*/ | |
protected $filters = []; | |
/** | |
* @var ICollectionParser | |
*/ | |
protected $collectionParser; | |
/** | |
* @param array $items | |
*/ | |
public function __construct(array $items) | |
{ | |
$this->items = $items; | |
} | |
public function getUniqueKey() | |
{ | |
return md5(json_encode($this->items) . json_encode($this->filters)); | |
} | |
/** | |
* Returns {@link Item} array | |
* @see Item | |
* @return array | |
*/ | |
public function get() | |
{ | |
return $this->collectionParser->parseCollection($this); | |
} | |
/** | |
* Returns first row | |
* @return mixed | |
*/ | |
public function first() | |
{ | |
$this->filters[] = new SliceCollectionFilter(0, 1); | |
return $this->get()[0]; | |
} | |
public function add($value) | |
{ | |
$this->items[] = $value; | |
} | |
public function getFilters() | |
{ | |
return $this->filters; | |
} | |
// Bad code | |
public function __call($name, $arguments) | |
{ | |
if (strpos($name, 'findBy') !== false) { | |
$string = strtolower(str_replace('findBy', '', $name)); | |
foreach ($this->items as $item) { | |
if ($item[$string] == $arguments[0]) { | |
return $this->collectionParser->parseItem($item); | |
} | |
} | |
} | |
} | |
public function toArray() | |
{ | |
return array_values($this->items); | |
} | |
public function toJSON() | |
{ | |
return json_encode($this->toArray(), JSON_PRETTY_PRINT); | |
} | |
public function isEmpty() | |
{ | |
return !$this->size(); | |
} | |
public function size() | |
{ | |
return count($this->items); | |
} | |
public function getItems() | |
{ | |
return $this->items; | |
} | |
public function setItems(array $items) | |
{ | |
$this->items = $items; | |
} | |
public function removeAt($i) | |
{ | |
$index = 0; | |
foreach ($this->items as $k => $v) { | |
// Numeric or associative | |
if ($index == $i || $k == $i) { | |
unset($this->items[$k]); | |
break; | |
} | |
++$index; | |
} | |
} | |
public function removeAtMany(array $ids) | |
{ | |
$index = 0; | |
foreach ($this->items as $k => $v) { | |
// Numeric or associative | |
if (in_array($index, $ids) || in_array($k, $ids)) { | |
unset($this->items[$k]); | |
} | |
++$index; | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
interface BaseCollectionFilter { | |
/** | |
* @param BaseCollection $collection | |
* @return array | |
*/ | |
public function execute(BaseCollection &$collection); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
trait CollectionMethods { | |
public function slice($a, $b) | |
{ | |
$this->filters[] = new SliceCollectionFilter($a, $b); | |
return $this; | |
} | |
/** | |
* @param \Closure $closure | |
* @return $this | |
*/ | |
public function where(\Closure $closure) | |
{ | |
$this->filters[] = new WhereCollectionFilter($closure); | |
return $this; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class DotaItem extends Item | |
{ | |
// Always is static for Dota items | |
public static $contextId = 2; | |
protected $appId = 570; | |
protected static $dotaRaritiesEnum = [ | |
'common', | |
'uncommon', | |
'rare', | |
'mythical', | |
'legendary', | |
'immortal', | |
'arcana', | |
'ancient' | |
]; | |
private static $dotaTypesEnum = [ | |
'Wearable', | |
'HUD Skin', | |
'Loading Screen', | |
'Announcer', | |
'Courier', | |
'Tool', | |
'Taunt', | |
'Gem / Rune', | |
'Bundle' | |
]; | |
private static $dotaQualitiesEnum = [ | |
'Infused', | |
'Normal', | |
'Auspicious', | |
'Inscribed', | |
'Heroic', | |
'Genuine', | |
'Cursed', | |
'Frozen', | |
'Unusual', | |
'Elder', | |
'Corrupted', | |
'Autographed', | |
'Exalted', | |
'Legacy', | |
'Ascendant', | |
'Favored', | |
]; | |
private static $_heroes = []; | |
public static function getHeroes() | |
{ | |
// Get from steam, change these | |
if (empty(self::$_heroes)) { | |
$api = new APIBridge(config('steam-auth.api_key')); | |
$json = $api->callApi('IEconDOTA2_570/', 'GetHeroes/v0001/', [ | |
'language' => 'russian' | |
]); | |
$result = json_decode($json, true); | |
$heroes = $result['result']['heroes']; | |
self::$_heroes = $heroes; | |
} | |
return self::$_heroes; | |
} | |
private $rarity; | |
private $quality; | |
public function __construct(array $data) | |
{ | |
parent::__construct($data); | |
foreach ($this->tags as $tag) { | |
if (strtolower($tag['category']) == 'rarity') { | |
$this->rarity = strtolower($tag['name']); | |
} elseif (strtolower($tag['category']) == 'hero') { | |
$this->characters[] = $tag['name']; | |
} elseif (strtolower($tag['category']) == 'quality') { | |
$this->quality = $tag['name']; | |
} | |
} | |
} | |
public function getRarity() | |
{ | |
return $this->rarity; | |
} | |
public function getHero() | |
{ | |
return $this->characters[0]; | |
} | |
private function getRarityOrder() | |
{ | |
return self::$dotaRaritiesEnum[$this->getRarity()]; | |
} | |
private static function checkBeforeSort($a, $b) | |
{ | |
$badType = false; | |
if (!($a instanceof DotaItem)) | |
$badType = gettype($a); | |
if (!($b instanceof DotaItem)) | |
$badType = gettype($b); | |
if ($badType) | |
throw new \RuntimeException('Incompatible types. Excepted: ' . self::class . '. Got: ' . $badType); | |
} | |
/** | |
* @param $a DotaItem | |
* @param $b DotaItem | |
* @return int | |
*/ | |
public static function sortByQuality($a, $b) | |
{ | |
static::checkBeforeSort($a, $b); | |
$al = (!isset(self::$dotaQualitiesEnum[$a->getQuality()])) ? 0 : self::$dotaQualitiesEnum[$a->getHero()]; | |
$bl = (!isset(self::$dotaQualitiesEnum[$b->getQuality()])) ? 0 : self::$dotaQualitiesEnum[$b->getHero()]; | |
if ($al == $bl) | |
return 0; | |
return ($al > $bl) ? -1 : 1; | |
} | |
/** | |
* @param $a DotaItem | |
* @param $b DotaItem | |
* @return int | |
*/ | |
public static function sortByType($a, $b) | |
{ | |
static::checkBeforeSort($a, $b); | |
$al = self::$dotaTypesEnum[$a->getType()]; | |
$bl = self::$dotaTypesEnum[$b->getType()]; | |
if ($al == $bl) { | |
return 0; | |
} | |
return ($al > $bl) ? -1 : 1; | |
} | |
/** | |
* @param $a DotaItem | |
* @param $b DotaItem | |
* @return int | |
*/ | |
public static function sortByCharacter($a, $b) | |
{ | |
static::checkBeforeSort($a, $b); | |
$al = $bl = 0; | |
foreach (self::getHeroes() as $hero) { | |
if ($hero['localized_name'] == $a->getHero()) | |
$al = true; | |
elseif ($hero['localized_name'] == $b->getHero()) | |
$bl = true; | |
} | |
if (!$al) { | |
return 1; | |
} | |
if (!$bl) { | |
return -1; | |
} | |
return strnatcmp($a->getHero(), $b->getHero()); | |
} | |
/** | |
* @param $a DotaItem | |
* @param $b DotaItem | |
* @return int | |
*/ | |
public static function sortByPrice($a, $b) | |
{ | |
static::checkBeforeSort($a, $b); | |
$al = $a->getPrice(); | |
$al = ($al) ? $al->getSitePrice() : 0; | |
$bl = $b->getPrice(); | |
$bl = ($bl) ? $bl->getSitePrice() : 0; | |
if ($al == $bl) { | |
return 0; | |
} | |
return ($al > $bl) ? -1 : 1; | |
} | |
/** | |
* @param $a DotaItem | |
* @param $b DotaItem | |
* @return int | |
*/ | |
public static function sortByRarity($a, $b) | |
{ | |
static::checkBeforeSort($a, $b); | |
$al = $a->getRarityOrder(); | |
$bl = $b->getRarityOrder(); | |
if ($al == $bl) { | |
return 0; | |
} | |
return ($al > $bl) ? -1 : 1; | |
} | |
/** | |
* @return mixed | |
*/ | |
public function getQuality() | |
{ | |
return $this->quality; | |
} | |
/** | |
* @param mixed $quality | |
*/ | |
public function setQuality($quality) | |
{ | |
$this->quality = $quality; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
interface ICollectionParser | |
{ | |
public function parseCollection(BaseCollection &$collection); | |
public function parseItem($item); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
abstract class Item | |
{ | |
public static $contextId; | |
/** | |
* Item name | |
* @var string | |
*/ | |
protected $name; | |
/** | |
* #Color of the item | |
* @var string | |
*/ | |
protected $nameColor; | |
/** | |
* Item's market name | |
* @var string | |
*/ | |
protected $marketName; | |
/** | |
* id of the application, which item is added to | |
* @var integer | |
*/ | |
protected $appId; | |
/** | |
* Item class id | |
* @var integer | |
*/ | |
protected $classId; | |
/** | |
* Item instance id | |
* @var integer | |
*/ | |
protected $instanceId; | |
/** | |
* Hash for url linked to to item's image | |
* @see http://cdn.steamcommunity.com/economy/image/ | |
* @var string | |
*/ | |
protected $iconUrl; | |
/** | |
* Hash for url linked to to item's bigimage | |
* @see http://cdn.steamcommunity.com/economy/image/ | |
* @var string | |
*/ | |
protected $iconUrlLarge; | |
/** | |
* Item type | |
* @var string | |
*/ | |
protected $type; | |
/** | |
* Can we trade with it? | |
* @var boolean | |
*/ | |
protected $tradable; | |
/** | |
* Can we sell this item on market? | |
* @var boolean | |
*/ | |
protected $marketable; | |
/** | |
* Item's descriptions | |
* @var array | |
*/ | |
protected $descriptions = []; | |
/** | |
* Item's tags | |
* @var array | |
*/ | |
protected $tags = []; | |
/** | |
* Characters who can use this item | |
* @var array | |
*/ | |
protected $characters = []; | |
/** | |
* Calculated in ItemPrice | |
* @see ItemCollection | |
* @var ItemPrice | |
*/ | |
protected $price; | |
public function __construct(array $data) | |
{ | |
$this->appId = $data['appid']; | |
$this->classId = $data['classid']; | |
$this->instanceId = $data['instanceid']; | |
$this->iconUrl = $data['icon_url']; | |
$this->iconUrlLarge = $data['icon_url_large']; | |
$this->name = $data['name']; | |
$this->marketName = $data['market_hash_name']; | |
$this->nameColor = $data['name_color']; | |
$this->tradable = $data['tradable']; | |
$this->marketable = $data['marketable']; | |
if (is_array($data['descriptions'])) { | |
foreach ($data['descriptions'] as $description) { | |
if (preg_replace('/\s+/', '', $description['value']) == '') | |
continue; | |
$this->descriptions[] = $description['value']; | |
} | |
} | |
if (is_array($data['tags'])) | |
$this->tags = $data['tags']; | |
foreach ($this->tags as $tag) { | |
if (strtolower($tag['category_name']) == 'type') { | |
$this->type = $tag['name']; | |
} | |
} | |
if ($data['type'] != '') | |
$this->type = $data['type']; | |
} | |
/** | |
* @return string | |
*/ | |
public function getName() | |
{ | |
return $this->name; | |
} | |
/** | |
* @param string $name | |
*/ | |
public function setName($name) | |
{ | |
$this->name = $name; | |
} | |
/** | |
* @return string | |
*/ | |
public function getNameColor() | |
{ | |
return $this->nameColor; | |
} | |
/** | |
* @param string $nameColor | |
*/ | |
public function setNameColor($nameColor) | |
{ | |
$this->nameColor = $nameColor; | |
} | |
/** | |
* @return string | |
*/ | |
public function getMarketName() | |
{ | |
return $this->marketName; | |
} | |
/** | |
* @return int | |
*/ | |
public function getAppId() | |
{ | |
return $this->appId; | |
} | |
/** | |
* @return int | |
*/ | |
public function getClassId() | |
{ | |
return $this->classId; | |
} | |
/** | |
* @return int | |
*/ | |
public function getInstanceId() | |
{ | |
return $this->instanceId; | |
} | |
/** | |
* @return string | |
*/ | |
public function getIconUrl() | |
{ | |
return $this->iconUrl; | |
} | |
/** | |
* @return string | |
*/ | |
public function getIconUrlLarge() | |
{ | |
return $this->iconUrlLarge; | |
} | |
/** | |
* @return string | |
*/ | |
public function getType() | |
{ | |
return $this->type; | |
} | |
/** | |
* @return boolean | |
*/ | |
public function isTradable() | |
{ | |
return $this->tradable; | |
} | |
/** | |
* @return boolean | |
*/ | |
public function isMarketable() | |
{ | |
return $this->marketable; | |
} | |
/** | |
* @return array | |
*/ | |
public function getDescriptions() | |
{ | |
return $this->descriptions; | |
} | |
/** | |
* @return array | |
*/ | |
public function getTags() | |
{ | |
return $this->tags; | |
} | |
/** | |
* Link to a transparent png image of item | |
* @return string | |
*/ | |
public function getClearUrl() | |
{ | |
return 'https://steamcommunity-a.akamaihd.net/economy/image/class/' . $this->appId . '/' . $this->classId . '/'; | |
} | |
/** | |
* @return ItemPrice | |
*/ | |
public function getPrice() | |
{ | |
return $this->price; | |
} | |
/** | |
* @param ItemPrice $price | |
*/ | |
public function setPrice(ItemPrice $price) | |
{ | |
$this->price = $price; | |
} | |
public function getSitePrice() { | |
if (is_null($this->price)) | |
return 0; | |
return $this->price->getSitePrice(); | |
} | |
abstract public function getRarity(); | |
/* | |
* Just to let children override all these methods | |
*/ | |
static public function sortByRarity($rarityA, $rarityB) | |
{ | |
return 0; | |
} | |
static public function sortByQuality($a, $b) | |
{ | |
return 0; | |
} | |
static public function sortByType($typeA, $typeB) | |
{ | |
return 0; | |
} | |
static public function sortByCharacter($characterA, $characterB) | |
{ | |
return 0; | |
} | |
static public function sortByPrice($priceA, $priceB) | |
{ | |
return 0; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* That's it! | |
**/ | |
class ItemCollection extends BaseCollection | |
{ | |
use CollectionMethods; | |
static $searches = []; | |
public function __construct(array $items, ItemMarketPriceHelper $marketPriceHelper) { | |
parent::__construct($items); | |
$this->collectionParser = new ItemCollectionParser($marketPriceHelper); | |
} | |
public function __call($name, $arguments) | |
{ | |
if (strpos($name, 'findBy') !== false) { | |
$string = strtolower(str_replace('findBy', '', $name)); | |
if (!empty(self::$searches[$string])) | |
return self::$searches[$string]; | |
foreach ($this->items as $item) { | |
if ($item[$string] == $arguments[0]) { | |
$parsed = $this->collectionParser->parseItem($item); | |
self::$searches[$string] = $parsed; | |
return $parsed; | |
} | |
} | |
} | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class ItemCollectionParser implements ICollectionParser | |
{ | |
private static $collectionCache; | |
private static $itemCache; | |
/** | |
* @var ItemMarketPriceHelper | |
*/ | |
protected $priceHelper; | |
public function __construct(ItemMarketPriceHelper $marketPriceHelper) | |
{ | |
$this->priceHelper = $marketPriceHelper; | |
} | |
public function parseCollection(BaseCollection &$collection) | |
{ | |
$key = $collection->getUniqueKey(); | |
if (isset(self::$collectionCache[$key]) && !empty(self::$collectionCache[$key])) | |
return self::$collectionCache[$key]; | |
if ($collection->isEmpty()) | |
return []; | |
/** @var BaseCollectionFilter $filter */ | |
foreach ($collection->getFilters() as $filter) { | |
$filter->execute($collection); | |
} | |
$result = []; | |
foreach ($collection->toArray() as $itemInfo) { | |
$item = $this->parseItem($itemInfo); | |
$result[] = $item; | |
} | |
self::$collectionCache[$key] = $result; | |
return $result; | |
} | |
/** | |
* @param $itemInfo | |
* @return Item | |
*/ | |
public function parseItem($itemInfo) | |
{ | |
if (empty($itemInfo) || !is_array($itemInfo)) | |
throw new \InvalidArgumentException('ItemInfo should be filled array!'); | |
$key = md5(json_encode($itemInfo)); | |
if (isset(self::$itemCache[$key]) && !empty(self::$itemCache[$key])) | |
return self::$itemCache[$key]; | |
/** @var Item $item */ | |
$item = ItemStorage::createItem($itemInfo); | |
if ($itemInfo['tradable'] !== '0') { | |
try { | |
/** @var $price ItemPrice */ | |
$price = $this->priceHelper->getItemPrice($item); | |
$item->setPrice($price); | |
} catch (\Exception $e) { | |
\Log::debug($e->getMessage()); | |
} | |
} | |
return $item; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace App\Helpers\Steam; | |
use App\Helpers\Steam\Items\Item; | |
use App\Models\ItemPrice; | |
use Cache; | |
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException; | |
class ItemMarketPriceHelper | |
{ | |
// protected $communityURL = 'http://anonymouse.org/cgi-bin/anon-www.cgi/http://steamcommunity.com/'; | |
protected $communityURL = 'http://steamcommunity.com/'; | |
protected $apiKey; | |
/** | |
* @var int | |
*/ | |
protected $currency; | |
/** | |
* @param $apiKey | |
* @param int $currency | |
*/ | |
public function __construct($apiKey, $currency = 5) | |
{ | |
$this->apiKey = $apiKey; | |
$this->currency = $currency; | |
} | |
protected function cleanFloat($str) | |
{ | |
$float = (float)str_replace(',', '.', preg_replace('/[\s]*/', '', $str)); | |
return $float; | |
} | |
protected function cleanInt($str) | |
{ | |
return (int)str_replace(',', '.', preg_replace('/[\s]*/', '', $str)); | |
} | |
public function setCurrency($currency) | |
{ | |
$this->currency = $currency; | |
} | |
/** | |
* @param $item Item | |
* @return ItemPrice | |
*/ | |
public function getItemPrice($item) | |
{ | |
$params = [ | |
'currency' => $this->currency, | |
'appid' => $item->getAppId(), | |
'market_hash_name' => $item->getMarketName() | |
]; | |
$query = http_build_query($params); | |
$price = ItemPrice:: | |
where('class_id', $item->getClassId()) | |
->where('app_id', $item->getAppId()) | |
->first(); | |
if (!$price) { | |
$url = $this->communityURL . 'market/priceoverview/?' . $query; | |
$contents = @file_get_contents($url); | |
$result = json_decode($contents, true); | |
if (!$result['success']) { | |
throw new NotFoundHttpException('Стим считает нас дудосерами по ссылке ' . $url); | |
} | |
$lowest = (isset($result['lowest_price'])) ? $this->cleanFloat($result['lowest_price']) : 0; | |
$median = (isset($result['median_price'])) ? $this->cleanFloat($result['median_price']) : 0; | |
$volume = (isset($result['volume'])) ? $this->cleanInt($result['volume']) : 0; | |
$cached = [ | |
'class_id' => $item->getClassId(), | |
'app_id' => $item->getAppId(), | |
'min' => $lowest, | |
'median' => $median, | |
'volume' => $volume, | |
]; | |
$price = ItemPrice::create($cached); | |
} | |
return $price; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class ItemStorage | |
{ | |
private static $relations = [ | |
'570' => DotaItem::class, | |
]; | |
public static function getItemClass($appId) | |
{ | |
$appId = $appId . ''; | |
if (!isset(self::$relations[$appId])) { | |
throw new \InvalidArgumentException('Theres no item for id: ' . $appId); | |
} | |
return self::$relations[$appId]; | |
} | |
public static function getItemContextID($appId) | |
{ | |
$className = self::getItemClass($appId); | |
$prop = 'contextId'; | |
if (!property_exists($className, $prop)) | |
throw new \RuntimeException('Item called ' . $className . ' hasnt ContextID! Fix it!'); | |
$vars = get_class_vars($className); | |
return $vars[$prop]; | |
} | |
/** | |
* @param $itemInfo | |
* @return mixed | |
*/ | |
public static function createItem($itemInfo) | |
{ | |
$item = self::getItemClass($itemInfo['appid']); | |
/* @var $item Item */ | |
return new $item($itemInfo); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class SliceCollectionFilter implements BaseCollectionFilter | |
{ | |
/** | |
* @var int | |
*/ | |
private $from; | |
/** | |
* @var int | |
*/ | |
private $to; | |
/** | |
* SliceCollectionFilter constructor. | |
* @param int $from | |
* @param int $to | |
*/ | |
public function __construct($from, $to) | |
{ | |
$this->from = max(0, $from); | |
$this->to = (int)$to; | |
} | |
public function execute(BaseCollection &$collection) | |
{ | |
$items = $collection->toArray(); | |
$bad = []; | |
foreach ($items as $i => $v) { | |
if ($i < $this->from || $i >= $this->to) { | |
$bad[] = $i; | |
} | |
} | |
$collection->removeAtMany($bad); | |
} | |
public function __toString() | |
{ | |
return 'Slice'; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
class WhereCollectionFilter implements BaseCollectionFilter | |
{ | |
/** | |
* @var \Closure | |
*/ | |
private $closure; | |
/** | |
* WhereCollectionFilter constructor. | |
* @param \Closure $closure | |
*/ | |
public function __construct(\Closure &$closure) | |
{ | |
$this->closure = &$closure; | |
} | |
public function execute(BaseCollection &$collection) | |
{ | |
$bad = []; | |
/* @var $closure \Closure */ | |
$closure = $this->closure; | |
$items = $collection->toArray(); | |
foreach ($items as $i => $v) { | |
if (!$closure($v)) { | |
$bad[] = $i; | |
} | |
} | |
$collection->removeAtMany($bad); | |
} | |
public function __toString() | |
{ | |
return 'Where'; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Will be waiting for advices and fixed!)))