前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >为woocommerce开发支付网关插件,对接支付通道

为woocommerce开发支付网关插件,对接支付通道

作者头像
IT不难
发布2024-08-11 09:03:51
1380
发布2024-08-11 09:03:51
举报
文章被收录于专栏:IT不难技术家园

前言

WooCommerce模板众多,可以选择出我们需要的模板,生态好,而且数千个钩子更加利于开发者开发。本文分享如何为woocommerce独立站开发第三方支付插件。

woocommerce
woocommerce

创建插件

因为WooCommerce有很多的钩子,所以我们在开发支付网关的时候,只需按照一个“框架”来开发就好,下面的是插件框架

代码语言:javascript
复制

具体代码

构造函数

代码语言:javascript
复制
public function __construct() {

  $this->id = 'kekc_cn'; // 支付网关插件ID,可以字符串,但是要唯一
  $this->icon = ''; // 将显示在结账页上你的支付网关图标。内容为URL
  $this->has_fields = true; // 你需要自定义支付网关字段就填true
  $this->method_title = 'kekc_cn Gateway';
  $this->method_description = 'Description of kekc_cn payment gateway'; // 显示在选项页上

  // 网关可以支持订阅、退款、保存支付方式。
  // 但在本教程中,我们从简单的支付开始
  $this->supports = array(
    'products'
  );

  // 所有选项字段的方法
  $this->init_form_fields();

  // 加载设置
  $this->init_settings();
  $this->title = $this->get_option( 'title' );
  $this->description = $this->get_option( 'description' );
  $this->enabled = $this->get_option( 'enabled' );
  $this->testmode = 'yes' === $this->get_option( 'testmode' );
  $this->private_key = $this->testmode ? $this->get_option( 'test_private_key' ) : $this->get_option( 'private_key' );
  $this->publishable_key = $this->testmode ? $this->get_option( 'test_publishable_key' ) : $this->get_option( 'publishable_key' );

  // 这个动作钩子保存上面的设置
  add_action( 'woocommerce_update_options_payment_gateways_' . $this->id, array( $this, 'process_admin_options' ) );

  // 我们需要自定义的JavaScript来获得token
  add_action( 'wp_enqueue_scripts', array( $this, 'payment_scripts' ) );
  
  // 你也可以在这里注册一个webhook
  // add_action( 'woocommerce_api_{webhook name}', array( $this, 'webhook' ) );
 }

添加管理配置字段

这个的话都需要把,比如开发易支付支付网关,就需要url,商户ID,商户token等,还需要"启用/禁用","标题","描述"和"测试模式"等设置项。

代码语言:javascript
复制
public function init_form_fields(){

  $this->form_fields = array(
    'enabled' => array(
      'title'       => 'Enable/Disable',
      'label'       => 'Enable kekc_cn Gateway',
      'type'        => 'checkbox',
      'description' => '',
      'default'     => 'no'
    ),
    'title' => array(
      'title'       => 'Title',
      'type'        => 'text',
      'description' => 'This controls the title which the user sees during checkout.',
      'default'     => 'Credit Card',
      'desc_tip'    => true,
    ),
    'description' => array(
      'title'       => 'Description',
      'type'        => 'textarea',
      'description' => 'This controls the description which the user sees during checkout.',
      'default'     => 'Pay with your credit card via our super-cool payment gateway.',
    ),
    'testmode' => array(
      'title'       => 'Test mode',
      'label'       => 'Enable Test Mode',
      'type'        => 'checkbox',
      'description' => 'Place the payment gateway in test mode using test API keys.',
      'default'     => 'yes',
      'desc_tip'    => true,
    ),
    'test_publishable_key' => array(
      'title'       => 'Test Publishable Key',
      'type'        => 'text'
    ),
    'test_private_key' => array(
      'title'       => 'Test Private Key',
      'type'        => 'password',
    ),
    'publishable_key' => array(
      'title'       => 'Live Publishable Key',
      'type'        => 'text'
    ),
    'private_key' => array(
      'title'       => 'Live Private Key',
      'type'        => 'password'
    )
  );
}

验证信息

为什么要验证信息呢?我们有的支付网关,可以先验证用户信息,比如你银行卡支付需要接收短信验证码之类的,来确认是用户本人操作,那就需要此步骤,反之,如微信支付、支付宝支付、易支付、PayPal等等,支付都在第三方处理,不在我们服务器,所以无需验证,你可以直接空着或者是删除这个验证类方法。

  1. 客户填写其卡数据并单击“购买”按钮。
  2. 我们使用WooCommerce中的事件延迟表单提交,并将带有卡数据的AJAX请求直接发送到我们的支付处理器,checkout_place_order
  3. 如果客户详细信息正常,处理器将返回一个令牌,我们将其添加到下面的表格中,
  4. 现在我们可以提交表格(当然在JS中),
  5. 我们使用PHP中的令牌通过支付处理器的API捕获付款。

PHP代码部分

