第三方金流串接 – 訂單開立和功能

更新於 發佈於 閱讀時間約 17 分鐘

※ 訂單開立流程

raw-image
  1. 前端資料驗證。
  2. 將商品的數量寫入(預扣)→ id。

※ 從前端需要傳入的資料:

商品ID、商品數量、使用哪個payment provider、 使用哪個payment way

※ 訂單Model(模型):model –––> order.ts

raw-image


定義了一個類別 OrderModel,所需要的訂單(Order)資料格式:

  • 用於處理與訂單相關的資料和操作。
import { Base } from "./base";
//PaymentProvider 介面:定義支付平台的結構。
export enum PaymentProvider {
ECPAY = "ECPAY",
PAYPAL = "PAYPAL"
}
//PaymentWay 介面:定義支付方式的結構。
export enum PaymentWay {
CVS = 'CVS',
PAYPAL = 'PAYPAL',
}
//OrderStatus 介面:定義訂單狀態的結構。
export enum OrderStatus {
WAITING = 'WAITING',
SUCCESS = 'SUCCESS',
FAILED = 'FAILED',
CANCEL = 'CANCEL',
}
//訂單的詳細資料
export interface OrderContent {
productId: number;
amount: number;
price: number;
}

//Order 介面定義了訂單的結構
export interface Order {
id: string;
total: number;
createdAt: Date;
updatedAt: Date;
paymentProvider: PaymentProvider;
paymentWay: PaymentWay;
status: OrderStatus;
contents: OrderContent[];
}



1.匯入模組

import { Knex } from "knex";
import { Base, IBase } from "./base";

程式碼解說:

  • 從 knex 模組匯入 Knex 類型,用於資料庫操作。
  • 因為order需要繼承base,所以從本地模組 ./base 匯入 Base 類別和 IBase 介面。

2.定義 Order 介面

export interface Order {
id: string;
total: number;
createdAt: Date;
updatedAt: Date;
paymentProvider: PaymentProvider;
paymentWay: PaymentWay;
status: OrderStatus;
contents: OrderContent[];
}

程式碼解說:

  • export interface Order {}:定義了一個 Order 介面,描述訂單的結構。
  • 定義訂單的結構,包括 ID、總金額、創建時間、更新時間、支付提供者、支付方式、訂單狀態和訂單內容。

3.用枚舉來定義支付平台、支付方式和訂單狀態的結構

export enum PaymentProvider {
ECPAY = 'ECPAY',
PAYPAL = 'PAYPAL',
}
export enum PaymentWay {
CVS = 'CVS',
PAYPAL = 'PAYPAL',
}
export enum OrderStatus {
WAITING = 'WAITING',
SUCCESS = 'SUCCESS',
FAILED = 'FAILED',
CANCEL = 'CANCEL',
}

程式碼解說:

  • 定義了三個枚舉:PaymentProvider、PaymentWay 和 OrderStatus,用於表示支付平台、支付方式和訂單狀態。

4.定義 OrderContent 介面:訂單的詳細資料

export interface OrderContent {
productId: number;
amount: number;
price: number;
}

程式碼解說:

  • 定義訂單內容,包括產品 ID、數量和價格。


5.定義訂單模型,對應到資料庫中的 orders 表:

export class OrderModel extends Base<Order> implements IBase<Order> {
tableName = 'orders';
//屬性會自動對應到資料庫表中的相應欄位
schema = {
id: 'id',
total: 'total',
createdAt: 'created_at',
updatedAt: 'updated_at',
paymentProvider: 'payment_provider',
paymentWay: 'payment_way',
status: 'status',
contents: 'contents',
}
}

程式碼解說:

  • 定義了一個類別 OrderModel,它繼承了 Base<Order>。這表示 OrderModel 類別將具有 Base 類別的所有屬性和方法,但它特別針對 Order 這個型別進行操作。
  • tableName 屬性:指定資料表名稱為 orders。
  • schema 屬性:定義資料表欄位與模型屬性的映射關係。

