-
Notifications
You must be signed in to change notification settings - Fork 47
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
Some issues, some solutions, and general thoughts #13
Comments
Thanks for the long thread and for taking the time to share your experience with RP2 and your research on the topic of crypto taxes! It will take me a few days to respond properly because I'm out of town right now, but I wanted to share my appreciation for the detailed feedback! |
I'm glad this question reappeared: it looked like your account was not accessible for a long time, and this question disappeared for me so I couldn't follow up. However today I noticed it reappeared in the issue page. Most of the things you mentioned have been fixed in the last few months. I'll respond in more detail in the next few days. |
Let me reiterate that I really appreciated your detailed message. Even though it disappeared when your account became non-accessible, I managed to keep a copy of it, which helped inspire some of the development. So thanks for taking the time to provide such good feedback! Here is my reply:
|
Closing the issue. I invite you to check the latest version of RP2 and DaLI, which incorporate a lot of your feedback. Feel free to open a new issue if you have more feedback. |
So far this year I've spent about 250 hours researching everything crypto tax related and running through various software packages (both commercial and open-source), and it was a nightmare. However, I learned a lot that I would like to share, and I would be interested in supporting this project and helping it grow. Since this is a going to be a really long post, the moral of the story is that here are a bunch of comments and suggestions; let me know how I can help contribute. I'm not a python expert, but I do a lot of work with Excel VBA and can probably write pseudo code fairly well.
First off, thank you so much for this software, as it was the only thing that was able to process all of my data with enough functionality to get it done CORRECTLY and then provide the right output (US tax forms). I ended up having around 103,000 crypto disposals between 14 wallets, exchanges, and services, crossing 7 blockchains, so doing these calculations manually was completely out of the question. However, while this software worked, I had to use several workarounds that I think can and should be integrated into the code, which I'll describe in a bit. First, I have thoughts about implementation, since I think there are two distinct pieces of the puzzle that need to work in tandem.
As mentioned above, this software is focused on primitive IN/OUT transactions, which is totally fine and works well for the tax calculation side of things. The downside to doing it this way is that huge challenge of accurately getting data into this form so that the code can do its job. This challenge is partially because it's a semi-manual process at best, but also because it requires extensive knowledge of the crypto world AND comprehensive tax knowledge. Both of these are difficult because the information on them is still lacking. As such, I think the biggest thing that this project needs is a data pre-processor/converter that prepares the data CORRECTLY for the tax calculation. I see that DaLI has been created, but it still seems pretty sparse and under-documented. I’ll discuss my thoughts on DaLI at the end of this. The primitive code, as it stands, also needs some tweaking to be able to more intelligently handle complex transactions. Here are things that need to be addressed:
FEES
The current code needs to be modified to handle DeFi situations, but most of this comes down to fees. Regarding "fee only" transactions, you guys have already come up with the two obvious solutions (100% Sell with $0 in proceeds vs. 0% Sell with 100% Fees). The problem is that the current software can't handle either of these. It doesn't allow you to put zero as the amount sold, nor does it allow you to put zero for the coin price. Was this done as a data integrity check only, or are these numbers (amount sold and coin price) used later in the denominator of an equation, which might lead to a "divide by zero" error? One solution could be to create a different type of transaction, such as "FEE" or "COST" (mentioned above), which allows either the sell amount or the coin price to be zero. This way the data can still be validated by checking that the right numbers exist in the right place, but also ensures that these numbers aren't used later in calculations that would cause an error. By the way, the current workaround I used here is listing the coin price of "fee only" transactions as 1e-10, which is messy, but it works.
IN, OUT, and INTRA transactions all need to be able to handle fees differently. In general, the most correct way to handle fees is to include them in the transaction by either adding them to the cost basis or removing them from the proceeds. This helps reduce the number of extra "disposals" by limiting the number of "fee only" transactions. This should be handled on two fronts. First, the current code should be modified such that "BUY" fees are in whatever currency is being traded, not simply in fiat. This brings up another issue with fiat currency fees that I'll address shortly. Anyway, the "BUY" fee currency should match that of the asset being bought. It comes up often that transaction fees are paid in the bought currency. The other piece that goes along with this is that the data pre-processor needs to keep the fee for each transaction with either the BUY or SELL half if the fee asset matches the BUY or SELL asset. For INTRA trades, the current code is fine, since adjusting the AMOUNT SENT and AMOUNT RECEIVED numbers sets the fee. This also needs to be part of the data pre-processor, though, since generally, the amount moved between accounts needs to be the same number in order to identify matching transactions. In other words, say you have 1 BTC in you account in the Cash App, and you send it all to Coinbase, which has a transaction fee of .005 BTC. In the ledger, this would look like a 0.995 BTC withdrawal from Cash, a 0.995 BTC Deposit to Coinbase, and a 0.005 BTC fee on the Cash App account. This is necessary so that internal movements of funds can be identified based on their date, asset, and amount. However, this can be converted to an INTRA transaction of 1 BTC send, 0.995 BTC received, if that's the smartest way to handle this in the future version of your software.
I'll take a moment to pause here with a sidenote on fiat currency fees. Am I correct in assuming that this software was developed to ignore USD as its own "crypto asset" for calculations? I realize that by including a USD tab to be processed by the software that it creates gains/losses on USD, which is a bit weird, but letting the software calculate stuff on USD is useful, since it provides a better picture of what's happening in your USD holdings. Including USD would probably be necessary, however, if the BUY fee asset is changed from USD to whatever the bought currency is. However, this could be managed by just logging USD fees in their own tab and modifying the cost basis/proceeds/expenses of transactions after the fact. Regardless, I bring this up because I included USD in my calculations and I got an error because the software didn't recognize that my excel tab for USD was not the same USD as the FIAT FEE column. So when I listed USD fees for transactions, these dollars weren't removed from my USD holdings. This is another reason why the BUY fees should be set as whatever the BUY asset is.
LIQUIDITY MINING
Interacting with smart contracts can be a tricky business. There are so many ways that these can complicate things, and it probably makes sense to add functionality for them as situations arise, but again, this should be part of the data pre-processor. One example of a very common situation is with liquidity mining. The concept is that you add liquidity to an exchange by adding two assets together, which can be used by people to buy and sell those assets. In return for offering these coins to be traded, you usually get some of the proceeds (trading fees) incurred by the person using the exchange. The way these transactions work is the following. You want to add BUSD/USDC liquidity to PancakeSwap. To do this, you add 1000 BUSD 1000 USDC, and in exchange, you get 2000 Cake-LP tokens as a receipt for the coins you’ve added to the liquidity pool. This transaction has 4 assets involved, in 3 parts. First, you had a withdrawal for 1000 BUSD and a withdrawal for 1000 USDC. Next, you received (a deposit) for 2000 Cake-LP. Lastly, you paid gas in the blockchain’s native token, say 0.001 BNB. In my opinion, the best way to handle this transaction is to split it. So the first transaction would be trading 1000 BUSD for 1000 Cake-LP with a transaction fee of 0.0005 BNB. The second would be trading 1000 USDC for 1000 Cake-LP with a transaction fee of 0.0005 BNB. Also note that the opposite of this situation happens when liquidity is removed from the liquidity pool.
STAKING
First, I think it’s dumb that the IRS, or whoever, decided that rewards from staking assets should be classified as “Staking”. This makes things very confusing for people who are also using “Staking” and “Unstaking” to describe doing those actions. Aside from this stupidity, the actions of staking and unstaking need to be handled appropriately. The current reigning theory in staking assets is that this act is non-taxable, because you still own the assets that you are staking, even though they’re being held by someone else. As such, you could probably exclude the movement of funds into and out of staking pools, except there are a couple problems with this. First, excluding these movements means that the transaction fees (expenses) from these movements wouldn’t be captured. Second, there are some instances where the staking pool charges a fee to add your coins. For example, there are staking pools on brand new “sh**coin” exchanges that charge 4% of your staked assets upon depositing, since the APR offered is incredibly high. In these cases, the coin price always drops like a rock, and you’re lucky to recoup the fees, but it can be done for a decent profit. In either case mentioned here, it’s important to be able to log and account for the fees incurred. The best way I’ve found to do this is to create a separate virtual wallet that stores all of my staked coins. By doing this, you can show your activity of staking and unstaking coins where the only taxable part of the transaction is the fee (which is what we want).
DATA PRE-PROCESSING
As mentioned throughout this post, the need for data pre-processing is huge here. I think this is one of the things that DaLI is supposed to be doing, but it seems to be more focused on parsing data files from common exchanges rather than cleaning, organizing, and preparing an ODS file that can be used for RP2. I suggest that the nearest-term project should be on creating a converter that takes a .csv file (or whatever) and turns it into an input file for RP2. The input data format for this should be predetermined (names of columns, categories, general conventions, etc), and information contained within it should dictate how the data gets transformed into the RP2 input file. As an example, say you label a transaction (a row in the data file) as “FEE”. The converter would then know that this line needs to be processed to make it a fee-only transaction for RP2. Similarly, if a set of 3 lines (all with the same transaction hash) are labeled “ADD LIQUIDITY”, then the converter will know to split the transaction, distribute the LP token and fee to each half, and then process these into IN/OUT lines for RP2.
Once the converter is made and is functional, then time should be spent on parsing and importing common data files from exchanges and wallets (DaLI). Note that these tools should extract data from the downloaded exchange files, for example, and put it into the converter file structure with proper labels and such, so that the converter will be useful for all data. The problem with DaLI currently is that each plugin must be managed separately, but the rules for converting the information to an RP2 input should be centralized. Please consider building a converter first, then using DaLI plugins to populate the input file for the converter. This is because a universal converter will be extremely useful right away, whereas DaLI is only useful for whichever plugins are written and written correctly. Plus, changes to how they convert data for RP2 would have to be managed in each of them individually instead of letting the converter do the hard work.
OUTPUT REPORTS
Another thing that would be useful, since the IRS wants this info, is a script that exports summary statements within the crypto tax report. Information should include:
Summary of Capital Gains with number of disposals, total proceeds from sales, total acquisition costs, total realized gains, total realized losses, net capital gains
Capital Gains Report showing realized gains, realized losses, and net gain/loss grouped by cryptocurrency
Year end holdings with the following information for each coin: quantity, cost basis for that amount, net value at year end (12/31), average cost per coin, and unrealized gains/losses
Income summary showing how much income was received from each type (airdrop, staking, interest, wages, etc.)
Expense summary whosing the total expenses incurred by category (transfer fees, contract approvals, etc.)
The settings and assumptions used by this software. For example, that transfers between accounts are not taxes, but the fees for moving them are included in the expense report and are based on fair market value at the time of the transaction. That gains/losses from crypto-to-crypto trades are included in the capital gains report. Etc...
ADDITIONAL THOUGHTS
The one thing this project is missing is the ability to automatically find and download historical coin prices to be added to the data. This feature would be killer, but the challenge seems to be finding a free crypto price API and interacting with it. Let me know if you want to see what I’ve accomplished on this front.
The text was updated successfully, but these errors were encountered: