Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[RFC] Support reporting #77

Open
nvandoorn opened this issue May 21, 2021 · 5 comments
Open

[RFC] Support reporting #77

nvandoorn opened this issue May 21, 2021 · 5 comments
Labels
needs-planning This issue needs to be broken into actionable issues and moved into a project RFC Request for comments

Comments

@nvandoorn
Copy link
Member

At this moment, this extension only calculates tax and does not report anything to TaxJar. This is a large feature that will require further decomposition.

@nvandoorn nvandoorn added this to the TaxJar Certification milestone May 21, 2021
@Noah-Silvera
Copy link
Member

Noah-Silvera commented Jun 23, 2021

After further discussion and research, we've landed on some acceptance requirements for how this will work.

According to the TaxJar documentation, we only need to push orders in certain cases.

While you can import orders at any time, we recommend importing an order once it’s been shipped and paid/invoiced. If an order is canceled, you can avoid having to delete the order from TaxJar if you wait until it’s been paid. There’s a couple ways you may want to do this:
If your platform has a completed_at date, only import orders that have been completed.
If your platform has the notion of an order status, ensure the order status is in a shipped, paid, or complete status before importing.

We should only push orders if all the following are true...
- SuperGood::SolidusTaxJar.taxable_order_check.call(order)
- order.complete?
- order.paid?

As long as an order has not been paid, we don't need to worry about pushing it to TaxJar, as no actual monetary transaction has been made yet sent - the client has not been charged yet. (We may want to confirm this with the TaxJar team - just to confirm it's ok that unpaid and unshipped orders on the system never get pushed to TaxJar).

In order for an order to be paid and shipped, "order_recalculated" has to be fired at least once. This means we only need to hook into refunds being created, and orders being recalcalculated, and not worry about the create_order hook used in #44 .

Remaining questions:

  1. What's the different between refunds and reimbursements? Which ones do we care about? How can we hook into solidus to report to TaxJar when they happen?
  2. What about store credit refunds?

cc: @nvandoorn

@Noah-Silvera
Copy link
Member

@Noah-Silvera
Copy link
Member

Noah-Silvera commented Jun 25, 2021

Investigated with @forkata and learned a little bit more about how refunds work, and had some more thoughts on how we need to handle them to correctly report them to TaxJar.

Some Background

We learned in #86 that refunds are actually a negative delta of the amounts refunded from the original order. An order will have at most two transactions associated with it - an order transaction, which represents all the positive payments made towards the order towards what items, and a refund transaction that represents the store-credit/credit card refunds given back to a customer.

Assumptions

  • TaxJar only needs an order/refund to be reported when a financial transaction is actually completed.
  • When creating a refund, the portion of the refund that was applied to shipping, sales tax, and the total amount needs to be accurate else the tax reporting will not be correct. (Note: this needs to be confirmed with Taxjar)

Scenarios (all of these refer to actual financial transactions happening, which is the event TaxJar cares about)

1. A user completes a payment for an order that doesn't exist in TaxJar

  • We call the "create transaction" endpoint with the sales tax, total amount, shipping, and line items

2. A user completes an additional payment for an order that does exist in TaxJar

  • We call the "update transaction" endpoint with the sales tax, total amount, shipping, and line items

3. A store issues a refund/store-credit for an order

The refund/store-credit is attached to a reimbursement

In this scenario, we can determine exactly the line items, shipping, and sales tax amounts from pure solidus

For example.....

  • Dig into the reimbursement and figure out the total cost + sales tax for each item.
  • The total amount of the refund/store-credit minus the the total cost is going to be the amount of shipping that was refunded.

The refund/store-credit is not attached to anything

In this scenario, we cannot trust the values of the Spree::Order in solidus to determine the amount, shipping, and sales tax amounts. Here's an example scenario that demonstrates why.

  1. An negative adjustment is applied at an order level. This adjustment affects the total amount, and could affect the total portion of the order that is sales tax, and shipping.
  2. A refund is issued for the adjustment amount. At this point, we can't calculate the "delta" that the refund applied to the sales tax, shipping, and total amount, as we don't know what those values were before the negative adjustment.

