По просьбам трудящихся выкладываю решение "Накопительные скидки для Ubercart 2".
При разработке магазина часто возникает необходимость делать скидки для покупателей. С единоразовыми скидками и купонами проблем обычно не возникает, но что делать если Вам нужны накопительные скидки?
Обсудив эту проблему со своим коллегой, покопавшись на форуме и приложив немного усилий нами было найдено вполне рабочее и удобное решение. Оно основано на присваивании определенной роли, пользователю, который оплатил покупку в нашем магазине.
Итак:
- Скачиваем модули Ubercart Discounts (Alternative) (для установки модуля вам так же понадобятся: Ubercart, date_popup, CCK), Rules и Uc rules.
- Устанавливаем их
- Идем в раздел Управление пользователями > Роли (/admin/user/roles) и создаем там 3 роли. Например , 10%, 15%, 20%. Сохраняем.
- Идем в настройки модуля Ubercart Discounts (Alternative), Управление магазином > Скидки > Добавить скидку(/admin/store/uc_discounts/add). Добавляем скидку 10% (переводы строк могут отличатся):
- Имя > 10%
- Короткое описание > 10%
- Описание > 10%
- Активна > Ставим галку
- Может быть объединена с другими скидками > Не ставим галку
- Скидка начнет действовать с > Не ставим галку
- Скидка истекает > Не ставим галку
- Вес 0
- Квалификационный тип > Минимальная цена
- Минимальное квалификационное значение > 1 (!)Обратите внимание, это очень важный пункт
- Из трех следующих чек-боксов выбираем третий, квалиФикация по роли > Ставим галку
- В ролях выбираем скидку 10%
- Фильтр Required products не трогаем
- Тип скидки > Процент от
- Значение > 0.1 (тут скидка указывается в десятых долях, т.е. если Вам нужна скидка 5% указываете цифру 0.05 и т.д.)
- Фильтр продуктов оставляем в положении "Все продукты", если хотите скидку на весь ассортимент, если нужно на отдельные продукты, то выбираем их из списка.
- Остальные пункты оставляем как есть
- Сохраняем
Со скидками 15% и 20% проделываем туже самую процедуру.
- Идем в раздел Правила > Срабаты- ваемые правила > Добавить - правило (/admin/rules/trigger/add)
- Метка > sale 10
- Событие > Выбираем из списк- а > ubercart rules > order checkout complete(заказ завершен)
- Данное правило активно и выполняется при возникновении ассоциированного события > Ставим галку > Жмем продолжить
Описание правила:
- ПРИ срабатывании события Order checkout complete > Выполнение php кода
- Все поля оставляем без изменений, в поле PHP кода пишем такой код
- Жмем сохранить
- ВЫПОЛНИТЬ > Добавить действие
- Из списка выбираем User > add user role (Добавить роль пользователю) > Жмем далее
- Выбираем нашу роль 10% > Жмем сохранить
- Добавляем еще одно действие > remove user role (Удалить роль пользователя) > Жмем сохранить
- Выбираем все оставшиеся "скидочные" роли (15% и 20%) > Жмем сохранить
<?php
global $user;
$user_id = $user->uid; $result = db_query("SELECT sum(order_total) FROM `uc_orders` where uid =".$user_id); $total = array();
while($value = db_fetch_array($result)) {
$total = $value;
}foreach(
$total as $value){
if ($value >= 10000 and $value < 15000){ /*вот тут задаем суммы при которых будет срабатывать наша скидка, если сумма больше или равна 10 000 и меньше или равна 15 000 то пользователь получит роль 10% на для которой создана скидка 10%, для 15%-скидки, уже указываете диапазон от 15 001 до 20 000 и так далее.*/
return 1; // А вот эта единица то как раз и запустит нашу скидку, созданную в модуле скидок.
};
}
?>После пункта "ПРИ срабатывании события Order checkout complete" будет пункт:
Для скидок 15% и 20% проделываем все те же действия, не забывая менять суммы скидок в PHP коде.
Вот тут уже интереснее.
Комментарии
Спасибо!
Очень нужно было! Спасибо огромнейшее и респект!
Делал такое с тем же набором модулей, но чуть по другому. Тоже несколько ролей.
Скидка выдается в зависимости от тотальной суммы.
Скидка 5% сумма 5000руб
Скидка 10% сумма 10000руб
Скидка 15% сумма 30000руб
Создал скидки
Сама скидка
В Rules создал запланированные правила
Для скидки в 5%
1)
2)
3)
В случае со скидкой 15% нудно удалить роли 5% и 10% у пользователя
PHP код такой
return $total_sum > 5000 && $total_sum <= 100000;
Но есть еще клиент со скидкой 15%. Ему уже двигаться некуда. (Хотя возможно создать правило "если сумма покупки больше 1 000 000 000, клиент становится владельцем магазина")
Для него правило такое:
Код такой:
return $total_sum > 300000;
А действия для него нет.
Код брал из модуля Order Total Discount http://drupal.org/project/uc_discount_total
А еще можно поставить модуль
price ranges field, и создать им поле в котором отображено, какая именно цена для пользователя со скидкой
Работа над ошибками.
Попробовал метод jchoo. Пожил не много со своим методом и хочу сказать что нашел одну особенность.
Если делать все как описано выше пользователь получит скидку после того как сделает заказ.
Т.е. пользователь:
1) делает заказ на приличную сумму
2) сообщает админу что ему это не надо
3) через неделю делает заказ на мелкую сумму, но уже являясь обладателем скидки. А за что ему скидка то?
Скидку пользователь должен получать, не после того как делает заказ, а после того как админ подтверждает заказ.
Что нужно:
Использовать в правиле (Rules) событие Order state is updated - per order line (наверное)
Условие 1. Filter order by status. Status: Complited (Завершено)
Условие 2. Выполнение PHP кода.
В коде сделать выборку из БД. "Если сумма заказов пользователя и имеющих статус Завершено больше и меньше определнного числа."
Действие 1. Load customer by order (User)
Действие 2. Изменить роль пользователя (как на скринах выше)
Буду рад если кто-то правильно напишет Условие 2. На это моих скилов не хватает.
1. У пользователя могут быть оформленные, но не оплаченные заказы, либо заказы, по которым произошли возвраты - их суммы будут учитываться в общей сумме покупок пользователя.
2. Бывает (у меня был такой случай), что заказчик хочет, чтобы общая сумма покупок считалась по товарам в оплаченных заказах, исключая стоимость доставок и прочих доп.услуг - тоже не реализовано.
За желание делиться опытом - спасибо.
UPD.
откопал и приаттачил свой модуль, которым делал накопительные скидки
Думаю считать по order total не совсем корректно, если есть Ubercart discount alt. При его наличии скидка (которая может быть) не попадает в переменную order total.
если не ошибаюсь, скидка пишется в line item, т.е. её можно также вычитать из общей суммы, как и доставку, у меня просто не было такой задачи.
на самом деле, я против расчета общей суммы покупок за вычетом скидок, доставок и т.п., поэтому у себя в модуле делал выбор - учитывать стоимость доставки или нет
попробую объяснить на пальцах:
допустим, я сделал в магазине 3 покупки: на 1, 2 и 3 тыс.руб
правильнее сказать - я заплатил магазину 1+2+3 = 6000р. и расчитываю на накопительную скидку, которая начинается, например, от 5000р.
но продавец мне говорит: эээ нет, всё не так, первый раз ты оформил заказ на 1000р, в котором доставка составляла 300р, а стоимость товаров - 700р.
во второй - была доставка 300р. и ещё один товар был по акции, его стоимость не учитывается при расчете общей суммы покупок, и и в третий раз - то же что-то в таком роде, и получается, что общая сумма покупок - 4700р, накопительной скидки пока не будет
пусть даже все эти правила были указаны в магазине - я всё равно пошлю его подальше, ну его нафиг с таким матаном
т.е. мое мнение - чем проще и понятнее покупателю, тем лучше.
накопительную скидку стоит считать от общей суммы заказа - именно её покупатель помнит и может проверить без логарифмической линейки,
уж лучше сделать повыше пороги, при которых предоставляется очередная скидка
Хорошо скидки можно не учитывать при рассчете общей суммы заказов.
Написал такое условие в Rules
<?php
$uload = $user_loaded -> uid;
$total = "SELECT sum(order_total) AS total FROM {drushop_uc_orders} WHERE
uid = ".$uload."
AND
order_status = '".completed."'";
return $total > 100000 && $total <= 200000;
?>
Не работает, выдает:
user warning: Table 'name_of_user.uc_orders' doesn't exist query: SELECT sum(order_total) FROM `uc_orders` where uid =1 in ...modules/rules/rules/modules/php.rules.inc(88) : eval()'d code on line 5.
Что это за: Table 'name_of_user.uc_orders'
норм идея, возьму на заметку
Скидку пользователь должен получать, не после того как делает заказ, а после того как админ подтверждает заказ.
чем решился вопрос?
Забили!
/*Добавлено*/ dimonx, спасибо за участие! На днях попробую.
В Rules добавил событие -User page has been viewed-
Выполнить PHP
<?php
$order_id = db_result(db_query("SELECT order_id FROM {uc_orders} WHERE order_status = 'completed' AND uid = $user->uid"));
$user_status = db_result(db_query("SELECT rid FROM {users_roles} WHERE uid = $user->uid"));
if ($user_status==9 && $order_id <> 0) {
db_query("UPDATE {users_roles} SET rid = 10 WHERE uid = $user->uid");
}
?>
Зарегистрированный пользователь имеет статус Покупателя. После оплаты заказа и подтверждения админом (Статус - Завершено), войдя на страницу своего аккаунта его роль становится Постоянный покупатель.
по аналогии делаются остальные статусы, необходимы только свои условия.
например есть статус Оптовик. суммирую оплату всех завершенных заказов определенного пользователя = и присваиваю новую роль...
ps. значение rid - не забываем менять на свои... афигенско работает ))
dimonx, если честно, не совсем ясно. Может где-то и прогнал. Можешь свои скрины дать.
Делал так
php код в условии:
<?php
$total_sum = db_result(db_query("SELECT COALESCE(SUM(price * qty), 0) AS total FROM {uc_order_products} ucpr LEFT JOIN {uc_orders} uc ON ucpr.order_id = uc.order_id LEFT JOIN {uc_order_statuses} ucs ON uc.order_status = ucs.order_status_id WHERE uid = %d AND state NOT IN('%s', '%s')", $user->uid, 'canceled', 'in_checkout'));
return $total_sum > 5000 && $total_sum <= 100000;
?>
В действии ставил как у тебя.
А в Arguments configuration нужно брать User: acting user или viewed user?
в моем случае IF - пустой
я кодом проверяю
Для ВИПа (общая сумма покупок => 10000) все тоже самое
код
<?php
$countrows
= db_result(db_query("SELECT SUM(order_total) FROM {uc_orders} WHERE uid = $user->uid AND order_status = 'completed'"));$user_status = db_result(db_query("SELECT rid FROM {users_roles} WHERE uid = $user->uid"));
if ($countrows >= 10000 && $user_status >= 9 && $user_status <=10) {
db_query("UPDATE {users_roles} SET rid = 11 WHERE uid = $user->uid");
}
?>
выбирается сумма всех ЗАВЕРШЕННЫХ заказов пользователя
проверяется что юзер имеет статус ПОСТОЯННОГО покупателя и имеет сумму ЗАВЕРШЕННЫХ >= 10000
обновляется роль
(!) ЕСЛИ (IF) - во всех случаях - пустое (!)
Ууууу.
rid = 11 - это номер роли пользователя отсюда admin/user/roles/edit/11
А $user_status==9 это что?
У меня их 2 активен и блокирован. Они где-то выставляются?
rid FROM {users_roles}
rid - столбец в таблице users_roles
в нем прописаны все роли которые созданы на сайте, каждой роли соответствует свой rid.
Хорошо, допустим я хочу т.обр. добавить зарегистрированному пользователю роль Пользователь со скидкой 5%
В таблице users_roles у меня минимальный rid=3, в то время как в талице role для authenticated user значение rid = 2
напиши в аську помогу 7551557
role для authenticated user это вообще не учитывается
если юзер есть в таблице users_roles, то конечно он authenticated user
какое необходимо условие на назначение Пользователь со скидкой 5% ???
какой rid Пользователь со скидкой 5% ???
Условие: сумма всех покупок больше 5000 и меньше 100000.
Пользователь со скидкой 5% имеет rid = 8
$countrows = db_result(db_query("SELECT SUM(order_total) FROM {uc_orders} WHERE uid = $user->uid AND order_status = 'completed'"));
$user_status = db_result(db_query("SELECT rid FROM {users_roles} WHERE uid = $user->uid"));
$user_statuss = $user_status + 1;
if ($user_statuss==1 && $countrows >= 5000) {
db_query("INSERT INTO {users_roles} (uid, rid) VALUES ($user->uid, 8)");
}
======================================
Если пользователь только зарегистрировался и не имеет никаких ролей то его нет в таблице users_roles.
Этот код проверяет: сумму всех заказов пользователя -> проверяет имеет ли он какие-то роли -> если ролей нет, а сумма завершенных больше 5000 = делаем вставку в таблицу users_roles.
Важно! Отработка кода произойдет только на странице пользовательского аккаунта.
Ограничение < 100000 - тут не нужно. Его необходимо вставлять в следующую роль (Пользователь со скидкой 10%).
Не работает почему-то.
Сделал правило.
Зарегистрированный юзер делает заказ, админ выставляет статус заказа как "Завершено", но юзер не переходит в следующую роль.
Важно! Отработка кода произойдет только на странице пользовательского аккаунта.
войди под юзером на страницу аккаунта
Да, действительно. Пользователь переходит на свою страничку и после этого у него меняется роль.
А зечем это?
А можно чтобы роль менялась без перехода юзера на свою страничку? Админ выставляет заказ завершенным и если сумма всех заказов юзера больше 100000, то юзер повышается в звании.
Добрый день, поднимаю вопрос, так как не нашел не чего на просторах интернета, мне нужная такая же фишка но на ubercart 3 и drupal 7 суть в том что! не могу понять рулес так как он стал в 7 не много другой! с ним не разу не работал! и в этом случае не могу сделать 5 пункт (из-за rules) может кто делал или кто подскажет это решение?