代码语言:javascript
复制
public function payment_scripts() {

// 我们只需要在购物车/结账页面用JavaScript来处理一个token,看它是否正确?
if ( ! is_cart() && ! is_checkout() && ! isset( $_GET['pay_for_order'] ) ) {
  return;
}

// 如果我们的支付网关被禁用,我们就不需要js了
if ( 'no' === $this->enabled ) {
  return;
}

// 如果没有设置API密钥,就不需要js
if ( empty( $this->private_key ) || empty( $this->publishable_key ) ) {
  return;
}

// 除非你的网站处于测试模式,否则不要在没有SSL的情况下验证。
if ( ! $this->testmode && ! is_ssl() ) {
  return;
}

// 让我们假设这是我们的支付处理器的JavaScript,它能得到一个token
wp_enqueue_script( 'kekc_cn_js', 'https://www.kekc_cnpayments.com/api/token.js' );

// 这是在插件目录中的自定义JS,与token.js一起处理。
wp_register_script( 'woocommerce_kekc_cn', plugins_url( 'kekc_cn.js', __FILE__ ), array( 'jquery', 'kekc_cn_js' ) );

// 在大多数支付处理程序中,必须使用公共密钥来获得一个token
wp_localize_script( 'woocommerce_kekc_cn', 'kekc_cn_params', array(
  'publishableKey' => $this->publishable_key
) );

wp_enqueue_script( 'woocommerce_kekc_cn' );

}

JS代码部分

代码语言:javascript
复制
var successCallback = function(data) {

var checkout_form = $( 'form.woocommerce-checkout' );

// 添加一个隐藏的token提交框
// console.log(data)查看token
checkout_form.find('#kekc_cn_token').val(data.token);

// 禁止token Request
checkout_form.off( 'checkout_place_order', tokenRequest );

// 现在提交form表单
checkout_form.submit();

};

var errorCallback = function(data) {
  console.log(data);
};

var tokenRequest = function() {

// 这里将是一个支付网关函数,处理来自你的表单的所有卡片数据,也许它需要你的可发布API密钥,即kekc_cn_params.publishableKey,
// 并在成功时触发successCallback(),失败时触发errorCallback。
return false;
  
};

jQuery(function($){

var checkout_form = $( 'form.woocommerce-checkout' );
checkout_form.on( 'checkout_place_order', tokenRequest );

});

添加支付字段表单

代码语言:javascript
复制
public function payment_fields() {
 
// 在支付表单前添加一些信息
if ( $this->description ) {
  // 你可以说明测试模式,显示测试之类的。
  if ( $this->testmode ) {
    $this->description .= ' TEST MODE ENABLED. In test mode, you can use the card numbers listed in documentation.';
    $this->description  = trim( $this->description );
  }
  // 显示带有标签的描述等。
  echo wpautop( wp_kses_post( $this->description ) );
}
 
// 我将用echo()的形式,你也可以直接在HTML中写
echo '';
 
// 如果你想让你的自定义支付网关支持这个动作,请添加这个动作钩子
do_action( 'woocommerce_credit_card_form_start', $this->id );
 
// #ccNo, #expdate, #cvc自己改成自己的
echo 'Card Number *
  
  
  
    Expiry Date *
    
  
  
    Card Code (CVC) *
    
  
  ';
 
do_action( 'woocommerce_credit_card_form_end', $this->id );
 
echo '';
 
}
效果图
效果图

处理付款

验证字段

像名字这样的结帐字段应该更早验证,下面是一个例子。

代码语言:javascript
复制
public function validate_fields(){
 
  if( empty( $_POST[ 'billing_first_name' ]) ) {
    wc_add_notice(  'First name is required!', 'error' );
    return false;
  }
  return true;
 
}

变更订单状态

使用API获取付款并设置订单状态

代码语言:javascript
复制
public function process_payment( $order_id ) {
 
  global $woocommerce;
 
  // 根据订单id获取订单明细
  $order = wc_get_order( $order_id );
 
 
  /*
    * 带有参数的数组,用于API交互
   */
  $args = array(
 
    ...
 
  );
 
  /*
   * API交互可以用wp_remote_post()来构建
    */
   $response = wp_remote_post( '{payment processor endpoint}', $args );
 
 
   if( !is_wp_error( $response ) ) {
 
     $body = json_decode( $response['body'], true );
 
     // 它可能是不同的,这取决于你的支付处理程序
     if ( $body['response']['responseCode'] == 'APPROVED' ) {
 
      // 我们收到付款
      $order->payment_complete();
      $order->reduce_order_stock();
 
      // 给客户备注。
      $order->add_order_note( '您的订单已经支付了! 谢谢你!', true );
 
      // 空购物车
      $woocommerce->cart->empty_cart();
 
      // 重定向到感谢页面
      return array(
        'result' => 'success',
        'redirect' => $this->get_return_url( $order )
      );
 
     } else {
      wc_add_notice(  '请重试!', 'error' );
      return;
    }
 
  } else {
    wc_add_notice(  '连接失败。', 'error' );
    return;
  }
 
}
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2024年08月10日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 前言
  • 创建插件
  • 具体代码
    • 构造函数
      • 添加管理配置字段
        • 验证信息
          • 处理付款
            • 验证字段
            • 变更订单状态
        相关产品与服务
        短信
        腾讯云短信(Short Message Service,SMS)可为广大企业级用户提供稳定可靠,安全合规的短信触达服务。用户可快速接入,调用 API / SDK 或者通过控制台即可发送,支持发送验证码、通知类短信和营销短信。国内验证短信秒级触达,99%到达率;国际/港澳台短信覆盖全球200+国家/地区,全球多服务站点,稳定可靠。
        领券
        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档