Download the PHP package dennykuo/invoice-porter without Composer
On this page you can find all versions of the php package dennykuo/invoice-porter. It is possible to download/install these versions without Composer. Possible dependencies are resolved automatically.
Informations about the package invoice-porter
Invoice Porter — 藍新電子發票 PHP SDK
藍新(NewebPay/EZPay)電子發票 API 的 PHP SDK。覆蓋 EZP_INVI_1.2.2(2024/4/22)所有發票 / 折讓相關端點,以及 EZP_Track_1.0.0(2018/10/3)所有字軌管理端點,並以 type-safe 的 DTO + Enum 取代字串魔術值。
特色
- 發票 7 端點:開立、觸發開立、作廢、查詢、開立折讓、觸發/取消折讓、作廢折讓
- 字軌 3 端點:新增字軌、字軌資料管理、字軌資料查詢
- 18 支 backed Enum 取代字串魔術值
- AES-256-CBC 加解密、CheckCode 驗證皆獨立模組可測試
- 例外階層化:
Validation/Api/CheckCode/Transport - HTTP 層注入點完整,可用 Guzzle MockHandler 做 feature test
- PHPStan level 10、PHP-CS-Fixer(PSR-12 +
declare_strict_types)、PHP 8.1 / 8.2 / 8.3 CI
系統需求
- PHP 8.1+(內建
ext-openssl、ext-json) guzzlehttp/guzzle^7.5
安裝
設定
EzpayConfig 為唯一入口,全部欄位皆 readonly:
也可改從環境變數讀取:
EZPAY_ENVIRONMENT 接受 sandbox(預設)或 production。
或從 array 建構(Laravel config:cache 友善):
fromArray() 只接受 snake_case keys(對齊 Laravel config/*.php 慣例);unknown keys 會被忽略以保留使用者擴充自家欄位的空間(例如 'logging' => true)。注意 fromArray() 不會 fallback 讀環境變數 — 想用 env 請改用 fromEnv()。對 php artisan config:cache 後 getenv() 失效的情境,這是最直觀的解法。
快速開始
⚠️
merchantOrderNo規則(自 0.4.1 起在 SDK 層強制)— 藍新規格 Varchar(20),僅允許英文、數字、底線。常見的'ORD-20260504-001'含連字號(-)會被 SDK 直接拋EzpayValidationException,請改用底線_作分隔(例:'ORD_20260504_001')。完整欄位規格與 SDK 驗證對照見docs/ezpay-api-mapping.md。⚠️
printFlag自 0.5.0 起為必填 — 是否寄送紙本是業務語意決策,過去預設PrintFlag::No配合 B2C 又強制要求載具/捐贈碼,等於是讓最少參數呼叫的使用者直接掉坑。請依場景明確指定PrintFlag::Yes(寄紙本)或PrintFlag::No(不寄紙本,需配 carrier 或 loveCode)。
API 對照
| 中文 | 方法 | 端點 | Version |
|---|---|---|---|
| 開立發票 | issue() |
invoice_issue |
1.5 |
| 觸發開立發票 | touchIssue() |
invoice_touch_issue |
1.0 |
| 作廢發票 | invalid() |
invoice_invalid |
1.0 |
| 查詢發票 | search() / searchRedirectHtml() |
invoice_search |
1.3 |
| 開立後跳查詢頁 | publicQueryRedirectHtml() |
invoice_search(Redirect 模式) |
1.3 |
| 開立折讓 | issueAllowance() |
allowance_issue |
1.3 |
| 觸發/取消折讓 | touchAllowance() |
allowance_touch_issue |
1.0 |
| 作廢折讓 | invalidAllowance() |
allowanceInvalid |
1.0 |
字軌管理 API(EZP_Track_1.0.0)
藍新「電子發票字軌管理」屬會員(公司)層級 API,與發票 API 用不同的金鑰與參數包裝(envelope 第一欄為 CompanyID_ 而非 MerchantID_)。EzpayConfig 沿用同一個入口,nullable companyId / companyHashKey / companyHashIv 三欄需於使用字軌時提供。
| 中文 | 方法 | 端點 | Version |
|---|---|---|---|
| 新增字軌 | trackCreate() |
Api_number_management/createNumber |
1.0 |
| 字軌資料管理 | trackManage() |
Api_number_management/manageNumber |
1.0 |
| 字軌資料查詢 | trackSearch() |
Api_number_management/searchNumber |
1.0 |
字軌 API 詳細欄位、CheckCode 策略與錯誤碼對照請見
docs/ezpay-track-api-mapping.md。
使用範例
examples/01-issue.php … examples/08-search-redirect.php 已涵蓋全部端點。下列為各方法的最小呼叫片段,省略 use 行;類別都在 InvoicePorter\Ezpay\Requests\…、InvoicePorter\Ezpay\Enums\…、InvoicePorter\Ezpay\Requests\Items\…。
觸發開立 / 作廢 / 折讓系列
查詢發票
進階情境
B2B 發票(買方統編必填)
載具(手機條碼 / 自然人憑證 / 會員)
愛心捐贈碼
提醒 — B2C 且
PrintFlag::No(不索取紙本)時,藍新會要求carrierType + carrierNum或loveCode擇一;SDK 自 0.4.0 起會在new InvoiceIssueRequest(...)直接以EzpayValidationException提早攔下,省一輪藍新後端來回。自 0.5.0 起本檢查涵蓋所有 TaxType(Taxable/ZeroRate/Exempt/Mixed),並加入更多 cross-field invariants(載具與捐贈碼互斥、B2B 不可使用載具或捐贈碼、carrierType / carrierNum 必須成對提供)。完整規則見docs/ezpay-api-mapping.md。
延遲開立(Status=3)
之後可用 `touchIssue()` 提前觸發,或交給藍新到期自動開立。混合稅率(TaxType=9)
Response 通用方法
所有 Response 物件繼承 EzpayResponse,提供以下共用方法:
特定端點的回傳欄位請見 src/Ezpay/Responses/*.php,例如 InvoiceIssueResponse::invoiceNumber() / invoiceTransNo() / randomNum() / barcode() / qrcodeL() / qrcodeR() 等。
時間欄位除了既有 createTime(): ?string(原始字串)外,自 0.4.0 起亦提供原生型別版:
createTimeAt() 涵蓋 InvoiceIssueResponse / InvoiceSearchResponse / InvoiceInvalidResponse / AllowanceIssueResponse / AllowanceTouchIssueResponse;AllowanceInvalidResponse 對應為 invalidTimeAt()(與既有 invalidTime() 對齊)。皆使用 PHP date_default_timezone_get() 之預設時區,需要 Asia/Taipei 請呼叫端自行 ->setTimezone(new DateTimeZone('Asia/Taipei'));解析失敗或欄位缺則回 null(不丟例外)。
錯誤處理
所有錯誤都會丟 exception,請統一 try/catch:
| Exception | 情境 |
|---|---|
EzpayValidationException |
DTO 內欄位驗證失敗(發生於 constructor) |
EzpayApiException |
藍新回業務錯誤碼(例 KEY10002、INV10003) |
EzpayCheckCodeException |
CheckCode 驗證不通過或欄位不齊 |
EzpayTransportException |
HTTP 連線、5xx、JSON 解析失敗 |
所有 exception 皆繼承 EzpayException(abstract,繼承 RuntimeException),可一次 catch。
錯誤碼語意分群(0.4.1+)
藍新錯誤碼以前綴分群,呼叫端常見處理策略不同:
| Helper | 涵蓋前綴 / 碼 | 建議處理 |
|---|---|---|
isFieldFormatError() |
INV100xx / INV700xx |
引導使用者修正輸入;重試無意義 |
isAuthError() |
INV900xx / KEY100xx |
告警 ops 檢查 hashKey / hashIv 設定 |
isDuplicateOrderNo() |
NOR10001 / LIB10003 |
產生新訂單編號重試 |
errorCodePrefix() |
(任意,未匹配時回空字串) | 自行分群或記 log 用 |
CheckCode 驗證
文件附件二記載 5 欄參與 SHA256:InvoiceTransNo、MerchantID、MerchantOrderNo、RandomNum、TotalAmt。但藍新實際上對「作廢發票」「折讓系列」回應未必提供完整 5 欄,因此本 SDK 採取保守策略:
- 預設驗證:
invoice_issue、invoice_touch_issue、invoice_search - 作廢發票 (
invoice_invalid):使用者建構 Request 時若帶齊randomNum/invoiceTransNo/merchantOrderNo/totalAmount,才會驗 CheckCode - 折讓三組 (
allowance_*):預設不驗,可透過建構參數expectCheckCode: true明確開啟
查詢發票轉址
藍新 v1.2.2 為 DisplayFlag 提供兩種模式:
-
DisplayFlag::Redirect(=1):呼叫searchRedirectHtml()取回自動 submit 的 HTML 字串,使用者自行echo: DisplayFlag::ResultUrl(=2,v1.2.2 新增):呼叫search()走一般 API 流程,從 Response 取出查詢結果 URL:
開立後快速產生公開查詢頁轉址
很多時候要做的就是「issue 完發票後馬上跳到藍新公開查詢頁讓使用者看明細」,自 0.4.0 起 SDK 提供兩種 sugar 寫法(內部都會包成 SearchType::ByInvoiceNumber + DisplayFlag::Redirect 的 InvoiceSearchRequest 後委派給 searchRedirectHtml(),回傳自動 submit 的 form HTML — 藍新公開查詢頁採 form-post,非 GET URL):
InvoiceIssueResponse::toSearchRequest() 在缺 invoiceNumber / randomNum 時會丟 EzpayValidationException(藍新異常回應時才會發生)。
範例程式
請見 examples/ 目錄。使用前先:
測試
本機若以高於 composer.json
require.php最低版本(^8.1)的 PHP 跑cs-check,PHP-CS-Fixer 會在 stderr 印一行版本不符提醒,不影響結果且 exit code 為 0,可忽略。CI matrix 會在 PHP 8.1 / 8.2 / 8.3 / 8.4 各跑一次。
文件
CHANGELOG.md— 版本歷程CONTRIBUTING.md— 貢獻指南SECURITY.md— 安全回報政策docs/ezpay-api-mapping.md— 藍新 EZP_INVI_1.2.2 發票文件 vs SDK 對照表(升版用)docs/ezpay-track-api-mapping.md— 藍新 EZP_Track_1.0.0 字軌文件 vs SDK 對照表docs/extending.md— 擴充新廠商指南(給未來貢獻者)
Roadmap
目前實作藍新 EZPay 一家。namespace 採 InvoicePorter\<Vendor>\… 結構,未來歡迎以 PR 形式擴充其他電子發票服務商(綠界 ECPay、歐付寶 O'Pay、紅陽 Pay2Go 等)。新廠商擴充指南請見 docs/extending.md。
跨廠商錯誤可一次 catch 共用根 InvoicePorter\Exceptions\InvoiceException:
License
MIT.