Good Day!
I am currently working on a QUICKBOOKS API payment and is using their DevKit https://github.com/consolibyte/quickbooks-php its working just fine, I can retrieve invoices and pay them individually. Now, I want to create a functionality that can pay multiple invoices in 1 payment. What I could think right now is doing a loop until all selected invoices gets paid individually but I guess its not the correct approach..
this is the code I got from the DevKit
$PaymentService = new QuickBooks_IPP_Service_Payment();
// Create payment object
$Payment = new QuickBooks_IPP_Object_Payment();
$Payment->setPaymentRefNum('WEB123');
$Payment->setTxnDate('2014-02-11');
$Payment->setTotalAmt(10);
// Create line for payment (this details what it's applied to)
$Line = new QuickBooks_IPP_Object_Line();
$Line->setAmount(10);
// The line has a LinkedTxn node which links to the actual invoice
$LinkedTxn = new QuickBooks_IPP_Object_LinkedTxn();
$LinkedTxn->setTxnId('{-84}');
$LinkedTxn->setTxnType('Invoice');
$Line->setLinkedTxn($LinkedTxn);
$Payment->addLine($Line);
$Payment->setCustomerRef('{-67}');
// Send payment to QBO
if ($resp = $PaymentService->add($Context, $realm, $Payment))
{
print('Our new Payment ID is: [' . $resp . ']');
}
else
{
print($PaymentService->lastError());
}
If I put them inside a loop, I am sure they will all get paid and also it will create multiple payments as well.
Is there any other much better ways to do this? please help. Thanks!
Just do this stuff more than one time:
// The line has a LinkedTxn node which links to the actual invoice
$LinkedTxn = new QuickBooks_IPP_Object_LinkedTxn();
$LinkedTxn->setTxnId('{-84}');
$LinkedTxn->setTxnType('Invoice');
$Line->setLinkedTxn($LinkedTxn);
$Payment->addLine($Line);
For example:
foreach ($invoices as $invoice_id)
{
// The line has a LinkedTxn node which links to the actual invoice
$LinkedTxn = new QuickBooks_IPP_Object_LinkedTxn();
$LinkedTxn->setTxnId($invoice_id);
$LinkedTxn->setTxnType('Invoice');
$Line->setLinkedTxn($LinkedTxn);
$Payment->addLine($Line);
}
I made it work with this code
$c = 0;
foreach ($invoice_ids as $i) {
$Line = new QuickBooks_IPP_Object_Line();
$Line->setAmount($i_line_amount[$c]); //amount per line
$LinkedTxn = new QuickBooks_IPP_Object_LinkedTxn();
$LinkedTxn->setTxnId($i);
$LinkedTxn->setTxnType('Invoice');
$Line->setLinkedTxn($LinkedTxn);
$Payment->addLine($Line);
$c++;
}
Related
I have been trying to execute a subscription plan. I have hit a roadblock in the form of the billing agreement. I keep getting the following error when trying to create the agreement.
{"name":"VALIDATION_ERROR","details":[{"field":"plan","issue":"Invalid Fields passed in plan. Pass only a valid plan-id."}],"message":"Invalid request. See details.","information_link":"https://developer.paypal.com/webapps/developer/docs/api/#VALIDATION_ERROR"}
I am unsure where the issue lies, trying to force the agreement's set plan to output the id itself also causes a JSON error and does nothing productive.
If you need more info feel free to ask.
$createdPlan = $startPlan->create($paypal);
$patch = new Patch();
$value = new PayPalModel('{
"state":"ACTIVE"
}');
$patch->setOp('replace')
->setPath('/')
->setValue($value);
$patchRequest = new PatchRequest();
$patchRequest->addPatch($patch);
$createdPlan->update($patchRequest, $paypal);
$plan = Plan::get($createdPlan->getId(), $paypal);
$agreement = new Agreement();
$agreement->setName($product . ' Agreement')
->setDescription('Recurring Payment')
->setStartDate(date(c, time()+4));
$agreement->setPlan($plan);
$payer = new Payer();
$payer->setPaymentMethod('paypal');
$agreement->setPayer($payer);
$agreement->create($paypal);
I was able to fix this by creating a new plan object and only setting the id to the actual plan like so.
$jsonplan = new Plan();
$jsonplan->setId($createdPlan->getId());
$agreement->setPlan($jsonplan);
$createdPlan is the plan variable that you need to pass in the $agreement class
$agreement->setPlan($createdPlan);
Is there a way to remove lines from an invoice using the Consolibyte quickbooks toolkit?
I can send invoices with lines but I would also like to update an invoice and I think the best way would be to remove each line and then send up the lines as they are currently. i.e: To update an invoice I would first get the invoice from quickbooks using the ref I store locally, remove the lines, then update the fields on the invoice object, then add the new lines and then send the invoice using the update method.
I have seen this example:
https://github.com/consolibyte/quickbooks-php/blob/master/docs/partner_platform/example_app_ipp_v3/example_invoice_update.php
But I am unsure how I could update individual lines as I have no reference to them stored locally, hence trying to remove them and then re-create.
Found the answer here:
How to access Quickbooks Invoice Line Items using php api
My solution looks like this, using Laravel:
public function qbUpdateInvoice(Invoice $invoice)
{
if ($invoice->qb_ref == null) {
throw new \Exception('Invoice Quickbooks ref not available.');
}
$qbInvoice = $this->findInvoiceByRef($invoice);
$count = $qbInvoice->countLine();
for ($i = 0; $i < $count; $i++) {
$qbInvoice->unsetLine($i);
}
$qbInvoice = $this->setInvoiceDetails($invoice, $qbInvoice);
$qbInvoice = $this->setInvoiceLines($invoice, $qbInvoice);
$response = $this->qbInvoiceService->update($this->context, $this->realm, $qbInvoice->getId(), $qbInvoice);
if (!$response) {
throw new \Exception($this->qbInvoiceService->lastError());
}
return $response;
}
My problem is that I want to get a bill after paying for storage ( in .pdf) on the server. I've been looking at the API and create an invoice but know not how to get the bill automatically.
<?php
require __DIR__ . '/../bootstrap.php';
use PayPal\Api\Address;
use PayPal\Api\BillingInfo;
use PayPal\Api\Cost;
use PayPal\Api\Currency;
use PayPal\Api\Invoice;
use PayPal\Api\InvoiceAddress;
use PayPal\Api\InvoiceItem;
use PayPal\Api\MerchantInfo;
use PayPal\Api\PaymentTerm;
use PayPal\Api\Phone;
use PayPal\Api\ShippingInfo;
$invoice = new Invoice();
Invoice Info
$invoice
->setMerchantInfo(new MerchantInfo())
->setBillingInfo(array(new BillingInfo()))
->setNote("Medical Invoice 16 Jul, 2013 PST")
->setPaymentTerm(new PaymentTerm())
->setShippingInfo(new ShippingInfo());
Merchant Info
A resource representing merchant information that can be used to identify merchant
$invoice->getMerchantInfo()
->setEmail("jaypatel512-facilitator#hotmail.com")
->setFirstName("Dennis")
->setLastName("Doctor")
->setbusinessName("Medical Professionals, LLC")
->setPhone(new Phone())
->setAddress(new Address());
$invoice->getMerchantInfo()->getPhone()
->setCountryCode("001")
->setNationalNumber("5032141716");
Address Information
The address used for creating the invoice
$invoice->getMerchantInfo()->getAddress()
->setLine1("1234 Main St.")
->setCity("Portland")
->setState("OR")
->setPostalCode("97217")
->setCountryCode("US");
Billing Information
Set the email address for each billing
$billing = $invoice->getBillingInfo();
$billing[0]
->setEmail("example#example.com");
$billing[0]->setBusinessName("Jay Inc")
->setAdditionalInfo("This is the billing Info")
->setAddress(new InvoiceAddress());
$billing[0]->getAddress()
->setLine1("1234 Main St.")
->setCity("Portland")
->setState("OR")
->setPostalCode("97217")
->setCountryCode("US");
Items List
You could provide the list of all items for detailed breakdown of invoice
$items = array();
$items[0] = new InvoiceItem();
$items[0]
->setName("Sutures")
->setQuantity(100)
->setUnitPrice(new Currency());
$items[0]->getUnitPrice()
->setCurrency("USD")
->setValue(5);
Tax Item
You could provide Tax information to each item.
$tax = new \PayPal\Api\Tax();
$tax->setPercent(1)->setName("Local Tax on Sutures");
$items[0]->setTax($tax);
Second Item
$items[1] = new InvoiceItem();
Lets add some discount to this item.
$item1discount = new Cost();
$item1discount->setPercent("3");
$items[1]
->setName("Injection")
->setQuantity(5)
->setDiscount($item1discount)
->setUnitPrice(new Currency());
$items[1]->getUnitPrice()
->setCurrency("USD")
->setValue(5);
Tax Item
You could provide Tax information to each item.
$tax2 = new \PayPal\Api\Tax();
$tax2->setPercent(3)->setName("Local Tax on Injection");
$items[1]->setTax($tax2);
$invoice->setItems($items);
Final Discount
You can add final discount to the invoice as shown below. You could either use "percent" or "value" when providing the discount
$cost = new Cost();
$cost->setPercent("2");
$invoice->setDiscount($cost);
$invoice->getPaymentTerm()
->setTermType("NET_45");
Shipping Information
$invoice->getShippingInfo()
->setFirstName("Sally")
->setLastName("Patient")
->setBusinessName("Not applicable")
->setPhone(new Phone())
->setAddress(new InvoiceAddress());
$invoice->getShippingInfo()->getPhone()
->setCountryCode("001")
->setNationalNumber("5039871234");
$invoice->getShippingInfo()->getAddress()
->setLine1("1234 Main St.")
->setCity("Portland")
->setState("OR")
->setPostalCode("97217")
->setCountryCode("US");
Logo
You can set the logo in the invoice by providing the external URL pointing to a logo
$invoice->setLogoUrl('https://www.paypalobjects.com/webstatic/i/logo/rebrand/ppcom.svg');
For Sample Purposes Only.
$request = clone $invoice;
try {
Create Invoice
Create an invoice by calling the invoice->create() method with a valid ApiContext (See bootstrap.php for more on ApiContext)
$invoice->create($apiContext);
} catch (Exception $ex) {
NOTE: PLEASE DO NOT USE RESULTPRINTER CLASS IN YOUR ORIGINAL CODE. FOR SAMPLE ONLY
ResultPrinter::printError("Create Invoice", "Invoice", null, $request, $ex);
exit(1);
}
NOTE: PLEASE DO NOT USE RESULTPRINTER CLASS IN YOUR ORIGINAL CODE. FOR SAMPLE ONLY
ResultPrinter::printResult("Create Invoice", "Invoice", $invoice->getId(), $request, $invoice);
return $invoice;
if they could orient themselves, or some link which explains how to find it I would be grateful
I'm creating an invoice with multiple lines. Sales tax is set up in QuickBooks for multiple provinces. I've read through https://developer.intuit.com/docs/0025_quickbooksapi/0050_data_services/020_key_concepts/global_tax_model to get an idea of how to properly integrate, but it's very confusing. I have to follow the international instructions because I am in Canada.
What I understand is that each SalesItemLineDetail gets set a TaxCode that I have to query for. How do I query for a specific GST rate? (Currently set up is GST and HST ON)
I also need tax to be exclusive. I could not find where to set this.
Do I need to add a TaxLine, or is that automatically done for me by QuickBooks?
Current snippet of my code looks like this:
// Set the IPP version to v3
$IPP->version(QuickBooks_IPP_IDS::VERSION_3);
$InvoiceService = new QuickBooks_IPP_Service_Invoice();
$Invoice = new QuickBooks_IPP_Object_Invoice();
$Invoice->setDocNumber("DVL-".$invoice_id);
$Invoice->setTxnDate($orderdate);
$Line = new QuickBooks_IPP_Object_Line();
$Line->setDetailType('SalesItemLineDetail');
$Line->setDescription($service['name']);
$Line->setAmount($service['price']);
$orderTotal += $service['price'];
$SalesItemLineDetail = new QuickBooks_IPP_Object_SalesItemLineDetail();
$SalesItemLineDetail->setUnitPrice($service['price']);
$SalesItemLineDetail->setQty(1);
//set sales tax here?
$Line->addSalesItemLineDetail($SalesItemLineDetail);
$Invoice->addLine($Line);
So I figured it out. At least, what I have now works.
$TaxCodeService = new QuickBooks_IPP_Service_TaxCode();
if($property_details['province'] == "ON" || $property_details['province'] == "Ontario"){
$tax_name = "HST ON";
} else {
$tax_name = "GST";
}
$taxcodes = $TaxCodeService->query($Context, $realm, "SELECT * FROM TaxCode WHERE name = '".$tax_name."'");
$this_tax_code = "";
foreach ($taxcodes as $TaxCode)
{
$this_tax_code = $TaxCode->getId();
}
This gives me the ID of the rate that I want, and then when setting the SalesItemLineDetail simply:
$SalesItemLineDetail->setTaxCodeRef($this_tax_code);
Hello im using paypal express checkout with the merchant sdk.
I have implemented recurring payment using the integration manual, but the given example doesnt make an initial payment(charge the user right away).
My code for making the payment is:
Initializing the payment:
$cart = $this->cart->getCart();
$items = $cart['items'];
$itemTotal = 0;
foreach ($items as $k => $item) {
$product = $this->addItem($item);
$itemTotal += $product->Amount;
$this->paymentDetails->PaymentDetailsItem[$k] = $product;
}
$this->orderTotal->currencyID = 'USD';
$this->orderTotal->value = $this->cart->getCartAmount();
$this->paymentDetails->OrderTotal = $this->orderTotal;
$this->paymentDetails->PaymentAction = 'Sale';
$this->paymentDetails->InvoiceID = $invoice_id->{'$id'};
$setECReqDetails = new \PayPal\EBLBaseComponents\SetExpressCheckoutRequestDetailsType();
$setECReqDetails->PaymentDetails[0] = $this->paymentDetails;
$setECReqDetails->CancelURL = $this->cancelURL;
$setECReqDetails->ReturnURL = $this->returnURL;
$billingAgreementDetails = new \PayPal\EBLBaseComponents\BillingAgreementDetailsType('RecurringPayments');
$billingAgreementDetails->BillingAgreementDescription = 'recurringbilling';
$setECReqDetails->BillingAgreementDetails = array($billingAgreementDetails);
$setECReqType = new \PayPal\PayPalAPI\SetExpressCheckoutRequestType();
$setECReqType->Version = $this->version;
$setECReqType->SetExpressCheckoutRequestDetails = $setECReqDetails;
$setECReq = new \PayPal\PayPalAPI\SetExpressCheckoutReq();
$setECReq->SetExpressCheckoutRequest = $setECReqType;
return $this->paypalService->SetExpressCheckout($setECReq);
And then on the return url i supplied i create the recurring payment with this code:
$profileDetails = new \PayPal\EBLBaseComponents\RecurringPaymentsProfileDetailsType();
$profileDetails->BillingStartDate = "2014-01-24T00:00:00:000Z";
$paymentBillingPeriod = new \PayPal\EBLBaseComponents\BillingPeriodDetailsType();
$paymentBillingPeriod->BillingFrequency = 10;
$paymentBillingPeriod->BillingPeriod = "Day";
$paymentBillingPeriod->Amount = new \PayPal\CoreComponentTypes\BasicAmountType("USD", "1.0");
$scheduleDetails = new \PayPal\EBLBaseComponents\ScheduleDetailsType();
$activationDetails = new \PayPal\EBLBaseComponents\ActivationDetailsType();
$activationDetails->InitialAmount = new \PayPal\CoreComponentTypes\BasicAmountType('USD', 49);
$activationDetails->FailedInitialAmountAction = 'ContinueOnFailure';
$scheduleDetails->Description = "recurringbilling";
$scheduleDetails->ActivationDetails = $activationDetails;
$scheduleDetails->PaymentPeriod = $paymentBillingPeriod;
$createRPProfileRequestDetails = new \PayPal\EBLBaseComponents\CreateRecurringPaymentsProfileRequestDetailsType();
$createRPProfileRequestDetails->Token = $token;
$createRPProfileRequestDetails->ScheduleDetails = $scheduleDetails;
$createRPProfileRequestDetails->RecurringPaymentsProfileDetails = $profileDetails;
$createRPProfileRequest = new \PayPal\PayPalAPI\CreateRecurringPaymentsProfileRequestType();
$createRPProfileRequest->CreateRecurringPaymentsProfileRequestDetails = $createRPProfileRequestDetails;
$createRPProfileReq = new \PayPal\PayPalAPI\CreateRecurringPaymentsProfileReq();
$createRPProfileReq->CreateRecurringPaymentsProfileRequest = $createRPProfileRequest;
return $this->paypalService->CreateRecurringPaymentsProfile($createRPProfileReq);
}
In my sandbox account i can see that the recurring payment is created, but there is no initial payment.
My question is: How can i setup this recurring payment, so that an initial payment is made?
Hope i`ve explained good my problem. If you need more information comment.
EIDT: My question was how to create a recurring payment with initial payment. and i edited my code snippet. After some reading i saw that i missed to set it up with setting "ActivationDetailsType". I set it up and it works fine with one problem ... The payment profile is pending for 4-5 hours and then comes through. I read in forums and etc... that this was a sandbox issue but unfortunetly i cannot be sure that the payment will not be deleyd. In my case i need the payment to be approved right away. My new question is, when creating recurring payment profile, and the response for the account is ok(succes or what not) and the profile is pending can i count the payment as successful and be sure i`ll get the money for sure
Thank you for the time.
Regards,
Georgi
Quite late but I'm having similar concerns.
My new question is, when creating recurring payment profile, and the response for the account is ok(succes or what not) and the profile is pending can i count the payment as successful and be sure i`ll get the money for sure?
I'm currently working on it but I wouldn't count the pay until PayPal reflects the payment. I would utilize the IPN to trigger actions that should be made when the payment has come through. As for the 4-5 hour processing by PayPal (though sources from the web say production should not have the same delay), I'll just be sure to notify the buyer that his/her payment is still being processed by PayPal.