6.靜態方法 createModel:專門用來生成模型(model)

static createModel =
({ knexSql, tableName }: { knexSql: Knex; tableName?: string })
=> {
return new OrderModel({ knexSql, tableName });
}

程式碼解說:

  • 定義一個靜態方法 createModel,用於創建 OrderModel 實例。

7.建構函數

constructor({ knexSql, tableName }: { knexSql: Knex, tableName?: string }) {
super({ knexSql, tableName });
}

程式碼解說:

  • 初始化 OrderModel 實例:在創建 OrderModel 實例時,可以傳入資料庫連接(knexSql)和可選的資料表名稱(tableName),這些參數將被傳遞給基類的建構函數,以正確初始化基類的狀態。
  • 確保類別的繼承和初始化:通過調用 super,確保基類的建構函數被正確調用,使得 OrderModel 繼承了基類的屬性和方法。

8.定義一個有基礎(Base)介面中所有功能的訂單(Order)

export interface IOrderModel extends IBase<Order> {
create(orderData: Omit<Order, "id"> & { id?: string },
trx?: Knex.Transaction): Promise<Order | null>; }

程式碼解說:

  • 使用 export 導出這個介面,使其可以在其他模組中使用。
  • 使用 interface 關鍵字定義介面 IOrderModel。
  • extends IBase<Order> 表示 IOrderModel 繼承自 IBase<Order> 介面。
  • 這意味著 IOrderModel 會擁有 IBase<Order> 定義的所有屬性和方法。
  • 參數:
    • orderData:這是一個物件,類型是 Omit<Order, "id"> & { id?: string },表示 orderData 具有 Order 的所有屬性(除了 id),並且有一個可選的 id 屬性。
    • trx:這是一個可選的參數,類型是 Knex.Transaction,用於資料庫交易處理。
  • 返回值:這個方法返回一個 Promise,表示這個方法是非同步的。Promise 的值可以是 Order 或 null

9.IBase<Order>改成 IOrderModel:

export class OrderModel extends Base<Order> implements IOrderModel



※ 建立ORDER的CONTROLLER,處理訂單相關的 API 請求:controller –––> orderController.ts

raw-image

1.匯入模組:

import { IOrderModel, OrderContent, PaymentProvider, PaymentWay } from "@/model/order";
import { IProductModel } from "@/model/product";
import { NextFunction, Request, Response } from "express";
import { Knex } from "knex";

程式碼解說:

  • 從 @/model/order 和 @/model/product 匯入相關的介面和類型。
  • 從 express 匯入 NextFunction, Request 和 Response。
  • 從 knex 匯入 Knex,用於資料庫操作。

2.定義 IOrder功能:

export interface IOrderController {
createOrder(
req: Request<any, any, CreateOrderRequestParams, any>,
res: Response,
next: NextFunction
): void;
updateAmount(
req: Request<any, any, any, any>,
res: Response,
next: NextFunction
): void;
}

程式碼解說:

  1. createOrder 方法:
    • 用途:用於創建新訂單。
    • 參數:req:型別為 Request<any, any, CreateOrderRequestParams, any>,包含 CreateOrderRequestParams 介面定義的參數(支付提供者、支付方式和訂單內容)。
    • res:型別為 Response,用來回應客戶端請求。
    • next:型別為 NextFunction,用來調用下一個中介軟體。
  2. updateAmount 方法:
    • 用途:用於更新訂單中的商品數量。
    • 參數:req:型別為 Request<any, any, any, any>,沒有具體定義請求體的結構。
    • res:型別為 Response,用來回應客戶端請求。
    • next:型別為 NextFunction,用來調用下一個中介軟體。

3.定義 OrderController 類別:

export class OrderController implements IOrderController {
knexSql: Knex;
orderModel: IOrderModel;
productModel: IProductModel;
constructor({ knexSql, orderModel, productModel }: {
knexSql: Knex;
orderModel: IOrderModel;
productModel: IProductModel;
}) {
this.knexSql = knexSql;
this.orderModel = orderModel;
this.productModel = productModel
}
}

