Last active
May 6, 2021 17:04
-
-
Save christianwach/ac8e8460c7f488a9a31f30a2c74eefc6 to your computer and use it in GitHub Desktop.
Order API & Payment API mismatches
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Using CiviCRM Sample Data (where "financial_type_id=5" is a Taxable Financial Type and "financial_type_id=2" is not) | |
Call Order.create with these params: | |
[params] => Array | |
( | |
[contact_id] => 206 | |
[financial_type_id] => 5 <----- Taxable Financial Type. | |
[payment_instrument_id] => 4 | |
[trxn_id] => WooCommerce Order - 1859 | |
[invoice_id] => 1859_woocommerce | |
[receive_date] => 2021-05-05 23:24:02 | |
[contribution_status_id] => Pending | |
[total_amount] => 109.69 <----- Total amount includes tax. | |
[tax_amount] => 9.69 <----- Taxable part of total. | |
[source] => Shop | |
[campaign_id] => 3 | |
[note] => Fundraiser Dinner Ticket x 1, Student Membership x 1 | |
[line_items] => Array | |
( | |
[20] => Array | |
( | |
[line_item] => Array | |
( | |
[0] => Array | |
( | |
[price_field_id] => 1 | |
[unit_price] => 50.00 | |
[qty] => 1 | |
[line_total] => 50.00 | |
[tax_amount] => 9.69 | |
[label] => Fundraiser Dinner Ticket | |
[financial_type_id] => 5 <----- Taxable Financial Type. | |
) | |
) | |
) | |
[21] => Array | |
( | |
[params] => Array | |
( | |
[membership_type_id] => 2 | |
[source] => Shop | |
[contact_id] => 206 | |
[skipStatusCal] => 1 | |
[status_id] => Pending | |
) | |
[line_item] => Array | |
( | |
[0] => Array | |
( | |
[price_field_id] => 1 | |
[unit_price] => 50.00 | |
[qty] => 1 | |
[line_total] => 50.00 | |
[tax_amount] => 0.00 | |
[label] => Student Membership | |
[financial_type_id] => 2 <----- Non-taxable Financial Type. | |
[entity_table] => civicrm_membership | |
[membership_type_id] => 2 | |
) | |
) | |
) | |
) | |
) | |
The result returned by the API call looks good: | |
[result] => Array | |
( | |
[is_error] => 0 | |
[version] => 3 | |
[count] => 1 | |
[id] => 104 | |
[values] => Array | |
( | |
[104] => Array | |
( | |
[id] => 104 | |
[contact_id] => 206 | |
[financial_type_id] => 5 <----- Taxable Financial Type. | |
[contribution_page_id] => | |
[payment_instrument_id] => 4 | |
[receive_date] => 20210505232402 | |
[non_deductible_amount] => | |
[total_amount] => 109.69 <----- Okay. | |
[fee_amount] => 0 | |
[net_amount] => 109.69 <----- Okay. | |
[trxn_id] => WooCommerce Order - 1859 | |
[invoice_id] => 1859_woocommerce | |
[invoice_number] => INV_104 | |
[currency] => USD | |
[cancel_date] => | |
[cancel_reason] => | |
[receipt_date] => | |
[thankyou_date] => | |
[source] => Shop | |
[amount_level] => | |
[contribution_recur_id] => | |
[is_test] => | |
[is_pay_later] => | |
[contribution_status_id] => 2 | |
[address_id] => | |
[check_number] => | |
[campaign_id] => 3 | |
[creditnote_id] => | |
[tax_amount] => 9.69 <----- Okay. | |
[revenue_recognition_date] => | |
[is_template] => | |
[contribution_type_id] => 5 | |
) | |
) | |
) | |
Now do a trivial update to the Contribution, e.g. the Source: | |
$result = civicrm_api3('Contribution', 'create', [ | |
'financial_type_id' => 5, // Happens to be a Taxable Financial Type but need not be. | |
'contact_id' => 206, | |
'id' => 103, | |
'source' => "Something", | |
]); | |
Retrieve Contribution via API Explorer. | |
The "total_amount" and "net_amount" have been recalculated. | |
(The "tax_amount" and "financial_type_id" are missing in API3 but not API4.) | |
{ | |
"is_error": 0, | |
"version": 3, | |
"count": 1, | |
"id": 104, | |
"values": [ | |
{ | |
"contact_id": "206", | |
"contribution_id": "104", | |
"currency": "USD", | |
"contribution_recur_id": "", | |
"contribution_status_id": "2", | |
"contribution_campaign_id": "1", | |
"payment_instrument_id": "4", | |
"receive_date": "2021-05-05 23:24:02", | |
"non_deductible_amount": "0.00", | |
"total_amount": "119.38", <----- This seems to have been recalculated. Where is "tax_amount"? | |
"fee_amount": "0.00", | |
"net_amount": "100.00", <----- This seems to have been recalculated. | |
"trxn_id": "WooCommerce Order - 1859", | |
"invoice_id": "1859_woocommerce", | |
"invoice_number": "INV_104", | |
"contribution_cancel_date": "", | |
"cancel_reason": "", | |
"receipt_date": "", | |
"thankyou_date": "", | |
"contribution_source": "Shop", | |
"amount_level": "", | |
"is_test": "0", | |
"is_pay_later": "0", | |
"contribution_check_number": "", | |
"civicrm_value_donor_information_3_id": "12", | |
"custom_6": "", | |
"custom_5": "", | |
"contribution_recur_status": "Pending", | |
"payment_instrument": "Check", | |
"contribution_status": "Pending", | |
"check_number": "", | |
"instrument_id": "4", | |
"cancel_date": "", | |
"id": "104" | |
} | |
] | |
} | |
Doesn't seem right. So, what's raw data? | |
mysql> SELECT `financial_type_id`, `total_amount`, `fee_amount`, `net_amount`, `tax_amount` FROM `civicrm_contribution` WHERE id = '104'; | |
+-------------------+--------------+------------+------------+------------+ | |
| financial_type_id | total_amount | fee_amount | net_amount | tax_amount | | |
+-------------------+--------------+------------+------------+------------+ | |
| 5 | 119.38 | 0.00 | 100.00 | 19.38 | | |
+-------------------+--------------+------------+------------+------------+ | |
Yup, confirms recalculation. | |
Now check the Line Items via the API Explorer. | |
The non-taxable Line Item now has (total Tax x 2) added. | |
{ | |
"is_error": 0, | |
"version": 3, | |
"count": 2, | |
"values": [ | |
{ | |
"id": "107", | |
"entity_table": "civicrm_membership", | |
"entity_id": "34", | |
"contribution_id": "104", | |
"price_field_id": "1", | |
"label": "Fundraiser Dinner Ticket", | |
"qty": "1.00", | |
"unit_price": "50.00", | |
"line_total": "50.00", <----- Okay. | |
"financial_type_id": "5", <----- Taxable Financial Type. | |
"non_deductible_amount": "0.00", | |
"tax_amount": "9.69", <----- Okay. | |
"contribution_type_id": "5" | |
}, | |
{ | |
"id": "108", | |
"entity_table": "civicrm_membership", | |
"entity_id": "34", | |
"contribution_id": "104", | |
"price_field_id": "1", | |
"label": "Student Membership", | |
"qty": "1.00", | |
"unit_price": "50.00", | |
"line_total": "50.00", <----- Okay. | |
"financial_type_id": "2", <----- Non-taxable Financial Type. | |
"non_deductible_amount": "0.00", | |
"tax_amount": "19.38", <----- Uh oh. | |
"contribution_type_id": "2" | |
} | |
] | |
} | |
Error confirmed in database: | |
mysql> select `financial_type_id`, `line_total`, `unit_price`, `tax_amount` FROM civicrm_line_item WHERE contribution_id = '104'; | |
+-------------------+------------+------------+------------+ | |
| financial_type_id | line_total | unit_price | tax_amount | | |
+-------------------+------------+------------+------------+ | |
| 5 | 50.00 | 50.00 | 9.69 | | |
| 2 | 50.00 | 50.00 | 19.38 | | |
+-------------------+------------+------------+------------+ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Using CiviCRM Sample Data (where "financial_type_id=5" is a Taxable Financial Type and "financial_type_id=2" is not) | |
Call Order.create with these params: | |
[params] => Array | |
( | |
[contact_id] => 208 | |
[financial_type_id] => 2 <----- Non-taxable Financial Type. | |
[payment_instrument_id] => 4 | |
[trxn_id] => WooCommerce Order - 1861 | |
[invoice_id] => 1861_woocommerce | |
[receive_date] => 2021-05-06 08:48:53 | |
[contribution_status_id] => Pending | |
[total_amount] => 109.69 <----- Total amount includes tax. | |
[tax_amount] => 9.69 <----- Taxable part of total. | |
[source] => Shop | |
[campaign_id] => 3 | |
[note] => Fundraiser Dinner Ticket x 1, Student Membership x 1 | |
[line_items] => Array | |
( | |
[26] => Array | |
( | |
[line_item] => Array | |
( | |
[0] => Array | |
( | |
[price_field_id] => 1 | |
[unit_price] => 50.00 | |
[qty] => 1 | |
[line_total] => 50.00 | |
[tax_amount] => 9.69 | |
[label] => Fundraiser Dinner Ticket | |
[financial_type_id] => 5 <----- Taxable Financial Type. | |
) | |
) | |
) | |
[27] => Array | |
( | |
[params] => Array | |
( | |
[membership_type_id] => 2 | |
[source] => Shop | |
[contact_id] => 208 | |
[skipStatusCal] => 1 | |
[status_id] => Pending | |
) | |
[line_item] => Array | |
( | |
[0] => Array | |
( | |
[price_field_id] => 1 | |
[unit_price] => 50.00 | |
[qty] => 1 | |
[line_total] => 50.00 | |
[tax_amount] => 0.00 | |
[label] => Student Membership | |
[financial_type_id] => 2 <----- Non-taxable Financial Type. | |
[entity_table] => civicrm_membership | |
[membership_type_id] => 2 | |
) | |
) | |
) | |
) | |
) | |
The result returned by the API call looks good: | |
[result] => Array | |
( | |
[is_error] => 0 | |
[version] => 3 | |
[count] => 1 | |
[id] => 106 | |
[values] => Array | |
( | |
[106] => Array | |
( | |
[id] => 106 | |
[contact_id] => 208 | |
[financial_type_id] => 2 <----- Non-taxable Financial Type. | |
[contribution_page_id] => | |
[payment_instrument_id] => 4 | |
[receive_date] => 20210506084853 | |
[non_deductible_amount] => | |
[total_amount] => 109.69 <----- Okay. | |
[fee_amount] => 0 | |
[net_amount] => 109.69 <----- Okay. | |
[trxn_id] => WooCommerce Order - 1861 | |
[invoice_id] => 1861_woocommerce | |
[invoice_number] => INV_106 | |
[currency] => USD | |
[cancel_date] => | |
[cancel_reason] => | |
[receipt_date] => | |
[thankyou_date] => | |
[source] => Shop | |
[amount_level] => | |
[contribution_recur_id] => | |
[is_test] => | |
[is_pay_later] => | |
[contribution_status_id] => 2 | |
[address_id] => | |
[check_number] => | |
[campaign_id] => 3 | |
[creditnote_id] => | |
[tax_amount] => 9.69 <----- Okay. | |
[revenue_recognition_date] => | |
[is_template] => | |
[contribution_type_id] => 2 | |
) | |
) | |
) | |
Now do a trivial update to the Contribution, e.g. the Source: | |
$result = civicrm_api3('Contribution', 'create', [ | |
'financial_type_id' => 2, // Happens to be a Non-taxable Financial Type but need not be. | |
'contact_id' => 206, | |
'id' => 103, | |
'source' => "Something", | |
]); | |
Retrieve Contribution via API Explorer. | |
The "total_amount" and "net_amount" have been recalculated to exclude the Tax. | |
(The "tax_amount" and "financial_type_id" are missing in API3 but not API4.) | |
{ | |
"is_error": 0, | |
"version": 3, | |
"count": 1, | |
"id": 106, | |
"values": [ | |
{ | |
"contact_id": "208", | |
"contribution_id": "106", | |
"currency": "USD", | |
"contribution_recur_id": "", | |
"contribution_status_id": "2", | |
"contribution_campaign_id": "1", | |
"payment_instrument_id": "4", | |
"receive_date": "2021-05-06 08:48:53", | |
"non_deductible_amount": "0.00", | |
"total_amount": "100.00", <----- This seems to have been recalculated. Where is "tax_amount"? | |
"fee_amount": "0.00", | |
"net_amount": "100.00", <----- This seems to have been recalculated. | |
"trxn_id": "WooCommerce Order - 1861", | |
"invoice_id": "1861_woocommerce", | |
"invoice_number": "INV_106", | |
"contribution_cancel_date": "", | |
"cancel_reason": "", | |
"receipt_date": "", | |
"thankyou_date": "", | |
"contribution_source": "Shop", | |
"amount_level": "", | |
"is_test": "0", | |
"is_pay_later": "0", | |
"contribution_check_number": "", | |
"civicrm_value_donor_information_3_id": "16", | |
"custom_6": "", | |
"custom_5": "", | |
"contribution_recur_status": "Pending", | |
"payment_instrument": "Check", | |
"contribution_status": "Pending", | |
"check_number": "", | |
"instrument_id": "4", | |
"cancel_date": "", | |
"id": "106" | |
} | |
] | |
} | |
Doesn't seem right. So, what's raw data? | |
mysql> SELECT `financial_type_id`, `total_amount`, `fee_amount`, `net_amount`, `tax_amount` FROM `civicrm_contribution` WHERE id = '106'; | |
+-------------------+--------------+------------+------------+------------+ | |
| financial_type_id | total_amount | fee_amount | net_amount | tax_amount | | |
+-------------------+--------------+------------+------------+------------+ | |
| 2 | 100.00 | 0.00 | 100.00 | NULL | | |
+-------------------+--------------+------------+------------+------------+ | |
Yup, confirms recalculation. | |
Now check the Line Items via the API Explorer: | |
{ | |
"is_error": 0, | |
"version": 3, | |
"count": 2, | |
"values": [ | |
{ | |
"id": "111", | |
"entity_table": "civicrm_membership", | |
"entity_id": "36", | |
"contribution_id": "106", | |
"price_field_id": "1", | |
"label": "Fundraiser Dinner Ticket", | |
"qty": "1.00", | |
"unit_price": "50.00", | |
"line_total": "50.00", <----- Okay. | |
"financial_type_id": "5", <----- Taxable Financial Type. | |
"non_deductible_amount": "0.00", | |
"tax_amount": "9.69", <----- Okay. | |
"contribution_type_id": "5" | |
}, | |
{ | |
"id": "112", | |
"entity_table": "civicrm_membership", | |
"entity_id": "36", | |
"contribution_id": "106", | |
"price_field_id": "1", | |
"label": "Student Membership", | |
"qty": "1.00", | |
"unit_price": "50.00", | |
"line_total": "50.00", <----- Okay. | |
"financial_type_id": "2", <----- Non-taxable Financial Type. | |
"non_deductible_amount": "0.00", | |
"tax_amount": "0.00", <----- Okay. | |
"contribution_type_id": "2" | |
} | |
] | |
} | |
Line Item data integrity confirmed: | |
mysql> select `financial_type_id`, `line_total`, `unit_price`, `tax_amount` FROM civicrm_line_item WHERE contribution_id = '106'; | |
+-------------------+------------+------------+------------+ | |
| financial_type_id | line_total | unit_price | tax_amount | | |
+-------------------+------------+------------+------------+ | |
| 5 | 50.00 | 50.00 | 9.69 | | |
| 2 | 50.00 | 50.00 | 0.00 | | |
+-------------------+------------+------------+------------+ |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment