Обновление остатков товара
        Хотелось бы поднять вопрос обновления остатков товара после оформления заказа.
Точнее, в момент совершения заказа на n-ое количество товара остаток должен уменьшиться на n заказанных штук.
Возможно, плохо гуглил, но информация какая-то разрозненная и нужно собрать по крупицам в кучу.
В общем, благодаря этому комменту написал такой плагин:
Вопрос 1: Как чистить кэш только для этого ресурса, а не для всего сайта?
Пробовал так:
===========
Изначально я пробовал обновлять значения available через процессоры. Однако так и не удалось победить «permission denied» при обновлении ресурса с фронтенда. Делал по аналогии:
Вопрос 2: как победить этот permission denied, поскольку хочется сделать через процессоры?
С правами пользователей помудрил — ничего не вышло.
    
    
                                                                                
            Точнее, в момент совершения заказа на n-ое количество товара остаток должен уменьшиться на n заказанных штук.
Возможно, плохо гуглил, но информация какая-то разрозненная и нужно собрать по крупицам в кучу.
В общем, благодаря этому комменту написал такой плагин:
<?php
switch ($modx->event->name) {
case 'msOnCreateOrder':
		$prs = $msOrder->getMany('Products');
		// так получаем объекты товаров в заказе
		foreach ($prs as $pr) { //повторяем для каждого товара в заказе
			$data['id'] = $pr->get('product_id'); //определяем id ресурса в заказе
			
			$q = $modx->newQuery('msProduct');
	    	$q->select('Data.available'); //выборка по available, где available - остаток на складе, из которого нужно вычитать количество товара в заказе
	    	$q->innerJoin('msProductData', 'Data', 'msProduct.id = Data.id');
	    	$q->where(array('id' => $data['id'])); //при условии,что id ресурса равен id товара в заказе
	        $q->prepare();
	    
	        if($q->stmt && $q->stmt->execute()){
		        $result = $q->stmt->fetchAll(PDO::FETCH_ASSOC);
		        $data['available'] = ($result[0]['available'] - $pr->get('count')); //определяем остаток товара путём вычитания из текущего остатка товара кол-во товара в заказе $pr->get('count')
			
				$resource = $modx->getObject('msProduct',array('id'=>$data['id'])); //получаем ресурс по его id
				$resource->set('available',$data['available']); //устанавливаем новое значение для поля available
				if ($resource->save()) {
					$modx->cacheManager->clearCache(); //если сохранение успешно, то чистим кэш
			    }
			}
		}
break;
}Такая конструкция работает, но есть пара вопросов.Вопрос 1: Как чистить кэш только для этого ресурса, а не для всего сайта?
Пробовал так:
.............up по коду
	$resource = $modx->getObject('msProduct',array('id'=>$data['id'])); //получаем ресурс по его id
	$resource->set('available',$data['available']); //устанавливаем новое значение для поля available
	if ($resource->save()) {
		$cache = $modx->cacheManager->getCacheProvider($modx->getOption('cache_resource_key', null, 'resource'));
		$key = 'web/resources/' . $data['id']; //пробовал и mgr/
		$cache->delete($key, array('deleteTop' => true));
		$cache->delete($key);
	}
.............down по кодуно не работает.===========
Изначально я пробовал обновлять значения available через процессоры. Однако так и не удалось победить «permission denied» при обновлении ресурса с фронтенда. Делал по аналогии:
<?php
switch ($modx->event->name) {
case 'msOnCreateOrder':
		$prs = $msOrder->getMany('Products');
		// так получаем объекты товаров в заказе
		foreach ($prs as $pr) { //повторяем для каждого товара в заказе
    		$data['id'] = $pr->get('product_id'); //определяем id ресурса в заказе
    		
    		$q = $modx->newQuery('msProduct');
        	$q->select(array('alias','Data.available')); //выборка по alias и available, где available - остаток на складе, из которого нужно вычитать количество товара в заказе; без alias или pagetitle runProcessor не работает
        	$q->innerJoin('msProductData', 'Data', 'msProduct.id = Data.id');
        	$q->where(array('id' => $data['id'])); //при условии,что id ресурса равен id товара в заказе
            $q->prepare();
        
            if($q->stmt && $q->stmt->execute()){
                $result = $q->stmt->fetchAll(PDO::FETCH_ASSOC);
                $data['available'] = ($result[0]['available'] - $pr->get('count')); //определяем остаток товара путём вычитания из текущего остатка товара кол-во товара в заказе $pr->get('count')
                $data['context_key'] = 'web';
                $data['alias'] = $result[0]['alias']; //определяем псевдоним ресурса
                $response = $modx->runProcessor('resource/update', $data); //передаём весь массив параметров $data на обработку процессору resource/update
                if ($response->isError()) { //на случай ошибок печатаем их в лог
        		  $modx->log(modX::LOG_LEVEL_ERROR, "Error on update: \n". print_r($response->getAllErrors(), 1));
                }
            }
        }
break;
}Данный плагин отрабатывает, если мы авторизованы. Если покупку делает аноним, то, как водится, «permission denied». Вопрос 2: как победить этот permission denied, поскольку хочется сделать через процессоры?
С правами пользователей помудрил — ничего не вышло.
Комментарии: 3
                Up!            
                    
                Попробуйте дать анонимусам права context для web.
Если Вы используете процессоры для апдейта, то у кэш будет автоматически обновляться.
                    Если Вы используете процессоры для апдейта, то у кэш будет автоматически обновляться.
                Победили ли вы как нибудь permission denied?            
                    
                            Авторизуйтесь или зарегистрируйтесь, чтобы оставлять комментарии.