javascript - Angular PayPal 处理、子组件和生命周期
问题描述
我目前正在我自己的商店(Angular Frontend,dotnet core WebApi backend)中进行 PayPal 集成,显然我在主组件(CheckoutProcessComponent)和子组件(PaymentPayPalComponent)之间的生命周期以及使用必要的 PayPal javascript。
基本上,只要我使用静态变量,完整的 PayPal 工作流程就可以工作。这正是我的问题开始的地方。
CheckoutProcessComponent.ts
import { Component, OnInit } from '@angular/core';
import { CartService } from 'src/app/_services/shop/cart.service';
import { ISubscriptionCollection } from 'src/app/_models/misc/ISubscriptionCollection';
import { serialUnsubscriber } from 'src/app/shared/utility.module';
import { CheckoutService } from 'src/app/_services/checkout/checkout.service';
import { ICheckoutOrderData } from 'src/app/_models/shop/ICheckoutOrderData';
import { IOrderProcessSummary } from 'src/app/_models/shop/IOrderProcessSummary';
@Component({
selector: 'app-checkout-process',
templateUrl: './checkout-process.component.html',
styleUrls: ['./checkout-process.component.css']
})
export class CheckoutProcessComponent implements OnInit {
subscriptions: ISubscriptionCollection = {};
checkoutOrderData = {} as ICheckoutOrderData;
orderSummaryFromServer: IOrderProcessSummary;
orderCreated: boolean = false;
constructor(public checkoutService: CheckoutService, public cartService: CartService) { }
ngOnInit() {
this.checkoutOrderData.Order = this.checkoutService.orderData;
this.checkoutOrderData.Cart = this.cartService.shoppingCart;
// Create Order
this.subscriptions['createOrder'] = this.checkoutService.createOrder(this.checkoutOrderData)
.subscribe((res: IOrderProcessSummary) => {
this.checkoutService.checkoutSummary = res;
this.orderSummaryFromServer = res;
console.log('Order created: ' + res);
}, error => {
console.log('Error');
});
}
ngOnDestroy(): void {
serialUnsubscriber(...Object.values(this.subscriptions));
}
nextStep(step: number) {
this.checkoutService.updateCheckoutStep(step);
}
...
}
CheckoutProcessComponent.html
<app-payment-paypal [orderSummary]="orderSummaryFromServer" *ngIf="checkoutService.orderData.paymentMethod === 'PM_PAYPAL'"></app-payment-paypal>
<app-payment-stripe *ngIf="checkoutService.orderData.paymentMethod === 'PM_STRIPE'"></app-payment-stripe>
<app-payment-moneytransfer *ngIf="checkoutService.orderData.paymentMethod === 'PM_TRANSFER'"></app-payment-moneytransfer>
支付PayPalComponent.ts
import { Component, OnInit, AfterViewChecked, Input } from '@angular/core';
import { environment } from 'src/environments/environment';
import { IOrderProcessSummary } from 'src/app/_models/shop/IOrderProcessSummary';
import { CheckoutService } from 'src/app/_services/checkout/checkout.service';
declare let paypal: any;
@Component({
selector: 'app-payment-paypal',
templateUrl: './payment-paypal.component.html',
styleUrls: ['./payment-paypal.component.css']
})
export class PaymentPaypalComponent implements OnInit, AfterViewChecked {
@Input() orderSummary: IOrderProcessSummary;
paypalClientId = environment.paymentPayPal.clientId;
addScript: boolean = false;
scriptTagElement: HTMLScriptElement;
constructor(private checkoutService: CheckoutService) { }
ngOnInit() {
}
ngOnDestroy(): void {
if (this.scriptTagElement) {
document.body.removeChild(this.scriptTagElement);
}
}
ngAfterViewChecked(): void {
if (!this.addScript) {
this.addPayPalScript().then(() => {
paypal.Buttons({
createOrder: function() {
return fetch('https://localhost:5021/api/payments/paypal-create-order', {
method: 'post',
headers: {
'content-type': 'application/json'
},
body: JSON.stringify({
orderId: 1234
})
}).then(function(res) {
return res.json();
}).then(function(data) {
return data.id; // Use the same key name for order ID on the client and server
});
},
onApprove: function(data, actions) {
console.log('onApprove - transaction was approved, but not authorized', data, actions);
actions.order.get().then(details => {
console.log('onApprove - you can get full order details inside onApprove: ', details);
});
return fetch('https://localhost:5021/api/payments/paypal-capture-order', {
method: 'post',
headers: {
'content-type': 'application/json'
},
body: JSON.stringify({
token: data.orderID,
payerID: data.payerID,
})
});
},
onClientAuthorization: (data) => {
console.log('onClientAuthorization - you should probably inform your server about completed transaction at this point', data);
// this.showSuccess = true;
},
onCancel: (data, actions) => {
console.log('OnCancel', data, actions);
// this.showCancel = true;
},
onError: err => {
console.log('OnError', err);
// this.showError = true;
}
}).render('#paypal-button-container');
})
}
}
addPayPalScript() {
return new Promise((resolve, reject) => {
this.scriptTagElement = document.createElement('script');
this.scriptTagElement.src = 'https://www.paypal.com/sdk/js?currency=EUR&client-id=' + this.paypalClientId;
this.scriptTagElement.onload = resolve;
document.body.appendChild(this.scriptTagElement);
this.addScript = true;
})
}
}
PaymentPayPalComponent.html
<div class="text-center" id="paypal-button-container"></div>
处理流程如下:
- CheckoutProcessComponent > 在服务器上使用购物车数据创建订单并将订单存储在数据库中(通用功能,与 PayPal 无关)
- 1. 的结果是 IOrderProcessSummary,其中包含订单 ID 和订单总额
- 根据选择的付款方式,将显示相应的付款-子组件。在这种情况下,PaymentPayPalComponent。
- 然后我使用 PayPal 功能“CreatePayPalOrderOnServer”,它在我的后端使用 PayPal Api 在 PayPal 服务器上创建订单。但为此我需要特定的 orderId,因为我需要使用系统中的特定订单数据填充 PayPal-Order 数据(在示例中,我有一个固定的 1234 订单 ID)。
对于第 4 步。我尝试使用 Input() 参数并将 CheckoutService 注入到 PaymentPayPalComponent 但我无法使用 PayPal-Button-Function (JavaScript) 中的任何类型的动态变量。在示例中,我需要使用 Input() orderSummary 中的值或 CheckoutService 中的相同值更改“orderId:1234”,但它们都保持未定义。
PayPal-Javascript 已正确加载,并且 PayPal-Buttons 显示并按技术预期工作。
如何将我的动态数据带入 PaymentPayPalComponent 和 PayPal.Buttons-Function?
感谢您的提示!
解决方案
推荐阅读
- php - 如何在全局范围内将所有 Eloquent 时间戳视为包括时区
- java - 如何根据另一个 TextView 的内容有条件地启用 TextView?
- java - Firebase 初始化未启动
- javascript - 如何从已加载的资产中检索 SVG 数据?
- c# - 在 Unity 中实现对话系统的问题
- php - 什么是最短的路
- java - JPanel、2D 图形和 MouseListener 遇到问题
- tensorflow - 卷积神经网络得到一个值错误
- wpf - 是否可以更改 WPF 元素的边界?
- ios - 错误 ibtoold[1345:11688] 调试:添加到环境:(在 IOS 中运行 xamarin 表单时出错)