pesafy 0.3.13 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.cts CHANGED
@@ -733,6 +733,161 @@ interface DynamicQRResponse {
733
733
  QRCode: string;
734
734
  }
735
735
 
736
+ /**
737
+ * Tax Remittance types
738
+ *
739
+ * API: POST /mpesa/b2b/v1/remittax
740
+ *
741
+ * Daraja request body (from official Tax Remittance docs):
742
+ * {
743
+ * "Initiator": "TaxPayer",
744
+ * "SecurityCredential": "...",
745
+ * "CommandID": "PayTaxToKRA",
746
+ * "SenderIdentifierType": "4",
747
+ * "RecieverIdentifierType":"4",
748
+ * "Amount": "239",
749
+ * "PartyA": "888880",
750
+ * "PartyB": "572572",
751
+ * "AccountReference": "353353",
752
+ * "Remarks": "OK",
753
+ * "QueueTimeOutURL": "https://mydomain.com/b2b/remittax/queue/",
754
+ * "ResultURL": "https://mydomain.com/b2b/remittax/result/"
755
+ * }
756
+ *
757
+ * NOTE: This is an ASYNCHRONOUS API.
758
+ * The synchronous response only confirms Safaricom received the request.
759
+ * The actual result arrives later via POST to your ResultURL.
760
+ *
761
+ * Ref: Tax Remittance — Daraja Developer Portal
762
+ */
763
+ interface TaxRemittanceRequest {
764
+ /**
765
+ * The transaction amount to remit to KRA.
766
+ * Must be a whole number ≥ 1.
767
+ * Daraja field: Amount
768
+ */
769
+ amount: number;
770
+ /**
771
+ * Your own M-PESA business shortcode from which the money is deducted.
772
+ * Daraja field: PartyA
773
+ */
774
+ partyA: string;
775
+ /**
776
+ * The KRA account to which money is credited.
777
+ * For Tax Remittance, only "572572" is allowed.
778
+ * Defaults to "572572" if omitted.
779
+ * Daraja field: PartyB
780
+ */
781
+ partyB?: string;
782
+ /**
783
+ * The Payment Registration Number (PRN) issued by KRA.
784
+ * This is your tax declaration reference from KRA.
785
+ * Daraja field: AccountReference
786
+ */
787
+ accountReference: string;
788
+ /**
789
+ * URL where Safaricom POSTs the final result after processing.
790
+ * Must be publicly accessible.
791
+ * Daraja field: ResultURL
792
+ */
793
+ resultUrl: string;
794
+ /**
795
+ * URL Safaricom calls when the request times out in the queue.
796
+ * Must be publicly accessible.
797
+ * Daraja field: QueueTimeOutURL
798
+ */
799
+ queueTimeOutUrl: string;
800
+ /**
801
+ * Optional remarks (up to 100 characters).
802
+ * Daraja field: Remarks
803
+ */
804
+ remarks?: string;
805
+ }
806
+ interface TaxRemittanceResponse {
807
+ /** Unique request identifier assigned by Daraja upon successful submission */
808
+ OriginatorConversationID: string;
809
+ /** Unique request identifier assigned by M-Pesa upon successful submission */
810
+ ConversationID: string;
811
+ /** "0" = successful submission */
812
+ ResponseCode: string;
813
+ /** Human-readable status description */
814
+ ResponseDescription: string;
815
+ }
816
+ interface TaxRemittanceResultParameter {
817
+ Key: "DebitAccountBalance" | "Amount" | "DebitPartyAffectedAccountBalance" | "TransCompletedTime" | "DebitPartyCharges" | "ReceiverPartyPublicName" | "Currency" | "InitiatorAccountCurrentBalance" | string;
818
+ Value: string | number;
819
+ }
820
+ interface TaxRemittanceResult {
821
+ Result: {
822
+ /** Usually "0" */
823
+ ResultType: string;
824
+ /** 0 = success */
825
+ ResultCode: number;
826
+ /** Human-readable result description */
827
+ ResultDesc: string;
828
+ OriginatorConversationID: string;
829
+ ConversationID: string;
830
+ TransactionID: string;
831
+ ResultParameters?: {
832
+ ResultParameter: TaxRemittanceResultParameter[];
833
+ };
834
+ ReferenceData?: {
835
+ ReferenceItem: {
836
+ Key: string;
837
+ Value: string;
838
+ } | Array<{
839
+ Key: string;
840
+ Value: string;
841
+ }>;
842
+ };
843
+ };
844
+ }
845
+ interface TaxRemittanceErrorResponse {
846
+ /** Unique request ID assigned by the API gateway */
847
+ requestId: string;
848
+ /** Daraja error code, e.g. "404.001.04" */
849
+ errorCode: string;
850
+ /** Human-readable error message, e.g. "Invalid Access Token" */
851
+ errorMessage: string;
852
+ }
853
+
854
+ /**
855
+ * Tax Remittance — remits tax to Kenya Revenue Authority (KRA) via M-PESA.
856
+ *
857
+ * API: POST /mpesa/b2b/v1/remittax
858
+ *
859
+ * This is ASYNCHRONOUS. The synchronous response only acknowledges receipt.
860
+ * Final results arrive via POST to your ResultURL.
861
+ *
862
+ * Prerequisites (from Daraja docs):
863
+ * - Prior integration with KRA for tax declaration.
864
+ * - A valid Payment Registration Number (PRN) from KRA.
865
+ * - Initiator with the "Tax Remittance ORG API" role on the M-PESA org portal.
866
+ * - SecurityCredential encrypted with the correct environment certificate.
867
+ *
868
+ * Fixed Daraja field values for this API:
869
+ * CommandID: "PayTaxToKRA" (always)
870
+ * SenderIdentifierType: "4" (always — Organisation ShortCode)
871
+ * RecieverIdentifierType: "4" (always — Organisation ShortCode)
872
+ * PartyB: "572572" (always — KRA's M-PESA shortcode)
873
+ */
874
+
875
+ /** KRA's M-PESA shortcode — the only allowed PartyB for tax remittance */
876
+ declare const KRA_SHORTCODE = "572572";
877
+ /** The only CommandID accepted by the Tax Remittance API */
878
+ declare const TAX_COMMAND_ID = "PayTaxToKRA";
879
+ /**
880
+ * Remits tax to Kenya Revenue Authority (KRA) via M-PESA.
881
+ *
882
+ * @param baseUrl - Daraja base URL (sandbox or production)
883
+ * @param accessToken - Valid OAuth bearer token
884
+ * @param securityCredential - RSA-encrypted initiator password (base64)
885
+ * @param initiatorName - M-PESA org portal API operator username
886
+ * @param request - Tax remittance parameters
887
+ * @returns - Daraja acknowledgement response
888
+ */
889
+ declare function remitTax(baseUrl: string, accessToken: string, securityCredential: string, initiatorName: string, request: TaxRemittanceRequest): Promise<TaxRemittanceResponse>;
890
+
736
891
  /**
737
892
  * Core M-Pesa / Daraja API types
738
893
  */
