function testUpdate_withDescriptor()
 {
     $creditCard = Braintree_SubscriptionTestHelper::createCreditCard();
     $plan = Braintree_SubscriptionTestHelper::triallessPlan();
     $subscription = Braintree_Subscription::create(array('paymentMethodToken' => $creditCard->token, 'planId' => $plan['id'], 'descriptor' => array('name' => '123*123456789012345678', 'phone' => '3334445555')))->subscription;
     $result = Braintree_Subscription::update($subscription->id, array('descriptor' => array('name' => '999*9999999', 'phone' => '8887776666')));
     $updatedSubscription = $result->subscription;
     $this->assertEquals('999*9999999', $updatedSubscription->descriptor->name);
     $this->assertEquals('8887776666', $updatedSubscription->descriptor->phone);
 }
 function testUpdate_canReplaceEntireSetOfAddonsAndDiscounts()
 {
     $oldCreditCard = Braintree_SubscriptionTestHelper::createCreditCard();
     $plan = Braintree_SubscriptionTestHelper::addOnDiscountPlan();
     $subscription = Braintree_Subscription::create(array('paymentMethodToken' => $oldCreditCard->token, 'price' => '54.99', 'planId' => $plan['id']))->subscription;
     $result = Braintree_Subscription::update($subscription->id, array('addOns' => array('add' => array(array('inheritedFromId' => 'increase_30'), array('inheritedFromId' => 'increase_20'))), 'discounts' => array('add' => array(array('inheritedFromId' => 'discount_15'))), 'options' => array('replaceAllAddOnsAndDiscounts' => true)));
     $this->assertTrue($result->success);
     $subscription = $result->subscription;
     $this->assertEquals(2, sizeof($subscription->addOns));
     $addOns = $subscription->addOns;
     Braintree_SubscriptionTestHelper::sortModificationsById($addOns);
     $this->assertEquals($addOns[0]->id, "increase_20");
     $this->assertEquals($addOns[1]->id, "increase_30");
     $this->assertEquals(1, sizeof($subscription->discounts));
     $discounts = $subscription->discounts;
     $this->assertEquals($discounts[0]->id, "discount_15");
 }
 public function checkout()
 {
     $this->layout = 'profile_new';
     if (!$this->request->is('post')) {
         throw new NotFoundException(__d('billing', 'Incorrect request type'));
     }
     $customer = Braintree_Customer::find('konstruktor-' . $this->currUser['User']['id']);
     if (isset($this->request->data['payment_method_nonce'])) {
         $nonceFromTheClient = $this->request->data['payment_method_nonce'];
         $payment = Braintree_PaymentMethod::create(['customerId' => 'konstruktor-' . $this->currUser['User']['id'], 'paymentMethodNonce' => $nonceFromTheClient]);
         if (!$payment->success) {
             $this->Session->setFlash($payment->message);
             $this->redirect(array('action' => 'payment'));
         }
         $payment = $payment->paymentMethod;
     } elseif (isset($this->request->data['payment_method']) && !empty($this->request->data['payment_method'])) {
         $payment = null;
         foreach ($customer->paymentMethods as $payment) {
             if ($payment->token == $this->request->data['payment_method']) {
                 break;
             }
         }
         if (empty($payment)) {
             throw new NotFoundException(__d('billing', 'Payment method not found'));
         }
     } else {
         throw new NotFoundException(__d('billing', 'Unable to create subscription'));
     }
     $braintreePlanId = $this->Session->read('Billing.plan');
     $plan = $this->BillingPlan->findByRemotePlan($braintreePlanId);
     $braintreePlans = Braintree_Plan::all();
     $braintreePlan = null;
     foreach ($braintreePlans as $_braintreePlan) {
         if ($_braintreePlan->id == $braintreePlanId) {
             $braintreePlan = $_braintreePlan;
             break;
         }
     }
     if (empty($braintreePlan)) {
         throw new NotFoundException(__d('billing', 'Unable to create subscription'));
     }
     //Important! unit setup for model must be here. Before creating Braintree subscription
     $unit = Configure::read('Billing.units.' . $plan['BillingGroup']['limit_units']);
     if (empty($unit['model']) || empty($unit['field'])) {
         throw new NotFoundException(__d('billing', 'Invalid billing plan'));
     }
     $this->BillingSubscription->Behaviors->load('Billing.Limitable', array('remoteModel' => $unit['model'], 'remoteField' => $unit['field'], 'scope' => isset($unit['scope']) ? $unit['scope'] : 'user_id'));
     //Precreate subscription
     $braintreeData = array('paymentMethodToken' => $payment->token, 'planId' => $braintreePlanId);
     $qty = $this->Session->read('Billing.qty');
     if (!empty($qty)) {
         if (empty($braintreePlan->addOns)) {
             throw new NotFoundException(__d('billing', 'Unable to create subscription'));
         }
         foreach ($braintreePlan->addOns as $addOn) {
             $braintreeData['addOns']['update'][] = array('existingId' => $addOn->id, 'quantity' => $qty);
         }
     }
     $billingSubscription = $this->BillingSubscription->find('first', array('conditions' => array('BillingSubscription.group_id' => $plan['BillingGroup']['id'], 'BillingSubscription.user_id' => $this->currUser['User']['id'], 'BillingSubscription.active' => true)));
     //braintree unable to update subscription to a plan with a different billing frequency So we need to cancel current
     if (!empty($billingSubscription)) {
         if ($braintreePlan->billingFrequency != $billingSubscription['BraintreePlan']->billingFrequency || $billingSubscription['BraintreeSubscription']->status == 'Canceled' || $billingSubscription['BraintreeSubscription']->status == 'Expired') {
             if ($braintreePlan->billingFrequency != $billingSubscription['BraintreePlan']->billingFrequency || $billingSubscription['BraintreeSubscription']->status != 'Canceled') {
                 try {
                     $result = Braintree_Subscription::cancel($billingSubscription['BraintreeSubscription']->id);
                     if ($result->success) {
                         $billingSubscription['BraintreeSubscription'] = $result->subscription;
                     }
                 } catch (Exception $e) {
                 }
             }
             $status = isset($billingSubscription['BraintreeSubscription']->status) ? $billingSubscription['BraintreeSubscription']->status : 'Canceled';
             $this->BillingSubscription->cancel($billingSubscription['BillingSubscription']['id'], $status);
             $billingSubscription = null;
         }
     }
     if (!isset($billingSubscription['BillingSubscription'])) {
         $data = array('group_id' => $plan['BillingGroup']['id'], 'plan_id' => $plan['BillingPlan']['id'], 'user_id' => $this->currUser['User']['id'], 'limit_value' => !empty($qty) ? $qty : $plan['BillingPlan']['limit_value'], 'active' => false);
     } else {
         $data = $billingSubscription['BillingSubscription'];
         $data['limit_value'] = !empty($qty) ? $qty : $plan['BillingPlan']['limit_value'];
     }
     //No Exceptions anymore!
     if (!isset($data['remote_subscription_id']) || empty($data['remote_subscription_id'])) {
         //Subscribe user by create
         $result = Braintree_Subscription::create($braintreeData);
     } else {
         $data['plan_id'] = $plan['BillingPlan']['id'];
         //Subscribe user by update
         $result = Braintree_Subscription::update($data['remote_subscription_id'], $braintreeData);
     }
     if (!$result->success) {
         $this->Session->setFlash(__d('billing', 'Unable to subscribe on chosen plan. Please contact with resorce administration'));
         $this->redirect(array('action' => 'plans', $plan['BillingGroup']['slug']));
     }
     $data = Hash::merge($data, array('remote_subscription_id' => $result->subscription->id, 'remote_plan_id' => $result->subscription->planId, 'active' => $result->subscription->status === 'Active' ? true : false, 'status' => $result->subscription->status, 'expires' => $result->subscription->billingPeriodEndDate->format('Y-m-d H:i:s'), 'created' => $result->subscription->createdAt->format('Y-m-d H:i:s'), 'modified' => $result->subscription->updatedAt->format('Y-m-d H:i:s')));
     if (!isset($data['id'])) {
         $this->BillingSubscription->create();
     }
     if ($this->BillingSubscription->save($data)) {
         $this->Session->write('Billing');
         if (!isset($data['id']) || empty($data['id'])) {
             $data['id'] = $this->BillingSubscription->getInsertID();
         }
         $this->redirect(array('action' => 'success', $data['id']));
     } else {
         $this->Session->setFlash(__d('billing', 'Unable to subscribe on chosen plan. Please contact with resorce administration'));
         $this->redirect(array('action' => 'plans', $plan['BillingGroup']['slug']));
     }
 }
 /**
  * @param $subscriptionId
  * @param $data
  *
  * @return array
  */
 public function updateSubscription($subscriptionId, $data)
 {
     $result = \Braintree_Subscription::update($subscriptionId, $data);
     if ($result->success) {
         return $this->response(true);
     } else {
         return $this->response(false);
     }
 }