Роман Воропаев (Volk)

Роман Воропаев (Volk)

Был в сети 06 ноября 2019, 08:28
Заказы принимаю
Василий Наумкин
Василий Наумкин
$pdo = $modx->getService('pdoFetch');
$result = $pdo->getArray(
	// Класс
	'msProduct',
	// Условие where
	array(
		'deleted' => false,
		'published' => true,
	),
	// Параметры выборки
	array(
		'parents' => 5, // Категория с товарами
		'innerJoin' => array(
			'Data' => array('class' => 'msProductData')
		),
		'select' => array('Data' => 'price'),
		'sortby' => 'Data.price',
		'sortdir' => 'asc',
	)
);
if (!empty($result)) {
	echo $result['price'];
}
// При желании можно лог посмотреть
echo '<pre>';
print_r($modx->getPlaceholder('pdoTools.log'));
Fi1osof
Fi1osof
Ставите Console.
Выполняете код:
ini_set('max_execution_time', 0);
ignore_user_abort(true);
$c = 'modResource';
$q = $modx->newQuery($c);
$q->sortby('id');
$q->select(array(
	"{$c}.*",
));
$s = $q->prepare();
$s->execute();
while($row = $s->fetch(2))
	$response = $modx->runProcessor('resource/update', $row);
	if($response->isError()){
		print_r($response->getResponse());
		return;
	}
	$modx->error->reset();
}
Так как у вас документов много, советую сначала прогнать только корневые документы (добавить в запрос $q->where(array('parent' => 0));), а потом по каждому разделу в отдельности, указывая соответствующий parent.
Алексей Ерохин
Алексей Ерохин
github.com/bezumkin/miniShop2/blob/186b18504214f0afde06343d9e9036c3505cf6a1/assets/components/minishop2/js/web/default.js#L128

Здесь делаете проверку, какое действие происходит.
Например так
var skip = 0;
for (var i=0; i < data.length; i++) {
     if (data[i].name == 'ms2_action' && data[i].value == 'cart/add') {
          skip = 1;
     }
}
if (!skip) {
    miniShop2.Message.success(response.message);
}
Володя
Володя
Приведу небольшой пример на пакете — Office, может кому пригодится…
Допустим хотим ограничить доступ пользователей по email. Пускать только разрешенные email.
1. создаем свое событие для плагина
<?php
$Event = $modx->newObject('modEvent');
$Event->set('name', 'OnOfficeBeforeLogin');
$Event->set('service',1); 
$Event->set('groupname', 'office');
$Event->save();
проверить создалось ли событие можно так
$test = $modx->getObject('modEvent',array('name'=>'OnOfficeBeforeLogin'));
echo $test->get('groupname');
2. добавляем в action.php
$modx->invokeEvent('OnOfficeBeforeLogin', array(
            '_REQUEST' => $_REQUEST
		));
3. пишем плагин на наше событие
<?php
switch ($modx->event->name) {

	case 'OnOfficeBeforeLogin':
	    if ($_REQUEST['action']='auth/sendlink') {
	    
	    $command = $modx->getOption('office_ms2_command', null, "", true);//системная настройка с email участниками
            $instructor = $modx->getOption('office_ms2_instructor', null, "", true);//системная настройка с email тренерами
        
            $emails = array_merge(explode(',', $command ),explode(',', $instructor ));
  
	    if (!in_array($_REQUEST['email'], $emails)) {
	        //меняем почту на неправильную для выдачи ошибки
            $_REQUEST['email'] = "неправильная";
   
	    }
	    else {
           //если есть доступ то ничего не делаем
           //или делаем чтото еще)))
	    }

	    }
	    break;
}
Andrey Grachov
Andrey Grachov
Василий Наумкин
Василий Наумкин
Рано радуешься, нужно же еще форму вынести в чанк.

Указываем параметр с именем чанка:
<div id="connect_table">
	[[!resource?tpl=`myForm`]]
</div>

Прописываем обработку чанка в сниппете:
if ($_SERVER['REQUEST_METHOD'] == 'POST') {
    extract($_POST);
}
$count = $count1 + $count2 + $count3;

return $modx->getChunk($tpl, array(
	'count' => $count
));

И пишем сам чанк с формой myForm:
<form action="[[~[[*id]]]]" method="post" class="form_db">
	<input type="number" name="count1" value="5" />
	<input type="number" name="count2" value="7" />
	<input type="number" name="count3" value="2" />
	<button type="submit" name="submit">ok</button>
</form>
<p>[[+count]]</p>

Вот, примерно так все в MODX и разделяется.
Перетягин Илья
Перетягин Илья
Блин, спасибо большое, ты реально помог!

Может кому интересно или пригодиться, выложу чудо творение:
Чанк
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.0/jquery.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function(){
    $('.form_db').submit(function(e){
	e.preventDefault();
	var m_method=$(this).attr('method');
	var m_action=$(this).attr('action');
	var m_data=$(this).serialize();
		$.ajax({
			type: m_method,
			url: m_action,
			data: m_data,
			success: function(result){
				$('#connect_table').html(result);
			}
		});
	});
});    
</script>
<div id="connect_table">[[!resource]]</div>
Тут мы вызываем наш сниппет который содержит форму, а script type перехватывает его… в общем получается ajax

Код сниппета
if ($_SERVER['REQUEST_METHOD'] == 'POST') {
    extract($_POST);
}
$count = $count1 + $count2 + $count3;

$output = '<form action="[[~[[*id]]]]" method="post" class="form_db">';
$output .= '<input type="number" name="count1" value="5" />';
$output .= '<input type="number" name="count2" value="7" />';
$output .= '<input type="number" name="count3" value="2" />';
$output .= '<button type="submit" name="submit">ok</button>';
$output .= '</form>';
$output .= "<p>$count</p>";
return $output;

Тут мы имеем три поля и кнопку отправки, так же прием запроса и вычисления суммы этих трех полей.

Еще раз большое спасибо Василий!

Василий Наумкин
Василий Наумкин
Выводить на сайте разные цены можно хотя бы условиями в чанке. Использовать можно не только ТВ, но и поле old_price, а также можно добавить свое собственное, расширением свойств товара.

Главная цель — положить товар в корзину с нужной ценой, этого можно добиться написанием плагина на событие корзины msOnBeforeAddToCart.

Плагин должен проверять авторизацию и получать нужную цену, а затем менять её в объекте product (но не сохранять!).

Пример плагина, меняющего нормальный price на old_price, если юзер авторизован:
if ($modx->event->name == 'msOnBeforeAddToCart' && $modx->user->isAuthenticated()) {
	$old_price = $product->get('old_price');
	if (!empty($old_price)) {
		$product->set('price', $old_price);
	}	
}