To deal with this problem, we can use the original TaxJar transaction to determine the delta.

  1. If a refund if not attached to a reimbursement....
  2. Pull the original taxjar transaction
  3. Determine the delta using the current values of the Spree::Order.
    • total amount refunded = taxjar transaction amount - current Spree::Order amount + shipping - sales tax
    • total amount of sales tax refunded = taxjar transaction sales tax - current order total sales tax
    • total amount of shipping refunded = taxjar transaction shipping - current order shipping
    • For each line item, do a comparision of the current Spree::LineItems with the line item in the taxjar transaction
      • If the Spree::LineItem no longer exists on the order, assume a full refund of the amount + sales tax
      • If the Spree::LineItem has had it's amount changed from the line item in taxjar, the delta is the amount refunded for the item
      • If the Spree::LineItem has had it's sales tax changed from the line item in taxjar, the delta is the sales tax refunded

This seems like the only way we could accurately send the correct amounts that have been refunded for shipping/individual line items/total order to TaxJar. This is important, as taxes can be calculated differently for each of those items, so we need to report the correct amounts to TaxJar.

cc: @jarednorman @nvandoorn does this sound like a reasonable approach for handling refunds, under the assumption we need to report accurate porportions for shipping/line-item-amounts/sales-tax?

Questions for TaxJar

  1. When creating a refund, does the portion of the refund that was applied to shipping, sales tax, and the line items need to be correct? Or could we just report a decrease in the total amount, and not pass the line items, and the portions of shipping, sales tax, and line items can be calculated on TaxJar's end, or by the customer? (note: this approach feels wrong... but it might be enough for now and we inform customers they need to sort refund portions on their own in TaxJar itself)

  2. Do store credits always act as a refund? To our current understanding, store credits are not taxable until they are used. That means for taxjars purposes, it's like the customer was issued a credit card refund. Is this true in all countries/states? Are their some cases where we should not report the issuing of store credits as a refund?

  3. Is it a correct assumption that TaxJar only needs to be aware of order changes when a financial transaction (payment or refund) is actually created? Our thought is that up until that point, the taxability of that order hasn't changed, because the amount paid has not changed.

@Noah-Silvera
Copy link
Member

Noah-Silvera commented Jul 9, 2021

We had a meeting with TaxJar, and got these questions answered.

  1. This is the way we should handle posting refunds.

    • When a refund is issues, post a refund for the entire order
    • Post a new transaction for the order with just the partial items remaining.
    • This is the preferred method for a couple reasons:
      • If a transaction is in a locked tax period in the past, it is simplest for tax purposes to do an entire refund and be liable for a new transaction in the current period. The refund should reference the original transaction, but the new transaction for the order does not directly reference the original transaction in taxjar, but could be linked through a naming scheme, etc, for traceability purposes
      • This is the simplest implementation wise, as you do not need to worry about refunds for individual line items, or how much of the refund was for shipping.
  2. Getting refunded with store credits or a gift card counts as a "tax exempt" purchase. However, it should still be reported to TaxJar. The order that uses the store credits/gift card to purchase goods is a taxable purchase, and should also get reported to taxjar.

  3. We should post the transaction to TaxJar when the store has liability for the order, i.e. when a service has been provided. In the case of a physical good, this would be when the order ships, in the case of a gift card or store credits, this would be when the gift card/store credits are issues.

@Noah-Silvera
Copy link
Member

One follow up question we need to contact Ryan Lee about

The suggested pattern for refunds is to refund the entire original transaction, and then to create a new transaction in taxjar with the reduced amount (the amended transaaction)

For an amended transaction, do we want the date of it to be current date, (date the refund was issued) or the date in the past (date the order was originally fufilled).

nvandoorn added a commit that referenced this issue Jul 21, 2021
@Noah-Silvera Noah-Silvera added large needs-planning This issue needs to be broken into actionable issues and moved into a project RFC Request for comments and removed large labels Nov 19, 2021
@Noah-Silvera Noah-Silvera changed the title Support reporting [RFC] Support reporting Nov 19, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
needs-planning This issue needs to be broken into actionable issues and moved into a project RFC Request for comments
Projects
None yet
Development

No branches or pull requests

2 participants