程式碼解說:

  • 繼承 IOrderController:這意味著 OrderController 必須實現 IOrderController 介面定義的方法。
  • 成員變數宣告在類別 OrderController 中,宣告了三個成員變數 knexSqlorderModelproductModel。這些變數的類型分別是 KnexIOrderModelIProductModel,用來存儲傳遞給建構子函數的值。
  • 建構函數接受 knexSql, orderModel 和 productModel 作為參數,並將它們賦值給類別的屬性。
  • 將傳入的 knexSql 資料庫連接實例賦值給 this.knexSql 屬性。
  • 將傳入的 orderModel 實例賦值給 this.orderModel 屬性,這樣可以在 OrderController 中方便地操作訂單資料。
  • 將傳入的 productModel 實例賦值給 this.productModel 屬性,確保可以在 OrderController 中操作與訂單相關的產品資料。


4.定義了一個 createOrder 的公開方法,:

public createOrder: IOrderController["createOrder"] = (req, res, _next) => {

let { paymentProvider, paymentWay, contents } = req.body
}

程式碼解說:

  • public createOrder:這表示這個方法是公開的,能夠從類別外部存取。
  • IOrderController["createOrder"]:這表示這個方法的型別必須符合 IOrderController 介面中的 createOrder 方法的定義。
  • (req, res, _next) => {}:這是一個箭頭函數,接受三個參數 req(請求物件)、res(回應物件)、_next(下一個中介軟體函數,這裡沒用到,所以用 _ 前綴表示未使用)。
  • 使用解構賦值,從請求物件 req.body 中提取 paymentProviderpaymentWaycontents 這三個屬性。
  • paymentProvider:支付提供者,例如 PayPal、信用卡等。
  • paymentWay:支付方式,例如在線支付、貨到付款等。
  • contents:訂單的內容,通常是包含商品詳細資訊的數據。


5.定義 CreateOrderRequestParams 介面:請求物件 req.body 的結構

interface CreateOrderRequestParams {
paymentProvider: PaymentProvider;
paymentWay: PaymentWay;
contents: OrderContent[];
}

程式碼解說:

  • 定義了 CreateOrderRequestParams 介面,用來描述創建訂單請求的參數結構。
  • paymentProvider:枚舉類型 PaymentProvider,指明支付提供者,如 ECPAY 或 PAYPAL。
  • paymentWay:枚舉類型 PaymentWay,指明支付方式,如 CVS 或 PAYPAL。
  • contents:一個 OrderContent 陣列,描述訂單中的每個產品項目。

6.修改IOrder功能:

createOrder(req: Request<any, any, CreateOrderRequestParams, any>, res: Response, next: NextFunction): void;








