无法读取未定义的 属性 'configure'

Cannot read property 'configure' of undefined

我收到错误:

core.js:5882 ERROR TypeError: Cannot read property 'configure' of undefined

当我在 Angular 中为万事达卡实施 Hosted Session Integration 时 2. 这是我的代码:

付款-detail.component.ts

import { AfterViewInit, Component, OnInit } from '@angular/core';
declare var $: any;

@Component({
  selector: 'app-payment-detail',
  templateUrl: './payment-detail.component.html',
  styleUrls: ['./payment-detail.component.css'],
})
export class PaymentDetailComponent implements OnInit, AfterViewInit {
  // PaymentSession: any;

  constructor() {}

  ngAfterViewInit(): void {


    $.getScript(
      'https://ap-gateway.mastercard.com/form/version/57/merchant/<MERCHANTID>/session.js?debug=true',
      function () {
        $.PaymentSession.configure({
          fields: {
            // Attach hosted fields to your payment page
            card: {
              number: '#card-number',
              securityCode: '#security-code',
              expiryMonth: '#expiry-month',
              expiryYear: '#expiry-year',
              nameOnCard: '#cardholder-name',
            },
            giftCard: {
              number: '#gift-card-number',
              pin: '#gift-card-pin',
            },
            ach: {
              accountType: '#ach-account-type',
              bankAccountHolder: '#ach-account-holder',
              bankAccountNumber: '#ach-account-number',
              routingNumber: '#ach-routing-number',
            },
          },
          frameEmbeddingMitigation: ['javascript'],
          callbacks: {
            initialized: function (response) {
              // HANDLE INITIALIZATION RESPONSE
              if (response.status === 'ok') {
                document.getElementById('visaCheckoutButton').style.display =
                  'block';
              }
            },

            formSessionUpdate: function (response) {
              // HANDLE RESPONSE FOR UPDATE SESSION
              if (response.status) {
                if ('ok' == response.status) {
                  console.log(
                    'Session updated with data: ' + response.session.id
                  );

                  //check if the security code was provided by the user
                  if (response.sourceOfFunds.provided.card.securityCode) {
                    console.log('Security code was provided.');
                  }

                  //check if the user entered a MasterCard credit card
                  if (
                    response.sourceOfFunds.provided.card.scheme == 'MASTERCARD'
                  ) {
                    console.log('The user entered a MasterCard credit card.');
                  }
                } else if ('fields_in_error' == response.status) {
                  console.log('Session update failed with field errors.');
                  if (response.errors.cardNumber) {
                    console.log('Card number invalid or missing.');
                  }
                  if (response.errors.expiryYear) {
                    console.log('Expiry year invalid or missing.');
                  }
                  if (response.errors.expiryMonth) {
                    console.log('Expiry month invalid or missing.');
                  }
                  if (response.errors.securityCode) {
                    console.log('Security code invalid.');
                  }
                  if (response.errors.number) {
                    console.log('Gift card number invalid or missing.');
                  }
                  if (response.errors.pin) {
                    console.log('Pin invalid or missing.');
                  }
                  if (response.errors.bankAccountHolder) {
                    console.log('Bank account holder invalid.');
                  }
                  if (response.errors.bankAccountNumber) {
                    console.log('Bank account number invalid.');
                  }
                  if (response.errors.routingNumber) {
                    console.log('Routing number invalid.');
                  }
                } else if ('request_timeout' == response.status) {
                  console.log(
                    'Session update failed with request timeout: ' +
                      response.errors.message
                  );
                } else if ('system_error' == response.status) {
                  console.log(
                    'Session update failed with system error: ' +
                      response.errors.message
                  );
                }
              } else {
                console.log('Session update failed: ' + response);
              }
            },
            visaCheckout: function (response) {
              // HANDLE VISA CHECKOUT RESPONSE
            },
            amexExpressCheckout: function (response) {
              // HANDLE AMEX EXPRESS CHECKOUT RESPONSE
            },
          },
          interaction: {
            displayControl: {
              formatCard: 'EMBOSSED',
              invalidFieldCharacters: 'REJECT',
            },
          },
          order: {
            amount: 10.0,
            currency: 'AUD',
          },
          wallets: {
            visaCheckout: {
              enabled: true,
              // Add Visa Checkout API specific attributes here
              countryCode: 'AU',
              displayName: 'Display name',
              locale: 'en_au',
              logoUrl: 'http://logo.logo',
              payment: {
                cardBrands: ['VISA'],
              },
              review: {
                buttonAction: 'Pay',
                message: 'Message',
              },
              shipping: {
                acceptedRegions: ['AU'],
                collectShipping: true,
              },
            },
            amexExpressCheckout: {
              enabled: true,
              // Add Amex Express Checkout API specific attributes here
              initTags: {
                theme: 'responsive',
                env: 'qa',
                disable_btn: 'false',
                button_color: 'light',
                client_id:
                  '<MSO Client Id from the Amex Express Checkout configuration page in Merchant Administration>',
              },
            },
          },
        });
      }
    );
  }

  ngOnInit(): void {
  }

  load(): void {}
}

付款-detail.component.html

<div>Please enter your payment details:</div>
<div>Card Number: <input type="text" id="card-number" class="input-field" value="5123450000000008" readonly></div>
<div>Expiry Month:<input type="text" id="expiry-month" class="input-field" value="05"></div>
<div>Expiry Year:<input type="text" id="expiry-year" class="input-field" value="21"></div>
<div>Security Code:<input type="text" id="security-code" class="input-field" value="1234" readonly></div>
<div><button id="payButton" onclick="pay();">Pay Now</button></div>

如果我从 $.PaymentSession.configure 中删除 $.,我将无法找到 PaymentSession。

更新

我按照 Maxine Lafarie 的建议使用了这段代码:

$.getScript( "your-script", function( data, textStatus, jqxhr ) {
  console.log( data ); // Data returned
  console.log( textStatus ); // Success
  console.log( jqxhr.status ); // 200
  console.log( "Load was performed." );
});

这是结果:

undefined payment-detail.component.ts:31 success payment-detail.component.ts:32 200 payment-detail.component.ts:33 Load was performed.

将 url 粘贴到浏览器我得到一个脚本:

您是否绑定记录了 $.getScript 的响应?

你可以这样做:

$.getScript( "your-script", function( data, textStatus, jqxhr ) {
  console.log( data ); // Data returned
  console.log( textStatus ); // Success
  console.log( jqxhr.status ); // 200
  console.log( "Load was performed." );
});

无论如何,我不知道您是在整个应用程序中使用 jQuery 还是只是为了 getScript 方法的“好处”,但我建议您避免混合使用Angular 和 jQ,因为 Angular 绝对可以做 jQuery 能做的所有事情。

如果您想以 Angular 方式加载第 3 方脚本,您可以 .

所以检查是否:

  • jQuery 被很好地导入 and/or 在你调用它时加载到你的组件中
  • 调用 $.getScript 方法后,您有一些成功日志
  • 导入第 3 方脚本的 Angular 方法有效(可能更好)

编辑:

自从您导入脚本后,您就可以这样调用全局 属性: $.PaymentSession.configure 但我认为你必须这样称呼它:PaymentSession.configure