Gains and different currencies

21 views

Oleg Bulatov

Nov 22, 2022, 2:58:05 PM11/22/22
to hledger
Hi all!

I suddenly discovered for myself that capital gains are a very difficult thing if you use multiple currencies. And I don't know how to use hledger to calculate them.

In my example (see foo.ldg below), the value of the stocks in USD:
2021-01-25 821.00 USD
2022-10-24 678.00 USD
2022-10-25 697.00 USD
in EUR:
2021-01-25 676.45 EUR
2022-10-24 686.65 EUR
2022-10-25 699.52 EUR
so it decreased in USD (and in CZK), but increased in EUR. I took me a while to realize that it isn't a mistake.

I can calculate these values in USD and EUR using hledger using the commands:

hledger -f foo.ldg bal Stocks --value=end,USD --daily -H
hledger -f foo.ldg bal Stocks --value=end,EUR --daily -H

and I can print capital gains in USD:

hledger -f foo.ldg bal Stocks --gain --value=end,USD --daily -H

but I cannot find a way how calculate capital gains in EUR. The command

hledger -f foo.ldg bal Stocks --gain --value=end,EUR --daily -H

just converts capital gains from USD to EUR (i.e. it prints negative numbers), but I'm looking for a command that can print difference between the initial cost in EUR and the current value in EUR. Is there a command that can print me:
2021-01-25 0.00 EUR
2022-10-24 10.20 EUR
2022-10-25 23.07 EUR
(and similar in CZK)?

And is there a way to find how much I spend on stocks in CZK? I tried two options:
1. --cost --value=end,CZK --daily -H -- it calculates the cost in USD, and then converts into CZK, i.e. every day the value is different, even though I don't do anything with stocks.
2. --cost --value=then,CZK --daily -H -- it shows incorrect negative values if there is the sell transaction. I expect the cost to be 0 once I've sold everything.

Perhaps hledger already can do it? I've just recently understood what and when should be converted (I hope), and I don't know how to explain it to hledger.

foo.ldg:
P 2021-01-25 EUR 26.1130 CZK
P 2022-10-24 EUR 24.4690 CZK
P 2022-10-25 EUR 24.4820 CZK

P 2021-01-25 EUR 1.2137 USD
P 2022-10-24 EUR 0.9874 USD
P 2022-10-25 EUR 0.9964 USD

P 2021-01-25 WITS 8.21 USD
P 2022-10-24 WITS 6.78 USD
P 2022-10-25 WITS 6.97 USD

2021-01-01 * Opening
Assets:Checking                     20000.00 CZK
Equity:Opening

Assets:Stocks                           100 WITS @ 8.21 USD
Assets:Checking                      -821.00 USD
Assets:Checking                       821.00 USD @@ 676.45 EUR
Assets:Checking                      -676.45 EUR
Assets:Checking                       676.45 EUR @@ 17664.14 CZK
Assets:Checking                    -17664.14 CZK

;2022-10-24 * Selling stocks
;    Assets:Stocks                          -100 WITS @ 8.21 USD
;    Expenses:Capital Losses               143.00 USD
;    Assets:Checking                       678.00 USD
;    Assets:Checking                      -678.00 USD @@ 686.64 EUR
;    Assets:Checking                       686.64 EUR

Oleg

Simon Michael

Dec 6, 2022, 4:54:27 PM12/6/22
to hledger
Hi Oleg,

On Nov 22, 2022, at 09:58, Oleg Bulatov <dmag...@gmail.com> wrote:

Hi all!

I suddenly discovered for myself that capital gains are a very difficult thing if you use multiple currencies. And I don't know how to use hledger to calculate them.

In my example (see foo.ldg below), the value of the stocks in USD:
2021-01-25 821.00 USD
2022-10-24 678.00 USD
2022-10-25 697.00 USD
in EUR:
2021-01-25 676.45 EUR
2022-10-24 686.65 EUR
2022-10-25 699.52 EUR
so it decreased in USD (and in CZK), but increased in EUR. I took me a while to realize that it isn't a mistake.

I can calculate these values in USD and EUR using hledger using the commands:

hledger -f foo.ldg bal Stocks --value=end,USD --daily -H
hledger -f foo.ldg bal Stocks --value=end,EUR --daily -H

and I can print capital gains in USD:

hledger -f foo.ldg bal Stocks --gain --value=end,USD --daily -H

but I cannot find a way how calculate capital gains in EUR. The command

hledger -f foo.ldg bal Stocks --gain --value=end,EUR --daily -H

just converts capital gains from USD to EUR (i.e. it prints negative numbers), but I'm looking for a command that can print difference between the initial cost in EUR and the current value in EUR. Is there a command that can print me:
2021-01-25 0.00 EUR
2022-10-24 10.20 EUR
2022-10-25 23.07 EUR
(and similar in CZK)?

I can't find a way either. I think it's a limitation of the bal --gain report: it will only calculate the gain in the currency you purchased with.

To see the effective gain as if you had purchased in another currency, I think you must fall back on reporting the periodic values in that currency and calculating gain yourself or with a script (compensating for inflows/outflows as --gain does). Eg (dates tweaked for readability):

\$ hledger bal Stocks --value=end,EUR --daily -H
Ending balances (historical) in 2022-10-23..2022-10-25, valued at period ends:

|| 2022-10-23  2022-10-24  2022-10-25
===============++====================================
Assets:Stocks || 676.44 EUR  686.65 EUR  699.52 EUR
---------------++------------------------------------
|| 676.44 EUR  686.65 EUR  699.52 EUR

=> changes: 10.20 EUR, 23.07 EUR

Perhaps a generic "show differences between these numbers" flag would make sense, sort of the opposite of --cumulative. (I tried adding --change, but it didn't work, I think that has a different meaning.)

And is there a way to find how much I spend on stocks in CZK? I tried two options:
1. --cost --value=end,CZK --daily -H -- it calculates the cost in USD, and then converts into CZK, i.e. every day the value is different, even though I don't do anything with stocks.
2. --cost --value=then,CZK --daily -H -- it shows incorrect negative values if there is the sell transaction. I expect the cost to be 0 once I've sold everything.

Hmm. I think for that last statement you need to pick fixed valuation date, like --value=now,CZK or 2022-10-23,CZK.

I hope it's some help. Best..

Simon Michael

Dec 6, 2022, 5:05:49 PM12/6/22
to hledger

On Dec 6, 2022, at 11:54, Simon Michael <si...@joyful.com> wrote:

I think it's a limitation of the bal --gain report: it will only calculate the gain in the currency you purchased with.

Actually, if that were true then altering the journal entry, expressing the cost as EUR, would be enough. But that doesn't work either, I think there might be some logic for choosing the gain currency based on SYMBOL's default valuation commodity, see https://hledger.org/1.28/hledger.html#valuation-commodity and the output of --debug=2, eg.

balance --gain needs more docs.

Simon Michael

Dec 6, 2022, 5:09:41 PM12/6/22
to hledger
Also I found this FWIW:

-- | Calculate the gain of each component amount, that is the
-- difference between the valued amount and the value of the cost basis.
--
-- If the commodity we are valuing in is not the same as the commodity of the
-- cost, this will value the cost at the same date as the primary amount. This
-- may not be what you want; for example you may want the cost valued at the
-- posting date. If so, let us know and we can change this behaviour.
mixedAmountGainAtDate :: PriceOracle -> M.Map CommoditySymbol AmountStyle -> Maybe CommoditySymbol -> Day -> MixedAmount -> MixedAmount