@@ -894,6 +1049,38 @@ declare class Mpesa {
894
1049
  * });
895
1050
  */
896
1051
  simulateC2B(request: C2BSimulateRequest): Promise<C2BSimulateResponse>;
1052
+ /**
1053
+ * Tax Remittance — remits tax to Kenya Revenue Authority (KRA) via M-PESA.
1054
+ *
1055
+ * Requires:
1056
+ * - initiatorName in config
1057
+ * - initiatorPassword + certificate (or pre-computed securityCredential)
1058
+ *
1059
+ * This is ASYNCHRONOUS. The synchronous response only confirms receipt.
1060
+ * Final details are POSTed to your resultUrl.
1061
+ *
1062
+ * Prerequisites (from Daraja docs):
1063
+ * - Prior integration with KRA for tax declaration.
1064
+ * - A Payment Registration Number (PRN) from KRA.
1065
+ * - Initiator with "Tax Remittance ORG API" role on M-PESA org portal.
1066
+ *
1067
+ * Fixed values (set automatically — do NOT override unless Safaricom changes them):
1068
+ * CommandID: "PayTaxToKRA"
1069
+ * SenderIdentifierType: "4"
1070
+ * RecieverIdentifierType: "4"
1071
+ * PartyB: "572572" (KRA shortcode)
1072
+ *
1073
+ * @example
1074
+ * await mpesa.remitTax({
1075
+ * amount: 5000,
1076
+ * partyA: "888880",
1077
+ * accountReference: "PRN1234XN", // PRN from KRA
1078
+ * resultUrl: "https://yourdomain.com/mpesa/tax/result",
1079
+ * queueTimeOutUrl: "https://yourdomain.com/mpesa/tax/timeout",
1080
+ * remarks: "Monthly PAYE remittance",
1081
+ * });
1082
+ */
1083
+ remitTax(request: TaxRemittanceRequest): Promise<TaxRemittanceResponse>;
897
1084
  /** Force the cached OAuth token to be refreshed on the next API call */
