Hello and great work on the module. I am trying to give all 1st time buyes on my site a coupon code that they can use just once. On setting up the coupons, i realised that setting it to once means that once any user has used that coupon, then no other user can use rendering it invalid.

DOes anyone know how to set this up? Thanks

Comments

Category:support» feature

Currently there's an action that gets the coupons by order commerce_coupon_action_get_coupons_for_order but not by user. We probably need to add an action for restricting that per user and order.

You can see an example of redemption limited by order here #1538158: Limit number of coupons applied to the order.

Did you happen to get a solution for this at all?

I am also looking for something exactly like this. I am surprised that this already does not exist.

Giving discount to first time user has sort of become a market standard to attract new users.

I'm also very interested. However thank you very much for this contribution.

I got the solution working, though not through Commerce Coupon module.

Had to use combination of Flag module and a custom line item with negative value.

Check it out if anybody wants to: http://www.getdandy.com

Let me know if anyone is looking for the solution.

Thank you for sharing. However to me this looks way to complicated.

Thanks uditmahajan. I still have not found a solution to this. The way you have done it seems to be the only solution out there. Please can you write down your steps used in making it work?

What user?
Sounds to me like you guys are in trouble, or am i missing something

commerce has the rule "Assign an anonymous order to a pre-existing user" this allows a user to complete an order without login in to the site and the order is still assigned to him through his email address on completion.
this event happens after both the "Validate a coupon" and "Redeem a coupon" events.

A Possible solution would be to:
1) If the user is not logged in, load the user from his email
2) cycle the user's orders and check if the coupon was used (see #1)

You may be able to do all this with rules but i suspect custom code will be needed.

@#7 guy_schneerson

Not only "what user," but what user who hasn't created a new account with a multitude of free Google email accounts. You would have to accept the credit card information and THEN confirm the name, account, etc and try to check for a previously used coupon. And this would only be efficient if you were running your own payment gateway of PP Pro and were collecting the information yourself. Then you check the account prior to running the credit card. Since a lot of people use Paypal standard, the customer information is there and you would have to get the Paypal info back, hold off on completing the order until you check the coupon, then if they've already used a coupon, decline/refund their order. What a mess that would be.

I too would like to limit a coupon but it doesn't seem realistic from a module standpoint. You would have to code for sites running their own gateway and there are far too many APIs to even consider that. Plus, then all the people on PP standard wouldn't have it working.

So the only realistic way I can even think is running your own gateway (like through your bank or PP Pro) and then custom your own module to work with that API to check coupons before processing the payment. That way, you can alert the user and make them confirm the higher total without the coupon if they are ineligible.

Other than that I would bet you're out of luck. I could be wrong, that's just my own brain and it's not perfect.

How about the checkout login?

http://drupal.org/project/commerce_checkout_login

In this case the system recognize an all ready existing account and a message would say like:

This account all ready exists and you can't use the "first buyer coupon" please login and check your cart again.

After login a rule would withdraw the coupon amount.

@#9

Again, how are you going to prevent users from setting up free web email accounts and registering for your site? I'm not saying there is NO solution, but so far I haven't seen anyone present one for this very important aspect of single coupons.

I hear you.

