Skip to Content

Currency conversion FM/method to rule them all?

We have a program that is using FM CONVERT_TO_FOREIGN_CURRENCY and recently ran into an issue with JPY conversion. It's a well-known problem and there are many related SCN questions (just one example).

The issue is that JPY currency is configured with "conversion factor". Current exchange rate is about 50 USD for 5000 JPY. But if FM CONVERT_TO_FOREIGN_CURRENCY (or many similar ones) is used then it returns 50 instead of 5000. The suggestions on SCN and in SAP Notes are to use BAPI_CURRENCY_CONV_TO_EXTERNAL in addition to the conversion FM to adjust the result for the factor, according to the configuration. I.e. the first FM would return 50 and then BAPI would turn it into 5000.

I've looked at some SAP correction notes and it seems that even SAP is basically doing the same: adding BAPI (or another FM) after the first FM.

My question is: is there really not a single FM or class/method that does both things? I searched using *cur*conv* mask in SE37 and SE24 but came up empty-handed. And if there is nothing like that in standard how is everyone handling this in Z code? Just call 2 FMs or a global custom method/FM?

I know this is 1001st question on the subject but it just seems odd there is still not a better standard option in 2018. Unless I'm missing something. We have ECC 6.0 EHP6 if it matters.

Thank you!

Add comment
10|10000 characters needed characters exceeded

  • Follow
  • Get RSS Feed

2 Answers

  • Best Answer
    Mar 26, 2018 at 09:29 PM

    The simplest explanation is to follow the rules: Use INTERNAL format for anything involving data type CURR. Use EXTERNAL for all other data types. Use BAPI_CURRENCY_CONV* to convert between them.

    The online help explains it fairly well, but for a really detailed explanation grab a cup of coffee (you'll need it) and have a read through note 153707

    Add comment
    10|10000 characters needed characters exceeded

    • Yes, BAPIs will almost always use the external format, because they are in principle supposed to be callable from the outside world.

      I think the reason for all this is historic, someone had a great idea that we just treat it as integers to simplify calculations but we'll define it as a type p with two decimals so it will automatically be displayed correctly and we save the poor developers the headache of having to convert all the time. If that doesn't make sense, keep in mind that SAP started out in the 70's, an era known for recreational drug use.

  • Mar 29, 2018 at 11:03 AM


    I usually retrieve the decimal places of the currency from tcurx table, and then do some math operations with the amount to convert.

    Then I use BAPI BAPI_EXCHANGERATE_GETDETAIL to get the exchange rate details and use that information to do the conversion of the amount.

    Example not tested.

    data: ls_tcurx type tcurx,
          lv_to_curr  type SYCURR,
          lv_fr_curr  type SyCurr,
          lv_date     type sy-datum,
          lv_amount type dmbtr,
          lv_convert type dmbtr,
          ls_exchrt type bapi1093_0,
          ls_return type bapiret1.
    lv_amount = 50.
    lv_to_curr = 'JPY'.
    lv_fr_curr = 'USD'.
    lv_date = sy-datum.
    select single * from tcurx into ls_tcurx
       where currkey eq lv_to_curr.
    if  ls_tcurx is not initial.
    case ls_tcurx-currdec.
      when 1.
        lv_amount  = lv_amount  * 10.
      when 0.
        lv_amount  = lv_amount  * 100.
      when 3.
        lv_amount  = lv_amount  / 10.
      when others.
          rate_type  = '1004' " 1004 P&L / '1002' Balance Sheet
          from_curr  = lv_fr_curr
          to_currncy = lv_to_curr
          date       = '20180329'
          exch_rate  = ls_exchrt
          return     = ls_return.
        lv_convert = lv_amount  * ( ( ls_exchrt-exch_rate *  ls_exchrt-to_factor ) / ls_exchrt-from_factor ).
    Add comment
    10|10000 characters needed characters exceeded

    • Well, if you look inside the internal/external conversion BAPIs you'll see they do pretty much the same thing as your code. Personally, I prefer to use standard functions whenever possible. No need to reinvent the bicycle and then be responsible for maintenance. Who knows if SAP decides to redesign the tables and what's not in S/4HANA. :)