898
1085
  clearTokenCache(): void;
899
1086
  }
@@ -1075,4 +1262,4 @@ declare class PesafyError extends Error {
1075
1262
  /** Convenience factory — identical API to `new PesafyError(...)` */
1076
1263
  declare function createError(options: PesafyErrorOptions): PesafyError;
1077
1264
 
1078
- export { type C2BApiVersion, type C2BCommandID, type C2BConfirmationAck, type C2BConfirmationPayload, type C2BRegisterUrlRequest, type C2BRegisterUrlResponse, type C2BResponseType, type C2BSimulateRequest, type C2BSimulateResponse, type C2BValidationPayload, type C2BValidationResponse, type C2BValidationResultCode, DARAJA_BASE_URLS, type DynamicQRRequest, type DynamicQRResponse, type Environment, type ErrorCode, Mpesa, type MpesaConfig, PesafyError, type PesafyErrorOptions, type QRTransactionCode, type RetryOptions, type RetryResult, SAFARICOM_IPS, type StkCallbackFailure, type StkCallbackInner, type StkCallbackMetadataItem, type StkCallbackSuccess, type StkPushCallback, type StkPushRequest, type StkPushResponse, type StkPushWebhook, type StkQueryRequest, type StkQueryResponse, type TransactionStatusRequest, type TransactionStatusResponse, type TransactionStatusResult, type TransactionStatusResultParameter, type TransactionType, type WebhookEvent, type WebhookEventType, type WebhookHandlerOptions, type WebhookHandlerResult, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, retryWithBackoff, simulateC2B, verifyWebhookIP };
1265
+ export { type C2BApiVersion, type C2BCommandID, type C2BConfirmationAck, type C2BConfirmationPayload, type C2BRegisterUrlRequest, type C2BRegisterUrlResponse, type C2BResponseType, type C2BSimulateRequest, type C2BSimulateResponse, type C2BValidationPayload, type C2BValidationResponse, type C2BValidationResultCode, DARAJA_BASE_URLS, type DynamicQRRequest, type DynamicQRResponse, type Environment, type ErrorCode, KRA_SHORTCODE, Mpesa, type MpesaConfig, PesafyError, type PesafyErrorOptions, type QRTransactionCode, type RetryOptions, type RetryResult, SAFARICOM_IPS, type StkCallbackFailure, type StkCallbackInner, type StkCallbackMetadataItem, type StkCallbackSuccess, type StkPushCallback, type StkPushRequest, type StkPushResponse, type StkPushWebhook, type StkQueryRequest, type StkQueryResponse, TAX_COMMAND_ID, type TaxRemittanceErrorResponse, type TaxRemittanceRequest, type TaxRemittanceResponse, type TaxRemittanceResult, type TaxRemittanceResultParameter, type TransactionStatusRequest, type TransactionStatusResponse, type TransactionStatusResult, type TransactionStatusResultParameter, type TransactionType, type WebhookEvent, type WebhookEventType, type WebhookHandlerOptions, type WebhookHandlerResult, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, remitTax, retryWithBackoff, simulateC2B, verifyWebhookIP };
package/dist/index.d.ts CHANGED
@@ -733,6 +733,161 @@ interface DynamicQRResponse {
733
733
  QRCode: string;
734
734
  }
735
735
 
736
+ /**
737
+ * Tax Remittance types
738
+ *
739
+ * API: POST /mpesa/b2b/v1/remittax
740
+ *
741
+ * Daraja request body (from official Tax Remittance docs):
742
+ * {
743
+ * "Initiator": "TaxPayer",
744
+ * "SecurityCredential": "...",
745
+ * "CommandID": "PayTaxToKRA",
746
+ * "SenderIdentifierType": "4",
747
+ * "RecieverIdentifierType":"4",
748
+ * "Amount": "239",
749
+ * "PartyA": "888880",
750
+ * "PartyB": "572572",
751
+ * "AccountReference": "353353",
752
+ * "Remarks": "OK",
753
+ * "QueueTimeOutURL": "https://mydomain.com/b2b/remittax/queue/",
754
+ * "ResultURL": "https://mydomain.com/b2b/remittax/result/"
755
+ * }
756
+ *
757
+ * NOTE: This is an ASYNCHRONOUS API.
758
+ * The synchronous response only confirms Safaricom received the request.
759
+ * The actual result arrives later via POST to your ResultURL.
760
+ *
761
+ * Ref: Tax Remittance — Daraja Developer Portal
762
+ */
763
+ interface TaxRemittanceRequest {
764
+ /**
765
+ * The transaction amount to remit to KRA.
766
+ * Must be a whole number ≥ 1.
767
+ * Daraja field: Amount
768
+ */
769
+ amount: number;
770
+ /**
771
+ * Your own M-PESA business shortcode from which the money is deducted.
772
+ * Daraja field: PartyA
773
+ */
774
+ partyA: string;
775
+ /**
776
+ * The KRA account to which money is credited.
777
+ * For Tax Remittance, only "572572" is allowed.
778
+ * Defaults to "572572" if omitted.
779
+ * Daraja field: PartyB
780
+ */
781
+ partyB?: string;
782
+ /**
783
+ * The Payment Registration Number (PRN) issued by KRA.
784
+ * This is your tax declaration reference from KRA.
785
+ * Daraja field: AccountReference
786
+ */
787
+ accountReference: string;
788
+ /**
789
+ * URL where Safaricom POSTs the final result after processing.
790
+ * Must be publicly accessible.
791
+ * Daraja field: ResultURL
792
+ */
793
+ resultUrl: string;
794
+ /**
795
+ * URL Safaricom calls when the request times out in the queue.
796
+ * Must be publicly accessible.
797
+ * Daraja field: QueueTimeOutURL
798
+ */
799
+ queueTimeOutUrl: string;
800
+ /**
801
+ * Optional remarks (up to 100 characters).
802
+ * Daraja field: Remarks
803
+ */
804
+ remarks?: string;
805
+ }
806
+ interface TaxRemittanceResponse {
807
+ /** Unique request identifier assigned by Daraja upon successful submission */
808
+ OriginatorConversationID: string;
809
+ /** Unique request identifier assigned by M-Pesa upon successful submission */
810
+ ConversationID: string;
811
+ /** "0" = successful submission */
812
+ ResponseCode: string;
813
+ /** Human-readable status description */
814
+ ResponseDescription: string;
815
+ }
816
+ interface TaxRemittanceResultParameter {
817
+ Key: "DebitAccountBalance" | "Amount" | "DebitPartyAffectedAccountBalance" | "TransCompletedTime" | "DebitPartyCharges" | "ReceiverPartyPublicName" | "Currency" | "InitiatorAccountCurrentBalance" | string;
818
+ Value: string | number;
819
+ }
820
+ interface TaxRemittanceResult {
821
+ Result: {
822
+ /** Usually "0" */
823
+ ResultType: string;
824
+ /** 0 = success */
825
+ ResultCode: number;
826
+ /** Human-readable result description */
827
+ ResultDesc: string;
828
+ OriginatorConversationID: string;
829
+ ConversationID: string;
830
+ TransactionID: string;
831
+ ResultParameters?: {
832
+ ResultParameter: TaxRemittanceResultParameter[];
833
+ };
834
+ ReferenceData?: {
835
+ ReferenceItem: {
836
+ Key: string;
837
+ Value: string;
838
+ } | Array<{
839
+ Key: string;
840
+ Value: string;
841
+ }>;
842
+ };
843
+ };
844
+ }
845
+ interface TaxRemittanceErrorResponse {
846
+ /** Unique request ID assigned by the API gateway */
847
+ requestId: string;
848
+ /** Daraja error code, e.g. "404.001.04" */
849
+ errorCode: string;
850
+ /** Human-readable error message, e.g. "Invalid Access Token" */
851
+ errorMessage: string;
852
+ }
853
+
854
+ /**
855
+ * Tax Remittance — remits tax to Kenya Revenue Authority (KRA) via M-PESA.
856
+ *
857
+ * API: POST /mpesa/b2b/v1/remittax
858
+ *
859
+ * This is ASYNCHRONOUS. The synchronous response only acknowledges receipt.
860
+ * Final results arrive via POST to your ResultURL.
861
+ *
862
+ * Prerequisites (from Daraja docs):
863
+ * - Prior integration with KRA for tax declaration.
864
+ * - A valid Payment Registration Number (PRN) from KRA.
865
+ * - Initiator with the "Tax Remittance ORG API" role on the M-PESA org portal.
866
+ * - SecurityCredential encrypted with the correct environment certificate.
867
+ *
868
+ * Fixed Daraja field values for this API:
869
+ * CommandID: "PayTaxToKRA" (always)
870
+ * SenderIdentifierType: "4" (always — Organisation ShortCode)
871
+ * RecieverIdentifierType: "4" (always — Organisation ShortCode)
872
+ * PartyB: "572572" (always — KRA's M-PESA shortcode)
873
+ */
874
+
875
+ /** KRA's M-PESA shortcode — the only allowed PartyB for tax remittance */
876
+ declare const KRA_SHORTCODE = "572572";
877
+ /** The only CommandID accepted by the Tax Remittance API */
878
+ declare const TAX_COMMAND_ID = "PayTaxToKRA";
879
+ /**
880
+ * Remits tax to Kenya Revenue Authority (KRA) via M-PESA.
881
+ *
882
+ * @param baseUrl - Daraja base URL (sandbox or production)
883
+ * @param accessToken - Valid OAuth bearer token
884
+ * @param securityCredential - RSA-encrypted initiator password (base64)
885
+ * @param initiatorName - M-PESA org portal API operator username
886
+ * @param request - Tax remittance parameters
887
+ * @returns - Daraja acknowledgement response
888
+ */
889
+ declare function remitTax(baseUrl: string, accessToken: string, securityCredential: string, initiatorName: string, request: TaxRemittanceRequest): Promise<TaxRemittanceResponse>;
890
+
736
891
  /**
737
892
  * Core M-Pesa / Daraja API types
738
893
  */
@@ -894,6 +1049,38 @@ declare class Mpesa {
894
1049
  * });
