In questo tutorial ti mostrerò come puoi eseguire i pagamenti utilizzando l'API REST di PayPal e C #. Tutte le librerie che hanno per linguaggi diversi come Ruby, Node.js, Python, PHP sono molto simili, quindi tutti i concetti qui si applicano a tutte le librerie.
Per iniziare, ho creato un progetto MVC in Visual Studio 2015: File> Nuovo> Progetto, e selezionare Applicazione ASP.NET.
Seleziona il Applicazione Web ASP.NET 5 Template, che utilizza il nuovo MVC 6. È simile a MVC 5 se si ha familiarità con esso.
Come puoi vedere nella foto qui sotto, ho aggiunto alcuni file e cartelle alla soluzione. Le due cose principali da notare sono:
Installa l'SDK PayPal utilizzando NuGet. Clic destro sul nome della soluzione e selezionare Gestisci i pacchetti NuGet, quindi cerca "PayPal" e installalo.
Per integrare la nostra applicazione con PayPal, abbiamo bisogno di navigare verso gli sviluppatori PayPal, e poi sotto App API REST, clicca su Crea app.
Dai un nome alla tua app e scegli un account sviluppatore sandbox associato all'app. A scopo di test, possiamo quindi navigare su http://sandbox.paypal.com ed effettuare il login con i dettagli di accesso sandbox per vedere il conto PayPal e le transazioni di prova.
Dopo aver cliccato su Crea app, vediamo la schermata di conferma con l'ID cliente e i token segreti.
Copia i token clientId e clientSecret su appsettings.json
, come puoi vedere nello screenshot qui sotto:
PayPal fornisce un ambiente Sandbox per i test. Puoi creare account compratore e venditore di prova da lì. Quando ti iscrivi, avrai un account Business nella Sandbox legato al tuo account sviluppatore.
Per creare un nuovo account di prova, accedere al sito per sviluppatori, quindi fare clic su Cruscotto scheda e vai a Sandbox> Account. Qui puoi vedere l'elenco degli account di prova se ne hai:
Se non hai ancora creato i tuoi account di prova, vai avanti e clicca su Creare un profilo, in alto a destra, per creare almeno un account personale di prova e un account aziendale di prova.
Dopo aver creato gli account di prova, puoi accedere tramite www.sandbox.paypal.com con l'indirizzo email di prova e la password che hai assegnato a ciascun account nel modulo precedente. Questo è davvero utile per testare che quando acquisti qualcosa con il tuo 'conto di prova personale' i fondi vengono trasferiti al tuo 'account di business di prova'. Ora sei pronto per iniziare l'integrazione con PayPal e verificare che i fondi passino da un account a un altro.
PayPal offre diversi metodi di pagamento. Puoi utilizzare i pagamenti diretti con carta di credito, il che significa che i tuoi clienti non riescono a visualizzare la pagina di accesso o il riepilogo di PayPal: tutto ciò avviene nel tuo sito web. Devi essere compatibile PCI per questo, e ti consiglio di usare Stripe, poiché hai solo bisogno di SSL usando la loro libreria JavaScript. D'altra parte, per effettuare pagamenti tramite pagamenti PayPal, sono necessari tre passaggi:
Nel mio progetto MVC, nel Servizi cartella, ho creato la classe PayPalPaymentService in cui ho aggiunto questi metodi:
pagamento statico pubblico CreatePayment (stringa baseUrl, stringa intent) // ### Api Contesto // Passa in un oggetto 'APIContext' per autenticare // la chiamata e inviare un ID di richiesta univoco // (che garantisce l'idempotenza). L'SDK genera // un ID di richiesta se non ne passi uno esplicitamente. var apiContext = PayPalConfiguration.GetAPIContext (); // Payment Variazione var payment = new Payment () intent = intent, // 'sale' o 'authorize' payer = new Payer () payment_method = "paypal", transaction = GetTransactionsList (), redirect_urls = GetReturnUrls (baseUrl , intento); // Crea un pagamento utilizzando un valore APIContext var creatoPayment = payment.Create (apiContext); return createdPayment; Elenco statico privatoGetTransactionsList () // Una transazione definisce il contratto di un pagamento // qual è il pagamento e chi lo sta rispettando. var transactionList = new List (); // L'API per la creazione del pagamento richiede un elenco di transazioni; // aggiungi la Transazione creata a un elenco transactionList.Add (new Transaction () description = "Descrizione transazione.", invoice_number = GetRandomInvoiceNumber (), amount = new Amount () currency = "USD", total = "100.00" , // Totale deve essere uguale alla somma di spedizione, tasse e subtotale Dettagli = nuovo Dettagli () // Dettagli: consente di specificare i dettagli di un importo di pagamento. IVA = "15", spedizione = "10", subtotale = "75", item_list = new ItemList () items = new List - () new Item () name = "Nome oggetto", valuta = "USD", prezzo = "15", quantità = "5", sku = "sku"); return transactionList; private static RedirectUrls GetReturnUrls (string baseUrl, stringa intent) var returnUrl = intent == "sale"? "/ Home / Pagamento riuscito": "/ Home / Autorizza successo"; // Reindirizzamento URL // Questi URL determineranno il modo in cui l'utente viene reindirizzato da PayPal // dopo aver approvato o annullato il pagamento. return new RedirectUrls () cancel_url = baseUrl + "/ Home / PaymentCancelled", return_url = baseUrl + returnUrl; Pagamento statico pubblico ExecutePayment (stringa paymentId, stringa payerId) // ### Api Context // Passare in un oggetto 'APIContext' per autenticare // la chiamata e inviare un ID di richiesta univoco // (che garantisce l'idempotenza). L'SDK genera // un ID di richiesta se non ne passi uno esplicitamente. var apiContext = PayPalConfiguration.GetAPIContext (); var paymentExecution = new PaymentExecution () payer_id = payerId; var payment = new Payment () id = paymentId; // Esegui il pagamento. var executionPayment = payment.Execute (apiContext, paymentExecution); ritorno eseguitoPagamento;
Ci sono alcuni parametri che vengono passati in questa chiamata:
Le funzioni precedenti possono essere utilizzate dal tuo controller in questo modo:
public IActionResult CreatePayment () var payment = PayPalPaymentService.CreatePayment (GetBaseUrl (), "sale"); return Redirect (payment.GetApprovalUrl ()); public IActionResult PaymentCancelled () // TODO: Gestire il pagamento annullato restituire RedirectToAction ("Errore"); public IActionResult PaymentSuccessful (stringa paymentId, stringa token, stringa PayerID) // Esegui pagamento var payment = PayPalPaymentService.ExecutePayment (paymentId, PayerID); return View ();
Come puoi vedere, ho creato tre azioni:
Questo scenario è molto simile al caso precedente. Potresti voler utilizzare questo metodo se stai tentando di prendere pre-ordini per un prodotto che non è ancora disponibile. I passaggi per ottenere questo pagamento sono:
Per implementare questo tipo di pagamento, ho solo aggiunto un nuovo metodo alla classe PayPalPaymentService per acquisire il pagamento:
public static Capture CapturePayment (stringa paymentId) var apiContext = PayPalConfiguration.GetAPIContext (); var payment = Payment.Get (apiContext, paymentId); var auth = payment.transactions [0] .related_resources [0] .authorization; // Specifica una quantità da catturare. Impostando 'is_final_capture' su true, tutti i restanti fondi detenuti dall'autorizzazione verranno rilasciati dallo strumento di finanziamento. var capture = new Capture () amount = new Amount () currency = "USD", total = "4.54", is_final_capture = true; // Catturare un pagamento autorizzato tramite POSTing su // URI v1 / pagamenti / autorizzazione / autorizzazione_id / capture var responseCapture = auth.Capture (apiContext, capture); return responseCapture;
Quindi da HomeController, ho aggiunto due nuove azioni per mostrare questo tipo di pagamento:
public IActionResult AuthorizePayment () var payment = PayPalPaymentService.CreatePayment (GetBaseUrl (), "authorize"); return Redirect (payment.GetApprovalUrl ()); public IActionResult AuthorizeSuccessful (stringa paymentId, stringa token, stringa PayerID) // Capture Payment var capture = PayPalPaymentService.CapturePayment (paymentId); return View ();
In questi esempi di codice, per semplicità, ho codificato i valori delle variabili di pagamento. Nella tua vera applicazione, probabilmente li racchiuderai in metodi che prendono tutti questi valori come variabili in modo che tutto possa essere impostato dinamicamente e riutilizzato.
Questo è chiamato "Piani di fatturazione" in PayPal: puoi creare piani di pagamento ricorrenti e sottoscrivere i tuoi clienti a un piano di fatturazione creando un contratto di fatturazione. Utilizzando l'API REST di PayPal è possibile creare, aggiornare o eliminare piani di fatturazione; questo è qualcosa che potresti usare se vuoi costruire un pannello di amministrazione per gestire queste cose per la tua azienda.
I passaggi per creare addebiti ricorrenti ai clienti potrebbero essere:
Crea un piano di fatturazione che definisca i periodi di fatturazione. Questo è un riepilogo dei parametri che dobbiamo passare per creare un piano.
Questo è uno snippet di codice che mostra come creare un piano di fatturazione:
// Definire il piano e allegare le definizioni di pagamento e le preferenze del commerciante. // Ulteriori informazioni: https://developer.paypal.com/webapps/developer/docs/api/#create-a-plan var billingPlan = new Plan name = "Tuts + Plus", description = "Piano mensile per i corsi. ", type =" fixed ", // Definire le preferenze del commerciante. // Ulteriori informazioni: https://developer.paypal.com/webapps/developer/docs/api/#merchantpreferences-object merchant_preferences = new MerchantPreferences () setup_fee = GetCurrency ("0"), $ $ return_url = "returnURL ", // Recupera da config cancel_url =" cancelURL ", // Recupera da config auto_bill_amount =" YES ", initial_fail_amount_action =" CONTINUA ", max_fail_attempts =" 0 ", payment_definitions = new List// Definisci un piano di prova che addebiterà solo $ 9,99 per il primo // mese. Successivamente, il piano standard subentrerà per i restanti 11 mesi dell'anno. new PaymentDefinition () name = "Trial Plan", type = "TRIAL", frequency = "MONTH", frequency_interval = "1", amount = GetCurrency ("0"), // Free per i cicli del 1 ° mese = "1 ", charge_models = new List new ChargeModel () type = "TAX", amount = GetCurrency ("1.65") // Se dobbiamo addebitare Tax, nuovo ChargeModel () type = "SHIPPING", amount = GetCurrency ("9,99") / / Se è necessario pagare per la spedizione, // Definire il piano di pagamento standard. Rappresenterà un piano // mensile per $ 19,99 USD che verrà addebitato una volta al mese per 11 mesi. new PaymentDefinition name = "Standard Plan", type = "REGULAR", frequency = "MONTH", frequency_interval = "1", amount = GetCurrency ("15.00"), //> NOTA: per i piani di tipo "IFNINITE", " cicli 'dovrebbe essere 0 per un oggetto' PaymentDefinition '' REGULAR 'cicli = "11", charge_models = new List new ChargeModel type = "TAX", amount = GetCurrency ("2.47"), nuovo ChargeModel () type = "SHIPPING", amount = GetCurrency ("9.99"); // Ottieni PayPal Config var apiContext = PayPalConfiguration.GetAPIContext (); // Crea Plan plan.Create (apiContext);
Un piano di fatturazione appena creato è in uno stato CREATO. Attivalo allo stato ATTIVO, in modo che i tuoi clienti possano iscriversi al piano. Per attivare il piano, dobbiamo fare una richiesta PATCH:
// Attiva il piano var patchRequest = new PatchRequest () new Patch () op = "replace", path = "/", value = new Plan () state = "ACTIVE"; plan.Update (apiContext, patchRequest);
Come potete vedere, le librerie PayPal sono un involucro diretto sulla loro API REST, che è buona, ma l'API è anche molto complessa rispetto ad altre come Stripe. Per questo motivo, è davvero una buona opzione per avvolgere tutte le comunicazioni PayPal in oggetti con API più chiare e più semplici per le nostre applicazioni. Qui puoi vedere cosa questo codice racchiude in più funzioni assumendo parametri come:
piano statico pubblico CreatePlanObject (stringa planName, stringa planDescription, string returnUrl, string cancelUrl, string frequency, int frequencyInterval, decimal planPrice, decimal shippingAmount = 0, decimal taxPercentage = 0, bool trial = false, int trialLength = 0, decimal trialPrezzo = 0 ) // Definire il piano e allegare le definizioni di pagamento e le preferenze del commerciante. // Ulteriori informazioni: https://developer.paypal.com/docs/rest/api/payments.billing-plans/ return new Plan nome = planName, description = planDescription, type = PlanType.Fixed, // Definisci il commerciante preferenze. // Ulteriori informazioni: https://developer.paypal.com/webapps/developer/docs/api/#merchantpreferences-object merchant_preferences = new MerchantPreferences () setup_fee = GetCurrency ("1"), return_url = returnUrl, cancel_url = cancelUrl , auto_bill_amount = "YES", initial_fail_amount_action = "CONTINUE", max_fail_attempts = "0", payment_definitions = GetPaymentDefinitions (trial, trialLength, trialPrice, frequency, frequencyInterval, planPrice, shippingAmount, taxPercentage); Elenco statico privatoGetPaymentDefinitions (bool trial, int trialLength, decimal trialPrice, string frequency, int frequencyInterval, decimal planPrice, decimal shippingAmount, decimal taxPercentage) var paymentDefinitions = new List (); if (trial) // Definire un piano di prova che addebiterà 'trialPrice' per 'trialLength' // Dopo questo, il piano standard prenderà il sopravvento. paymentDefinitions.Add (new PaymentDefinition () name = "Trial", type = "TRIAL", frequency = frequency, frequency_interval = frequencyInterval.ToString (), amount = GetCurrency (trialPrice.ToString ()), cycles = trialLength.ToString ( ), charge_models = GetChargeModels (trialPrice, shippingAmount, taxPercentage)); // Definire il piano di pagamento standard. Rappresenterà un piano di "frequenza" (mensile, ecc.) Per "planPrice" che addebita "planPrice" (una volta al mese) per #cycles. var regularPayment = new PaymentDefinition name = "Piano standard", type = "REGULAR", frequency = frequency, frequency_interval = frequencyInterval.ToString (), amount = GetCurrency (planPrice.ToString ()), //> NOTA: per 'IFNINITE 'digita piani,' cicli 'dovrebbe essere 0 per un oggetto' REGOLARE 'PaymentDefinition'. cycles = "11", charge_models = GetChargeModels (trialPrice, shippingAmount, taxPercentage); paymentDefinitions.Add (regularPayment); return paymentDefinitions; private static Elenco GetChargeModels (decimal planPrice, decimal shippingAmount, decimal taxPercentage) // Crea il piano di fatturazione var chargeModels = new List (); if (shippingAmount> 0) chargeModels.Add (new ChargeModel () type = "SHIPPING", importo = GetCurrency (shippingAmount.ToString ())); if (taxPercentage> 0) chargeModels.Add (new ChargeModel () type = "TAX", amount = GetCurrency (String.Format ("0: f2", planPrice * taxPercentage / 100))); return chargeModels;
È possibile aggiornare le informazioni per un piano di fatturazione esistente facendo una richiesta di 'PATCH'. Questa è una funzione che avvolge quella chiamata:
pubblico static void UpdateBillingPlan (stringa planId, percorso stringa, valore oggetto) // Token Autenticazione PayPal var apiContext = PayPalConfiguration.GetAPIContext (); // Recupera piano var plan = Plan.Get (apiContext, planId); // Attiva il piano var patchRequest = new PatchRequest () new Patch () op = "replace", percorso = percorso, valore = valore; plan.Update (apiContext, patchRequest);
Per aggiornare la descrizione del piano di fatturazione, possiamo chiamare questa funzione e passare i parametri corretti:
UpdateBillingPlan (planId: "P-5FY40070P6526045UHFWUVEI", percorso: "/", valore: new Plan description = "new description");
Idealmente, quando non desideri accettare nuovi clienti in un piano di fatturazione, ti consigliamo di aggiornarlo allo stato "INATTIVO". Ciò non influirà sugli accordi di fatturazione esistenti su questo piano. Questo può essere fatto semplicemente chiamando la funzione UpdateBillingPlan:
UpdateBillingPlan (planId: "P-5FY40070P6526045UHFWUVEI", percorso: "/", valore: new Plan state = "INACTIVE");
Dopo aver creato uno o più piani di fatturazione, si desidera iniziare a chiedere ai clienti di sottoscrivere i piani di abbonamento. Per fare ciò, è necessario raccogliere i dettagli del cliente ed effettuare una richiesta a PayPal. Per poter testare questa funzionalità, ho aggiunto diverse azioni a HomeController:
public IActionResult Subscribe () var plan = PayPalSubscriptionsService.CreateBillingPlan ("Tuts + Plan", "Piano di test per questo articolo", GetBaseUrl ()); var subscription = PayPalSubscriptionsService.CreateBillingAgreement (plan.id, new PayPal.Api.ShippingAddress city = "London", line1 = "riga 1", postal_code = "SW1A 1AA", country_code = "GB", "Pedro Alonso", "Tuts +", DateTime.Now); return Redirect (subscription.GetApprovalUrl ()); public IActionResult SubscribeSuccess (stringa token) // Esegui l'accordo approvato PayPalSubscriptionsService.ExecuteBillingAgreement (token); return View (); public IActionResult SubscribeCancel (stringa token) // TODO: gestisce il pagamento annullato restituito RedirectToAction ("Errore");
Come puoi vedere nello snippet di codice precedente, ho spostato la maggior parte delle funzionalità in diversi metodi. Il primo è "CreateBillingPlan" che è stato spiegato nella sezione precedente. Il secondo è "CreateBillingAgreement" che viene utilizzato per iscrivere un utente a un piano:
accordo statico pubblico CreateBillingAgreement (string planId, ShippingAddress shippingAddress, nome stringa, descrizione stringa, DateTime startDate) // Token di autenticazione PayPal var apiContext = PayPalConfiguration.GetAPIContext (); var agreement = new Agreement () name = nome, descrizione = descrizione, start_date = startDate.ToString ("aaaa-MM-ggTHH: mm: ss") + "Z", pagatore = nuovo pagatore () payment_method = "paypal ", plan = new Plan () id = planId, shipping_address = shippingAddress; var createdAgreement = agreement.Create (apiContext); return createdAgreement;
Il terzo metodo è "ExecuteBillingAgreement". Dopo l'approvazione dell'abbonamento, utilizziamo il token restituito per attivare l'abbonamento:
pubblico static void ExecuteBillingAgreement (stringa token) // Token di autenticazione PayPal var apiContext = PayPalConfiguration.GetAPIContext (); var agreement = new Agreement () token = token; var executionAgreement = agreement.Execute (apiContext);
Utilizzare questo metodo per sospendere un accordo:
public static void SuspendBillingAgreement (string agreementId) var apiContext = PayPalConfiguration.GetAPIContext (); var agreement = new Agreement () id = agreementId; agreement.Suspend (apiContext, new AgreementStateDescriptor () note = "Sospensione del contratto");
Questo è molto simile al precedente:
public static void ReactivateBillingAgreement (string agreementId) var apiContext = PayPalConfiguration.GetAPIContext (); var agreement = new Agreement () id = agreementId; agreement.ReActivate (apiContext, new AgreementStateDescriptor () note = "Riattivazione dell'accordo");
Utilizzare questa funzione per cancellare un piano:
public static void CancelBillingAgreement (string agreementId) var apiContext = PayPalConfiguration.GetAPIContext (); var agreement = new Agreement () id = agreementId; agreement.Cancel (apiContext, new AgreementStateDescriptor () note = "Annullamento dell'accordo");
Questa opzione è molto limitata e ciò che mi aspetterei da questa chiamata è la possibilità di modificare il piano di abbonamento, per l'aggiornamento o il downgrade di un cliente. Questo non è supportato in una singola chiamata come in Stripe. È necessario gestire questo scenario annullando l'accordo corrente e creando uno nuovo per aggiornamenti o downgrade. Non è l'ideale, ma potrebbe cambiare in futuro.
Questa è una panoramica delle funzioni più comuni che le persone utilizzano per l'integrazione con PayPal. La loro API è molto più grande dei metodi di integrazione spiegati in questo articolo: puoi anche emettere rimborsi e rimborsi parziali, e hanno molte opzioni diverse per i casi limite negli esempi trattati in questo articolo. Se sei interessato a ottenere maggiori dettagli su qualsiasi integrazione specifica, lascia un suggerimento nei commenti.