But we can`t prevent people doing this.

@mysoftmusic

Sure you can. You would have to process the CC details prior to actually processing the order. Create a custom module that will check the name on the CC with your order tables and you should be able to get the vast majority of people trying to use fake emails. There will still be some exceptions and you'd have to send the data directly to the payment gateway and back to that step if it's invalidated at the gateway, but it's possible to get the majority of all cases like this.

It's not up to you to know how i'll manage fake orders (btw more orders = more sell, that could be a win).

I need to create a single coupon code, redeemable once for user.
Is there a way to do this?

@reysharks

It may not be up to me to to know how you'll manage fake orders but it is important to consider the community as a whole, many of which who will have no idea how to manage fake orders. We can't just implement something that could potentially cause grief for the community at large.

I understand your position, but i think that adding that solution like an option could not be a trouble.

Btw i did it via rules.

I added a bool field on coupon content type, "use once for user".
Then I added a entity field on user "used coupons" obviously coupon type, unlimited values, list, hidden.

Then I added a rule for every coupon redeemed to add the coupon to the "used coupon" list of the cart owner.
Then I added a rule that validate coupons looking IF the coupon has the field "use once for user" AND check if the coupon is on the "used coupons" list AND check if the coupon field "use once for user" is not null, THEN set invalid and show a message.

I hope this can be usefull, tested a little, seems to work but more testing is required.

Let me know.

+1 for rules and theoretically I don't see any problems with the way you've done it. That looks like a good solution. Believe me, I agree that the majority of the time we do too much hand-holding but I think even an option would add too much overhead for the module maintainers. Despite it being an option, people would still use it, then come in and complain because it "wasn't working" and people were gaming the system.

But I think your solution is the way we should handle it for those who have a plan to combat the duplicate coupons with new accounts or for people who don't care. Like you said, more sales might be a good thing. For someone who has taken a loss on an item in an effort to upsell that might not be a great plan.

On a sidenote, I was here originally looking to solve another problem that wasn't coupon once per user but your last post made a solution click and I think I've got it. I could even use parts of your solution to add some things I didn't even think about.

I've found a bug in my method, if I use a coupon on an order, but I don't finish the order himself but I go back to shopping cart, when I remove the commerce line item the coupon is not given back to the user, I don't find a way to catch this event and give back the coupon to the user (I mean remove the coupon from the USED COUPONS field of the user).

Any help is appreciated..

I've solved creating an action for this purpose.

/**
* Implements hook_rules_action_info().
*/
function YOURMODULE_rules_action_info() {
  $actions = array();
  $actions['YOURMODULE_action_restore_coupons_to_user'] = array(
    'label' => t('Restore coupons to user'),
    'parameter' => array(
      'commerce_order' => array(
        'type' => 'commerce_order',
        'label' => t('Commerce Order'),
      ),
    ),
    'group' => t('Commerce Coupon'),
  );
  return $actions;
}
/**
* Action to give back a coupon to a user
*/
function YOURMODULE_action_restore_coupons_to_user($order) {
  if (empty($order)) {
    return array();
  }
  $account = user_load($order->uid);
  $order_wrapper = entity_metadata_wrapper('commerce_order', $order);
  $coupons = $order_wrapper->commerce_coupon_order_reference->value();
  foreach ($coupons as $coupon) {
    YOURMODULE_remove_coupon_from_user($coupon,$account);
  }
}
function YOURMODULE_remove_coupon_from_user($coupon, $account){
$coupons_to_remove = array();
        //field_cust_used_coupons is the USER field containing the used coupons
foreach($account->field_cust_used_coupons[LANGUAGE_NONE] as $key => $value){
if($value["target_id"] == $coupon->coupon_id){
$coupons_to_remove[] = $key;
}
}
foreach($coupons_to_remove as $coupon_to_remove){
unset($account->field_cust_used_coupons[LANGUAGE_NONE][$coupon_to_remove]);
}
field_attach_update('user', $account);
}

The i call this action on a rule of this type:

EVENT: After removing a product from the cart
CONDITIONS: Total product quantity comparison (Parameter: Order: [commerce_order], Operator: =, Quantity: 0)
ACTION: Restore coupons to user (Parameter: Commerce Order: [commerce_order]) //The action we just created.

Hi !

I needed to this functionnality, I have searched how, and I found !
So I have created a little module (only in sandbox for now), so try this and create issues in this project if you find something to update.

Commerce Coupon - Per user redemption

The sandbox module in #20 works like a charm straight out-of-the-box.

Thank you , rkcreation .

Why not make that one a contrib module ?

Status:Active» Needs review

I can also confirm that the sandbox module by @rkcreation in #20 works great. +1 to make it a contrib module.

I can also confirm that the sandbox works

Do you guys know if this works with the 2.x branch?

Just tried it. Does not work for 2.x