lets say I have an ecommerce website and I want to start accepting Solana.
The customer will fill the cart and proceed to the checkout page, there I can display a QR code where the user can scan to pay.
Now I want to know if the checkout has been paid so I can mark the order as paid, is there a good way to accomplish that? maybe using Solana pay I can pass a reference or something?
You can use the validateTransfer method to do that
validateTransfer allows you to validate that the transaction signature found matches the transaction that you expected.
try {
await validateTransfer(connection, signature, {
recipient: MERCHANT_WALLET,
amount
});
// Update payment status
paymentStatus = 'validated';
console.log('✅ Payment validated');
console.log('📦 Ship order to customer');
} catch (error) {
console.error('❌ Payment failed', error);
}
check out the solana documentation for this
Related
I'm trying to push a transaction into square via the API, using the following endpoint:
POST https://connect.squareup.com/v2/locations/location_id/transactions
// Below the data pushed
{
"card_nonce": "-card_nonce-",
"idempotency_key": "-idempotency_key-",
"reference_id": "-reference_id-",
"amount_money": {
"amount": 100,
"currency": "-currency-"
}
}
The problem is that, when I look at the transaction in the dashboard, the details won't display the TAX withheld for the payment. I've also created in the "taxes" tab, an appropriate tax element, which is applied to all the items.
This seems to be working fine for the payments that go through the square app, although, it doesn't work for the payments that go through the API endpoint mentioned above.
Is there any way to specify the tax in the transaction payload? if not, is there any way to solve this issue?
Thanks.
To get your desired outcome, I think you want to create an order first.
You should be able to create the order (with the appropriate taxes, but also itemizations and discounts as well) and then pass the order_id to the charge endpoint. Then your taxes should be correctly calculated, and more details reflected in Dashboard.
I'm creating a new customer in stripe using a token created in the user's browser. This is on parse.com's servers, for what it's worth. I would like to retain a few details on the card, such as last4, but the customer object shows no sources under sources.data. Any pointers on how to get this information? Thanks for your help.
return Stripe.Customers.create({
source: token,
email: email
}).then(function(rr) {
console.log(rr.sources);
[ process response...]
});
This is the output:
{"object":"list","total_count":1,"has_more":false,"url":"/v1/customers/cus_[removed]/sources","data":[{}]}
It's bit strange that you are creating a customer but getting the object of customers list (https://stripe.com/docs/api/node#list_customers).
If customer is created successfully at stripe than it should return the customer object. You can check in more details here: https://stripe.com/docs/api/node#create_customer
I suggest here that please check the customer creation code once again at your side.
I'm working on an iOS app that uses Stripe to process payments. We are moving from a system that uses two separate charges for initial purchase and tip to a system that uses a single charge that begins as a hold on the user's account and then is captured upon setting the tip. This was the system that Stripe recommended to us when we inquired how to work with a single charge but also validate that the card can handle a charge of the designated amount.
For our back end, we are using Parse.com to track our orders, and so we are using Stripe's integration with Parse.com's Cloud Code as our server. Our main issue is that Parse.com doesn't seem to outright support most of Stripe's functionality (i.e. capturing charges). After some searching, I found that http POST requests were the best option to interact with Stripe.js and actually capture charges. However, I haven't been able to get quite that far because Parse.com is giving me a Code 141 error (Received unknown parameter: captured) when I try to create a charge that is uncaptured. Parse.com's Stripe API suggests that you can set all parameters through their Stripe.Charges.create, but it won't accept captured as a valid parameter.
To abstract for anyone else with this issue, how can I create a charge that has the parameter captured set to false using Parse.com Stripe API?
I have posted some of my Cloud Code below that should define a method to create a charge that has not yet been captured. This method is what is giving me the error that captured is not a valid parameter.
/**
* Create Hold on Card
* Required:
* orderCostInCents -- in cents ex. $10.24 = 1024
* customer -- cus_11EXEXEXEXEXEX
* description -- order.objectId to link it with order item.
*/
Parse.Cloud.define("holdAccount", function(request, response) {
//response.success("Not Charged");
var Stripe = require("stripe");
Stripe.initialize(kStripePrivateKey);
Stripe.Charges.create({
amount : request.params.orderCostInCents,
currency : "usd",
customer : request.params.customer,
captured : false,
description : request.params.description
},{
success: function(httpResponse) {
console.log(httpResponse);
response.success(httpResponse);
},
error: function(httpResponse) {
console.log(httpResponse.message);
response.error("Failed to create charge");
}
});
});
I believe that I can structure an http (POST) request after creating the charge by following the guidelines set at https://www.parse.com/questions/stripe-payment-capture-method-not-available. This guide might be very helpful to anyone else with my issue!
Best, and thanks for your help!
Edit: I realized that I didn't post the version of Cloud Code that we are using. It is 1.2.19.
Well, after taking a break from my hours of staring at the screen, I certainly feel like a doofus! The parameter I was using was captured, where the correct parameter should be capture. I was able to fix my issue by simply removing the "d" from the parameter name while creating the charge.
Whoops! I would still be open to advice on http requests via comments, but I will test those on my own and post a separate thread if I run into issues there as that issue is tangential to this one and thus off-topic.
For everyone joining, the answer is that the above code works perfectly if you replace the parameter captured with capture
Edit: For anyone else that is interested, the follow-up to this question was about actually making the capture via http requests on Parse Cloud Code. The following method works after much searching and trial and error. The hardest part here was figuring out how to format the URL since this is my first foray into http requests. If you need to chain parameters, simply add "&{parameter-name}={parameter-value}"
//kStripePrivateKey is your stripe private key
//Must pass in chargeID = stripe charge id and
//orderCostInCents = capture amount in cents as parameters
var captureURL = "https://"+ kStripePrivateKey +
":#api.stripe.com/v1/charges/"+
request.params.chargeID+
"/capture?amount="+request.params.orderCostInCents;
Parse.Cloud.httpRequest({
url: captureURL,
method: 'POST',
success: function(httpResponse) {
// Handle any success actions here
response.success(httpResponse);
}, error: function(httpResponse) {
response.error(httpResponse);
}
});
I have been trying to integrate a payment system for a subscription service using Laravel Cashier.
I have set up my RegistrationController so that it works out how many days until the first day of the next month.
Using $user->trial_ends_at = Carbon::now()->addDays($datediff);
When creating a user it sets the trial end date for the first of the next month.
From here I want to use the $user->onTrial() method to create the actual subscription.
Please note: Even though the user is created there is no customer created in Stripe as the subscription has not yet been created.
My questions:
In the registration form the card details are taken so the users can subscribe and set up their payment method. This involves stripe validating the card and sending back a token.
Can this token be stored and used later?
Assuming I can use this token later on, to create the actual subscription in cashier I have to check whether the users trial has ended using the onTrial method.
The subscription is created using this:
$user->subscription($subscription_plan)->create($stripeToken);
Where is best to add the above code so that the user is subscribed and the billing period is started at the end of the trial?
This isn't mentioned at all in the in the documentation so I was just wondering if I create a new controller to actually start the subscription where to call the function and how to get it to run as each users trial ends.
Edit:
Would something like this be possible using Queues?
http://laravel.com/docs/4.2/queues
$start_subscription = Carbon::now()->addDays($datediff);
Queue::later($start_subscription, 'RegistrationController#subscribe',
array('stripeToken' => $stripeToken, 'details' => $otherDetails));
and then run the subscription method for each user at the set time.
I noticed some issues with creating the Stripe customer at the same time as the subscription. I was ending up with lots of extra customers inside Stripe because if the customer is created, but the subscription has an error, it doesn't connect them in Cashier, but the customer is connected in Stripe.
So to separate the two, I created a helper method in the User model. It will let me create the customer without creating a subscription. I can then create a subscription at a later time.
I think this addresses your issue.
Helper methods in user model:
/**
* Method to create stripe customer without subscription
*/
public function createStripeCustomer($token, $properties) {
$gateway = $this->subscription();
$customer = $gateway->createStripeCustomer($token, $properties);
$gateway->updateLocalStripeData($customer);
}
public function getStripeCustomer() {
$gateway = $this->subscription();
return $gateway->getStripeCustomer();
}
Then in my API controller where I handle the subscription:
if (!$user->getStripeId()) {
$user->createStripeCustomer($inputs['token'], ['email' => $user->email]);
//this can be done at a much later time, the customer is already stored.
$user->subscription($inputs['plan'])->create(null, [], $user->getStripeCustomer());
Flash::success("Subscription Success!");
} elseif (!$user->getStripeSubscription()) {
$user->subscription($inputs['plan'])->create($inputs['token'], [], $user->getStripeCustomer());
Flash::success("Subscription Success!");
}
As for the Stripe token, you'll want to use that within a few moments of its creation. It's not expected to last for longer than that.
As for your other questions, I'm not a Laravel person, so I couldn't speak to that, but PHP's strtotime() function takes a variety of strings and returns a timestamp. So if you always wanted to have billing start at noon of the first of the next month, you'd set your timestamp to:
strtotime('first day of next month 12:00');
Hope that helps,
Larry
PS I work on Support at Stripe.
I have integrated paypal into codeigniter with paypal_helper (didn't rememeber where I found it, but it is a slightly rewritten version of Paypals original code for express checkout. I try calling this function,
CallShortcutExpressCheckout( $paymentAmount, $currencyCodeType,
$paymentType, $returnURL, $cancelURL)
sending $paymentAmount as int, $currencyCodeType as "NOK" and $paymentType as "Sale".
Both in Sandbox and live, no amount appears on the paypal site...
What could be wrong?
Edit, to further explain my process. I use this, mostly as specified in the https://www.paypal-labs.com/integrationwizard/ecpaypal/cart.php. This should be doable without the form? The paymentAmount could be sent as a standard variable, when calling the function CallShortcutExpressCheckout?:
$resArray = CallShortcutExpressCheckout ($paymentAmount, $currencyCodeType, $paymentType, $returnURL, $cancelURL);
$ack = strtoupper($resArray["ACK"]);
if($ack=="SUCCESS" || $ack=="SUCCESSWITHWARNING")
{
RedirectToPayPal ( $resArray["TOKEN"] );
}
else
{
//Display a user friendly Error on the page using any of the following error information returned by PayPal
$ErrorCode = urldecode($resArray["L_ERRORCODE0"]);
$ErrorShortMsg = urldecode($resArray["L_SHORTMESSAGE0"]);
$ErrorLongMsg = urldecode($resArray["L_LONGMESSAGE0"]);
$ErrorSeverityCode = urldecode($resArray["L_SEVERITYCODE0"]);
echo "SetExpressCheckout API call failed. ";
echo "Detailed Error Message: " . $ErrorLongMsg;
echo "Short Error Message: " . $ErrorShortMsg;
echo "Error Code: " . $ErrorCode;
echo "Error Severity Code: " . $ErrorSeverityCode;
}
The token is saved in a database. The user gets redirected to Paypal, where no amount is listed.
As you're not passing so called 'line item details' (product data), PayPal doesn't display the total amount.
If you only want to show the amount for the current purchase, redirect buyers to https://www.paypal.com/cgi-bin/webscr?cmd=_express-checkout&token=EC-xxxxxx&useraction=commit (instead of https://www.paypal.com/cgi-bin/webscr?cmd=_express-checkout&token=EC-xxxxx)
If you want to start sending line-item details to PayPal, include the following in your SetExpressCheckout API request:
// Total amount of the purchase, incl shipping, tax, etc
PAYMENTREQUEST_0_AMT=300.0
// Total amount of items purchased, excl shipping, tax, etc
PAYMENTREQUEST_0_ITEMAMT=300.0
// Authorize the funds first (Authorization), or capture immediately (Sale)?
PAYMENTREQUEST_0_PAYMENTACTION=Sale
// First item
L_PAYMENTREQUEST_0_NAME0=Item1
L_PAYMENTREQUEST_0_QTY0=1
L_PAYMENTREQUEST_0_AMT0=100.00
// Second item
L_PAYMENTREQUEST_0_NAME1=Item2
L_PAYMENTREQUEST_0_QTY1=1
L_PAYMENTREQUEST_0_AMT1=200.00
If you want to see this in your own history as well, you'll also need to include this in DoExpressCheckoutPayment.
This was also posted in php paypal express checkout problem
After an extensive reading on messy Paypal docs site this is a short ExpressCheckout guide working on year 2013. I wanted to have item details shown on paypal payment page and merchant transaction history page.
Paypal documentation links
https://developer.paypal.com/webapps/developer/docs/classic/api/
https://developer.paypal.com/webapps/developer/docs/classic/api/merchant/SetExpressCheckout_API_Operation_NVP/
https://developer.paypal.com/webapps/developer/docs/classic/api/merchant/DoExpressCheckoutPayment_API_Operation_NVP/
https://developer.paypal.com/webapps/developer/docs/classic/api/merchant/GetExpressCheckoutDetails_API_Operation_NVP/
You can call following url methods directly on web browser, update token and payerid parameters accordingly.
This is a digital goods so shipping and handling fees are not given. Single item row. Amount and tax fees are given. Do not require a confirmed delivery address, no shipping address fields, no allow freetext note, payer don't need paypal account and no registration required (solutiontype=sole). Activate credit card section on paypal site (landingpage=billing). Use customized brand title on paypal site. Use custom field to give own value for tracking purpose. Merchant site transaction history must show item details (give item details on SetExpressCheckout and DoExpressCheckoutPayment methods).
SetExpressCheckout method opens a new transaction
https://api-3t.sandbox.paypal.com/nvp?
USER=<userid>
&PWD=<pwd>
&SIGNATURE=<mysig>
&METHOD=SetExpressCheckout
&VERSION=98
&PAYMENTREQUEST_0_PAYMENTACTION=SALE
&REQCONFIRMSHIPPING=0
&NOSHIPPING=1
&ALLOWNOTE=0
&SOLUTIONTYPE=Sole
&LANDINGPAGE=Billing
&BRANDNAME=MY+WEBSHOP+TITLE
&PAYMENTREQUEST_0_AMT=22.22
&PAYMENTREQUEST_0_TAXAMT=4.30
&PAYMENTREQUEST_0_ITEMAMT=17.92
&PAYMENTREQUEST_0_DESC=mypurdesc
&PAYMENTREQUEST_0_CUSTOM=custom1
&PAYMENTREQUEST_0_CURRENCYCODE=EUR
&L_PAYMENTREQUEST_0_NUMBER0=itemid1
&L_PAYMENTREQUEST_0_NAME0=MyItem1
&L_PAYMENTREQUEST_0_DESC0=Item1+description
&L_PAYMENTREQUEST_0_QTY0=1
&L_PAYMENTREQUEST_0_AMT0=17.92
&L_PAYMENTREQUEST_0_TAXAMT0=4.30
&RETURNURL=https://myserver.com/webapp/paypal.jsp%3Fcmd=successexp
&CANCELURL=https://myserver.com/webapp/paypal.jsp%3Fcmd=cancelexp
Reply must have ACK=Success or ACK=SuccessWithWarning, read TOKEN value
Redirect user browser to Paypal site, give token value
https://www.sandbox.paypal.com/cgi-bin/webscr?cmd=_express-checkout&token=<token>
User uses paypal account or credit card. Paypal redirects user to return or cancel url.
Redirect destination url gets token and PayerID parameter values.
Transaction is not completed yet we must call doExpressCheckoutPayment method.
Show confirm dialog on screen (with OK, CANCEL button) or simple case
commit a transaction and show "Thank you, purchase completed" message.
User has already accepted a payment in paypal site and expects transaction be finalized.
You may commit transaction within a same request-response handler or using
asynchronous background task. Paypal site may temporarily be unavailable so don't expect it to work immediately.
Commit transaction if redirect was success, use token and payerid
https://api-3t.sandbox.paypal.com/nvp?
USER=<userid>
&PWD=<pwd>
&SIGNATURE=<mysig>
&METHOD=DoExpressCheckoutPayment
&VERSION=98
&PAYMENTREQUEST_0_PAYMENTACTION=SALE
&PAYMENTREQUEST_0_AMT=22.22
&PAYMENTREQUEST_0_TAXAMT=4.30
&PAYMENTREQUEST_0_ITEMAMT=17.92
&PAYMENTREQUEST_0_CURRENCYCODE=EUR
&L_PAYMENTREQUEST_0_NUMBER0=itemid1
&L_PAYMENTREQUEST_0_NAME0=MyItem1
&L_PAYMENTREQUEST_0_QTY0=1
&L_PAYMENTREQUEST_0_AMT0=17.92
&L_PAYMENTREQUEST_0_TAXAMT0=4.30
&token=<token>
&payerid=<payerid>
Read ACK=Success and verify fields
ACK=Success
PAYMENTINFO_0_PAYMENTSTATUS=Completed
PAYMENTINFO_0_ACK=Success
PAYMENTINFO_0_AMT=22.22 total amount must match
PAYMENTINFO_0_FEEAMT=0.99 (just for fun, read paypal comission fee)
PAYMENTINFO_0_CURRENCYCODE=EUR currency must match
(Optional) Read transaction details from Paypal
You can use this during transaction workflow or any time if stored a token for later use.
https://api-3t.sandbox.paypal.com/nvp
?USER=<userid>
&PWD=<pwd>
&SIGNATURE=<mysig>
&METHOD=GetExpressCheckoutDetails
&VERSION=98
&token=<token>
Read response parameters.
ACK=Success
CHECKOUTSTATUS=PaymentActionCompleted
PAYMENTREQUEST_0_AMT=22.22
PAYMENTREQUEST_0_TAXAMT=4.30
PAYMENTREQUEST_0_CURRENCYCODE=EUR
(Optional) Read and save transaction id, correlation id and token id and write to logtable.
PAYMENTREQUEST_0_TRANSACTIONID=11E585715B622391E
CORRELATIONID=4534b683c335f
I'm willing to receive comments if there is any logic errors.
Check this link, hope it helps in some sense:
https://cms.paypal.com/us/cgi-bin/?cmd=_render-content&content_ID=developer/e_howto_api_ECGettingStarted
PAYMENTREQUEST_0_AMT=amount //for amount