Антон Фомичёв

Антон Фомичёв

Был в сети 12 марта 2026, 08:08
Заказы не принимаю
Таким образом можно получить свойство $user->Profile->email, даже если именно в этот момент еще не был получен связанный объект modProfile для этого пользователя.
Вот за эту наводку — отдельное огромное спасибо! Во мне вскипает очередная волна влюблённости в modx:))
В итоге проблема решилась, на мой взгляд, изящнее, чем расширение класса modUser.

С версии 5.3 в php появились замыкания, а с версии 5.4 к ним добавили два метода: bind и bindTo. Подробнее о теории можно почитать
тут.

Эти методы позваляют связать ваше замыкание с конкретным объектом, после чего замыканию становится доступен $this. То есть, фактически, мы можем добавить на лету произвольный метод классу и он будет выполняться в контексте класса.

В рассмотренном мной в заметке случае делается так:
$user = $modx->user;
$method = function($name, $value)
	{
		$this->_setRaw($name, $value);
		return $this->save();
	}

$method = $method->bindTo($user, 'modUser');
$method('password', '12345');
Вуа-ля! Защищенный метод нам доступен из любого класса, поскольку выполняется как будто изнутри класса modUser.
3. Перегрузка методов xPDOCacheManager. Но это уже дебри дремучие, с которыми придётся воевать с каждой новой версией modx.
Так не надо изменять их прямо в файле MODX. Напиши свою реализацию кэширования, какой-нибудь modMultipleCache, расширяющий xPDOCacheManager. Там опиши все, что тебе необходимо (собственно, и изменять поведение методов родительского класса никто не запрещал). В настройках системы укажи свой класс как отвечающий за кэширование и воевать ни с чем не придётся.
Вижу два варианта.

Первый:
1. У каждой из форм есть атрибут id, а так же тэг
<input type="hidden" name="formid" value="[[+значение атрибута id]]">
2. Сниппет должен вместе с основным ответом возвращать значение $_POST['formid'] виде {«formid»:«значение»}.
3. Тогда обработчик события выглядит следующим образом:
$(document).on('af_complete', function(event,res) {
	var form = $("#"+res.formid);
	if(!res.success){
		form.find('[name="' + res.key + '"]').addClass('error');
	}
});
Второй:
1. Через гитхаб или как-то по-другому предложить Василию изменить часть кода default.js таким образом:
$(document).trigger("af_complete", response, form);
2. Если коммит будет принят, то тогда твой скрипт будет выглядеть так:
$(document).on('af_complete', function(event,res,form) {
	var $form = $(form);
	if(!res.success){
		$form.find('[name="' + res.key + '"]').addClass('error');
	}
});
Я бы предложил что-то такое:

$(document).on('af_complete', function(event,res) {
	if(!res.success){
		form.find('[name="' + res.key + '"]').addClass('error');
	}
});
При этом, не забудь определить переменную form (она должна содержать объект jQuery).
Ну и твой сниппет должен отдавать json с полями success и key по меньшей мере.
В конструкции
$(document).on('af_complete', function(res) {
	console.log(res);
});
res предсказуемо содержит объект jquery.event, таргетом которого является $(document).
В соответствии с API jQuery дополнительные параметры передаются обработчику начиная со второго аргумента функции.

То есть так:
$(document).on('af_complete', function(event,res) {
	console.log(res);
});
Было же недавно
А вообще, у меня такое только при запуске кроном через API_MODE. И только при использовании APC.
А у тебя ошибки генерит index.php. Подозреваю, что-то не так с настройками кэширования MODX.

Если используешь APC, то почитай здесь в сообществе статью Василия об этом. Там после изменения класса-обработчика кэша надо еще один параметр добавить, иначе есть вероятность пересечения кэшей разных сайтов, крутящихся на одном сервере. Ну и он должен присутствовать в виде установленного аддона к PHP и быть включенным в php.ini
0.0046291: Created inline chunk
2.0591421: Total time
4 456 448: Memory usage

Ужжжасный компутер клиента, co-location, халявный.
Скока он мне мозга вынес с постоянной нехваткой памяти, дикими тормозами и отваливанием MySQL.
Стараюсь плавно агитировать за переход в нормальное облако. Все же это дешевле нового сервера тыщ за 100-150.
Тебе нужно для обмена с удаленной БД, а не для авторизации — или я неправильно понял?
Не совсем так. Я получаю хэш пароля от удалённой БД и потом использую его для авторизации на сайте. Причины, по которым устроено всё именно так, сложны и многогранны и многими гранями упираются в требования заказчика:))

Есть нормальная работа с юзерами с одной стороны, а есть таблица id — открытый пароль, с другой.
Во-первых, не хотелось бы хранить пароль открытым, во-вторых, работа с юзерами и обмен с БД, как я написал выше, неразделимы. Я получаю хэш и он должен в итоге позволять пользователю авторизоваться во фронт-энде.

По моему, это гораздо красивее, чем вламываться в нутро движка и все там курочить.
Абсолютно согласен, я это сделал только как временное решение, чтобы сайт мог продолжать работать, пока я разбираюсь.