895
1050
  */
896
1051
  simulateC2B(request: C2BSimulateRequest): Promise<C2BSimulateResponse>;
1052
+ /**
1053
+ * Tax Remittance — remits tax to Kenya Revenue Authority (KRA) via M-PESA.
1054
+ *
1055
+ * Requires:
1056
+ * - initiatorName in config
1057
+ * - initiatorPassword + certificate (or pre-computed securityCredential)
1058
+ *
1059
+ * This is ASYNCHRONOUS. The synchronous response only confirms receipt.
1060
+ * Final details are POSTed to your resultUrl.
1061
+ *
1062
+ * Prerequisites (from Daraja docs):
1063
+ * - Prior integration with KRA for tax declaration.
1064
+ * - A Payment Registration Number (PRN) from KRA.
1065
+ * - Initiator with "Tax Remittance ORG API" role on M-PESA org portal.
1066
+ *
1067
+ * Fixed values (set automatically — do NOT override unless Safaricom changes them):
1068
+ * CommandID: "PayTaxToKRA"
1069
+ * SenderIdentifierType: "4"
1070
+ * RecieverIdentifierType: "4"
1071
+ * PartyB: "572572" (KRA shortcode)
1072
+ *
1073
+ * @example
1074
+ * await mpesa.remitTax({
1075
+ * amount: 5000,
1076
+ * partyA: "888880",
1077
+ * accountReference: "PRN1234XN", // PRN from KRA
1078
+ * resultUrl: "https://yourdomain.com/mpesa/tax/result",
1079
+ * queueTimeOutUrl: "https://yourdomain.com/mpesa/tax/timeout",
1080
+ * remarks: "Monthly PAYE remittance",
1081
+ * });
1082
+ */
1083
+ remitTax(request: TaxRemittanceRequest): Promise<TaxRemittanceResponse>;
897
1084
  /** Force the cached OAuth token to be refreshed on the next API call */