留言
avatar-img
留言分享你的想法!
avatar-img
奧莉薇走在成為後端工程師之路上
18會員
141內容數
全端網頁開發專業知識分享
2025/04/26
※ 場景: 即時聊天應用: 設計一個支持多房間功能的即時聊天平台,像 WhatsApp、LINE或Facebook Messenger,提供文字、語音、視訊聊天功能,方便管理群組聊天。 功能亮點:加入特別功能,例如可加入多房間功能、使用者名單、表情符號支持、文件分享或訊息已讀未讀狀態。 展示
2025/04/26
※ 場景: 即時聊天應用: 設計一個支持多房間功能的即時聊天平台,像 WhatsApp、LINE或Facebook Messenger,提供文字、語音、視訊聊天功能,方便管理群組聊天。 功能亮點:加入特別功能,例如可加入多房間功能、使用者名單、表情符號支持、文件分享或訊息已讀未讀狀態。 展示
2025/04/26
※ 先建立基本的express後端服務: 1.建立新資料夾:Socket mkdir socket 2.進入資料夾:Socket cd ​bsocket 3. 安裝 Experss 到專案中 npm init -y //初始化專案,建立 package.json 檔 npm insta
Thumbnail
2025/04/26
※ 先建立基本的express後端服務: 1.建立新資料夾:Socket mkdir socket 2.進入資料夾:Socket cd ​bsocket 3. 安裝 Experss 到專案中 npm init -y //初始化專案,建立 package.json 檔 npm insta
Thumbnail
2025/04/10
※ 什麼是 Socket.io:一個基於傳統 WebSocket API 之上的框架。 ※ Socket.io常用功能: Custom Events:在 Socket.io 中,開發者可以創建自己的事件來處理特定的功能或需求。 Rooms:分組的功能。每個連接的用戶(或稱為 socket)可
Thumbnail
2025/04/10
※ 什麼是 Socket.io:一個基於傳統 WebSocket API 之上的框架。 ※ Socket.io常用功能: Custom Events:在 Socket.io 中,開發者可以創建自己的事件來處理特定的功能或需求。 Rooms:分組的功能。每個連接的用戶(或稱為 socket)可
Thumbnail
看更多
你可能也想看
Thumbnail
TOMICA第一波推出吉伊卡哇聯名小車車的時候馬上就被搶購一空,一直很扼腕當時沒有趕緊入手。前陣子閒來無事逛蝦皮,突然發現幾家商場都又開始重新上架,價格也都回到正常水準,估計是官方又再補了一批貨,想都沒想就立刻下單! 同文也跟大家分享近期蝦皮購物紀錄、好用推薦、蝦皮分潤計畫的聯盟行銷!
Thumbnail
TOMICA第一波推出吉伊卡哇聯名小車車的時候馬上就被搶購一空,一直很扼腕當時沒有趕緊入手。前陣子閒來無事逛蝦皮,突然發現幾家商場都又開始重新上架,價格也都回到正常水準,估計是官方又再補了一批貨,想都沒想就立刻下單! 同文也跟大家分享近期蝦皮購物紀錄、好用推薦、蝦皮分潤計畫的聯盟行銷!
Thumbnail
每年4月、5月都是最多稅要繳的月份,當然大部份的人都是有機會繳到「綜合所得稅」,只是相當相當多人還不知道,原來繳給政府的稅!可以透過一些有活動的銀行信用卡或電子支付來繳,從繳費中賺一點點小確幸!就是賺個1%~2%大家也是很開心的,因為你們把沒回饋變成有回饋,就是用卡的最高境界 所得稅線上申報
Thumbnail
每年4月、5月都是最多稅要繳的月份,當然大部份的人都是有機會繳到「綜合所得稅」,只是相當相當多人還不知道,原來繳給政府的稅!可以透過一些有活動的銀行信用卡或電子支付來繳,從繳費中賺一點點小確幸!就是賺個1%~2%大家也是很開心的,因為你們把沒回饋變成有回饋,就是用卡的最高境界 所得稅線上申報
Thumbnail
※ 在orderController.ts檔案中定義createOrder:  public createOrder: IOrderController['createOrder'] = (req, res, _next) => { let { paymentProvider, paym
Thumbnail
※ 在orderController.ts檔案中定義createOrder:  public createOrder: IOrderController['createOrder'] = (req, res, _next) => { let { paymentProvider, paym
Thumbnail
Wassup ! This is 就這樣栽進Web 3.0 & Economic 的路易斯。 秉持著Simple Is good,盡我所能讓讀者們看了就能理解。 這次就要來介紹: 『如果你是企業主,該如何設置 Stripe USDC?』
Thumbnail
Wassup ! This is 就這樣栽進Web 3.0 & Economic 的路易斯。 秉持著Simple Is good,盡我所能讓讀者們看了就能理解。 這次就要來介紹: 『如果你是企業主,該如何設置 Stripe USDC?』
Thumbnail
簡介如何使用Solana Pay API整合商店頁面進行支付
Thumbnail
簡介如何使用Solana Pay API整合商店頁面進行支付
Thumbnail
前篇提要,介面功能主要會被分以下三個區塊介紹: 1. 左側設定區 (Part I) 2. 中間及右側預算設定區(Part II) 3. 帳戶內錢錢進出記錄功能 (Part III) 此篇終於來到尾聲,要介紹帳戶內錢錢建出紀錄功能。
Thumbnail
前篇提要,介面功能主要會被分以下三個區塊介紹: 1. 左側設定區 (Part I) 2. 中間及右側預算設定區(Part II) 3. 帳戶內錢錢進出記錄功能 (Part III) 此篇終於來到尾聲,要介紹帳戶內錢錢建出紀錄功能。
Thumbnail
導讀 開始美股分享之前,由於股票數目眾多,先了解行業背景作起步應該會更易。 第一個我十分喜歡的行業就是支付(Payment),龍頭公司如VISA、MasterCard地位穩固,而且涉及的科技日新月異,在跟蹤支付行業的同時,亦更易了解跟其他行業的連動,例如電商跟支付密不可分。支付行業技術廣範,入場門檻
Thumbnail
導讀 開始美股分享之前,由於股票數目眾多,先了解行業背景作起步應該會更易。 第一個我十分喜歡的行業就是支付(Payment),龍頭公司如VISA、MasterCard地位穩固,而且涉及的科技日新月異,在跟蹤支付行業的同時,亦更易了解跟其他行業的連動,例如電商跟支付密不可分。支付行業技術廣範,入場門檻
Thumbnail
介紹了這麼多Solidity的函數和方法,今天來寫一個簡單的錢包,順便介紹一下payable。
Thumbnail
介紹了這麼多Solidity的函數和方法,今天來寫一個簡單的錢包,順便介紹一下payable。
Thumbnail
本文延續上一次的程式碼,並增加錢包餘額查詢以及轉帳功能,完成後將會嘗試轉帳,若測試與查詢的結果都沒有問題的話,恭喜你完成一個可以被轉帳交易的加密貨幣,今年過年就靠它讓你在親戚朋友之間成為被眾人討論的紅人了!
Thumbnail
本文延續上一次的程式碼,並增加錢包餘額查詢以及轉帳功能,完成後將會嘗試轉帳,若測試與查詢的結果都沒有問題的話,恭喜你完成一個可以被轉帳交易的加密貨幣,今年過年就靠它讓你在親戚朋友之間成為被眾人討論的紅人了!
Thumbnail
繼上篇文章STEP 1 註冊&身份驗證圖文教學,此篇文章將介紹幣安的入金方法 幣安目前提供五種入金方式: 1. 錢包轉帳 (從其他交易所錢包將貨幣轉入) 2. 信用卡買幣 3. C2C 交易 4. 第三方平台 5. 美金電匯 錢包轉帳 (從其他交易所錢包將貨幣轉入)
Thumbnail
繼上篇文章STEP 1 註冊&身份驗證圖文教學,此篇文章將介紹幣安的入金方法 幣安目前提供五種入金方式: 1. 錢包轉帳 (從其他交易所錢包將貨幣轉入) 2. 信用卡買幣 3. C2C 交易 4. 第三方平台 5. 美金電匯 錢包轉帳 (從其他交易所錢包將貨幣轉入)
Thumbnail
1.首先要先年滿20歲,準備好雙證件(身分證+健保卡/駕照/護照) 點擊:https://lihi1.cc/iESSc 點擊右上角的註冊/登入 (就可以開始加入我們囉~!) 按下 去註冊 依照畫面順序填下來,接著進入審核程序 在9:00-23:00註冊,我們會在30分鐘內馬
Thumbnail
1.首先要先年滿20歲,準備好雙證件(身分證+健保卡/駕照/護照) 點擊:https://lihi1.cc/iESSc 點擊右上角的註冊/登入 (就可以開始加入我們囉~!) 按下 去註冊 依照畫面順序填下來,接著進入審核程序 在9:00-23:00註冊,我們會在30分鐘內馬
追蹤感興趣的內容從 Google News 追蹤更多 vocus 的最新精選內容追蹤 Google News