898
1085
  clearTokenCache(): void;
899
1086
  }
@@ -1075,4 +1262,4 @@ declare class PesafyError extends Error {
1075
1262
  /** Convenience factory — identical API to `new PesafyError(...)` */
1076
1263
  declare function createError(options: PesafyErrorOptions): PesafyError;
1077
1264
 
1078
- export { type C2BApiVersion, type C2BCommandID, type C2BConfirmationAck, type C2BConfirmationPayload, type C2BRegisterUrlRequest, type C2BRegisterUrlResponse, type C2BResponseType, type C2BSimulateRequest, type C2BSimulateResponse, type C2BValidationPayload, type C2BValidationResponse, type C2BValidationResultCode, DARAJA_BASE_URLS, type DynamicQRRequest, type DynamicQRResponse, type Environment, type ErrorCode, Mpesa, type MpesaConfig, PesafyError, type PesafyErrorOptions, type QRTransactionCode, type RetryOptions, type RetryResult, SAFARICOM_IPS, type StkCallbackFailure, type StkCallbackInner, type StkCallbackMetadataItem, type StkCallbackSuccess, type StkPushCallback, type StkPushRequest, type StkPushResponse, type StkPushWebhook, type StkQueryRequest, type StkQueryResponse, type TransactionStatusRequest, type TransactionStatusResponse, type TransactionStatusResult, type TransactionStatusResultParameter, type TransactionType, type WebhookEvent, type WebhookEventType, type WebhookHandlerOptions, type WebhookHandlerResult, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, retryWithBackoff, simulateC2B, verifyWebhookIP };
1265
+ export { type C2BApiVersion, type C2BCommandID, type C2BConfirmationAck, type C2BConfirmationPayload, type C2BRegisterUrlRequest, type C2BRegisterUrlResponse, type C2BResponseType, type C2BSimulateRequest, type C2BSimulateResponse, type C2BValidationPayload, type C2BValidationResponse, type C2BValidationResultCode, DARAJA_BASE_URLS, type DynamicQRRequest, type DynamicQRResponse, type Environment, type ErrorCode, KRA_SHORTCODE, Mpesa, type MpesaConfig, PesafyError, type PesafyErrorOptions, type QRTransactionCode, type RetryOptions, type RetryResult, SAFARICOM_IPS, type StkCallbackFailure, type StkCallbackInner, type StkCallbackMetadataItem, type StkCallbackSuccess, type StkPushCallback, type StkPushRequest, type StkPushResponse, type StkPushWebhook, type StkQueryRequest, type StkQueryResponse, TAX_COMMAND_ID, type TaxRemittanceErrorResponse, type TaxRemittanceRequest, type TaxRemittanceResponse, type TaxRemittanceResult, type TaxRemittanceResultParameter, type TransactionStatusRequest, type TransactionStatusResponse, type TransactionStatusResult, type TransactionStatusResultParameter, type TransactionType, type WebhookEvent, type WebhookEventType, type WebhookHandlerOptions, type WebhookHandlerResult, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, remitTax, retryWithBackoff, simulateC2B, verifyWebhookIP };
package/dist/index.js CHANGED
@@ -559,6 +559,66 @@ function getCallbackValue(callback, name) {
559
559
  return inner.CallbackMetadata.Item.find((i) => i.Name === name)?.Value;
560
560
  }
561
561
 
562
+ // src/mpesa/tax-remittance/remit-tax.ts
563
+ var KRA_SHORTCODE = "572572";
564
+ var TAX_COMMAND_ID = "PayTaxToKRA";
565
+ async function remitTax(baseUrl, accessToken, securityCredential, initiatorName, request) {
566
+ const amount = Math.round(request.amount);
567
+ if (!Number.isFinite(amount) || amount < 1) {
568
+ throw createError({
569
+ code: "VALIDATION_ERROR",
570
+ message: `amount must be a whole number \u2265 1 (got ${request.amount} which rounds to ${amount}).`
571
+ });
572
+ }
573
+ if (!request.partyA) {
574
+ throw createError({
575
+ code: "VALIDATION_ERROR",
576
+ message: "partyA is required \u2014 your M-PESA business shortcode from which tax is deducted."
577
+ });
578
+ }
579
+ if (!request.accountReference?.trim()) {
580
+ throw createError({
581
+ code: "VALIDATION_ERROR",
582
+ message: "accountReference is required \u2014 the Payment Registration Number (PRN) issued by KRA."
583
+ });
584
+ }
585
+ if (!request.resultUrl?.trim()) {
586
+ throw createError({
587
+ code: "VALIDATION_ERROR",
588
+ message: "resultUrl is required \u2014 Safaricom POSTs the tax remittance result here."
589
+ });
590
+ }
591
+ if (!request.queueTimeOutUrl?.trim()) {
592
+ throw createError({
593
+ code: "VALIDATION_ERROR",
594
+ message: "queueTimeOutUrl is required \u2014 Safaricom calls this on request timeout."
595
+ });
596
+ }
597
+ const payload = {
598
+ Initiator: initiatorName,
599
+ SecurityCredential: securityCredential,
600
+ CommandID: TAX_COMMAND_ID,
601
+ SenderIdentifierType: "4",
602
+ RecieverIdentifierType: "4",
603
+ Amount: String(amount),
604
+ PartyA: String(request.partyA),
605
+ PartyB: request.partyB ?? KRA_SHORTCODE,
606
+ AccountReference: request.accountReference,
607
+ Remarks: request.remarks ?? "Tax Remittance",
608
+ QueueTimeOutURL: request.queueTimeOutUrl,
609
+ ResultURL: request.resultUrl
610
+ };
611
+ const { data } = await httpRequest(
612
+ `${baseUrl}/mpesa/b2b/v1/remittax`,
613
+ {
614
+ method: "POST",
615
+ headers: { Authorization: `Bearer ${accessToken}` },
616
+ body: payload
617
+ }
618
+ );
619
+ return data;
620
+ }
621
+
562
622
  // src/mpesa/transaction-status/query.ts
563
623
  async function queryTransactionStatus(baseUrl, token, securityCredential, initiator, request) {
564
624
  if (!request.transactionId) {
@@ -848,6 +908,52 @@ var Mpesa = class {
848
908
  const token = await this.getToken();
849
909
  return simulateC2B(this.baseUrl, token, request);
850
910
  }
911
+ // ── Tax Remittance ────────────────────────────────────────────────────────
912
+ /**
913
+ * Tax Remittance — remits tax to Kenya Revenue Authority (KRA) via M-PESA.
914
+ *
915
+ * Requires:
916
+ * - initiatorName in config
917
+ * - initiatorPassword + certificate (or pre-computed securityCredential)
918
+ *
919
+ * This is ASYNCHRONOUS. The synchronous response only confirms receipt.
920
+ * Final details are POSTed to your resultUrl.
921
+ *
922
+ * Prerequisites (from Daraja docs):
923
+ * - Prior integration with KRA for tax declaration.
924
+ * - A Payment Registration Number (PRN) from KRA.
925
+ * - Initiator with "Tax Remittance ORG API" role on M-PESA org portal.
926
+ *
927
+ * Fixed values (set automatically — do NOT override unless Safaricom changes them):
928
+ * CommandID: "PayTaxToKRA"
929
+ * SenderIdentifierType: "4"
930
+ * RecieverIdentifierType: "4"
931
+ * PartyB: "572572" (KRA shortcode)
932
+ *
933
+ * @example
934
+ * await mpesa.remitTax({
935
+ * amount: 5000,
936
+ * partyA: "888880",
937
+ * accountReference: "PRN1234XN", // PRN from KRA
938
+ * resultUrl: "https://yourdomain.com/mpesa/tax/result",
939
+ * queueTimeOutUrl: "https://yourdomain.com/mpesa/tax/timeout",
940
+ * remarks: "Monthly PAYE remittance",
941
+ * });
942
+ */
943
+ async remitTax(request) {
944
+ const initiator = this.config.initiatorName ?? "";
945
+ if (!initiator) {
946
+ throw new PesafyError({
947
+ code: "VALIDATION_ERROR",
948
+ message: "initiatorName is required for Tax Remittance"
949
+ });
950
+ }
951
+ const [token, securityCred] = await Promise.all([
952
+ this.getToken(),
953
+ this.buildSecurityCredential()
954
+ ]);
955
+ return remitTax(this.baseUrl, token, securityCred, initiator, request);
956
+ }
851
957
  /** Force the cached OAuth token to be refreshed on the next API call */
852
958
  clearTokenCache() {
853
959
  this.tokenManager.clearCache();
@@ -972,6 +1078,6 @@ function isSuccessfulCallback(webhook) {
972
1078
  return webhook.Body?.stkCallback?.ResultCode === 0;
973
1079
  }
974
1080
 
975
- export { DARAJA_BASE_URLS, Mpesa, PesafyError, SAFARICOM_IPS, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, retryWithBackoff, simulateC2B, verifyWebhookIP };
1081
+ export { DARAJA_BASE_URLS, KRA_SHORTCODE, Mpesa, PesafyError, SAFARICOM_IPS, TAX_COMMAND_ID, acceptC2BValidation, acknowledgeC2BConfirmation, createError, encryptSecurityCredential, extractAmount, extractPhoneNumber, extractTransactionId, formatSafaricomPhone as formatPhoneNumber, getC2BAccountRef, getC2BAmount, getC2BCustomerName, getC2BTransactionId, getCallbackValue, getTimestamp, handleWebhook, isBuyGoodsPayment, isC2BPayload, isPaybillPayment, isStkCallbackSuccess, isSuccessfulCallback, parseStkPushWebhook, registerC2BUrls, rejectC2BValidation, remitTax, retryWithBackoff, simulateC2B, verifyWebhookIP };
976
1082
  //# sourceMappingURL=index.js.map
977
1083
  //# sourceMappingURL=index.js.map