Tutorial/Power BI quickstart

Load exchange rates into Power BI with Power Query

Paste a Power Query M query into Power BI Desktop, turn the JSON response into a currency table, and keep scheduled refresh working after publication.

ERexchangerate.dev·Aug 5, 2026·5 min read

Power BI already has the connector you need. Create a blank query, call exchangerate.dev with Web.Contents, and split the stable host from the RelativePath. That last detail is easy to miss: it gives the Power BI service a fixed data source it can recognize when the semantic model refreshes.

Key points
Use a blank Power Query and paste the M code in Advanced Editor.
Keep https://api.exchangerate.dev fixed and put the endpoint in RelativePath.
The query returns a currency / rate table plus source and update-time columns.
Choose Anonymous for the web data-source credential because the API key travels in the request header.
Treat a key embedded in a PBIX file as visible to trusted report editors; use a server-side proxy for broad distribution.

Create a key and open a blank query

Create a free key at exchangerate.dev/signup. In Power BI Desktop, choose Get data → Blank query, then open View → Advanced Editor in Power Query Editor. The published report will use this query as its web data source.

Paste the Power Query M script

Power Query M · Advanced Editorcopy
let
    ApiKey = "exr_live_replace_with_your_key_here",
    Base = "USD",
    Symbols = "EUR,GBP,JPY",
    Response = Json.Document(
        Web.Contents(
            "https://api.exchangerate.dev",
            [
                RelativePath = "v1/latest/" & Base,
                Query = [symbols = Symbols],
                Headers = [Authorization = "Bearer " & ApiKey]
            ]
        )
    ),
    Rates = Record.ToTable(Response[rates]),
    Renamed = Table.RenameColumns(
        Rates,
        {{"Name", "currency"}, {"Value", "rate"}}
    ),
    WithBase = Table.AddColumn(Renamed, "base", each Response[base], type text),
    WithSource = Table.AddColumn(WithBase, "source", each Response[source], type text),
    WithUpdatedAt = Table.AddColumn(
        WithSource,
        "data_updated_at",
        each DateTimeZone.FromText(Response[data_updated_at]),
        type datetimezone
    )
in
    WithUpdatedAt

Replace the placeholder key, select Done, and name the query FxRates. The preview should show one row per requested currency.

Set the data types before loading

Confirm that currency, base, and source are Text; rate is Decimal number; and data_updated_at is Date/Time/Timezone. Then select Close & Apply. One row per currency is easier to relate to a Currency dimension than a record with one column per code.

Publish and configure scheduled refresh

Publish the report, open the semantic model settings in the Power BI service, and edit the credentials for https://api.exchangerate.dev. Choose Anonymous because the M query already sends the key in the Authorization header. Set a refresh schedule that fits the report.

Why RelativePath matters
Power BI needs to identify a stable web data source for refresh. Keeping the host fixed in Web.Contents and moving the endpoint into RelativePath avoids the common “dynamic data source” failure after publication.

Do not treat an M parameter as a secret vault

A parameter is convenient, but anyone trusted to edit the PBIX or query may be able to see the key. That is acceptable for a small internal workspace. If the report file is distributed widely, put exchangerate.dev behind your own server-side endpoint and let Power BI call that endpoint instead.

Indicative rates, not for settlement
These rates work for reporting, analytics, planning, and display. They are not an executable dealing quote and should not be used to settle a trade.
ER
exchangerate.dev
Integration guides for developers.

Keep reading

TutorialLive exchange rates in Excel with Power QueryRead ReferenceHistorical exchange rate APIRead TutorialGet exchange rates in n8nRead
More ComparisonsFixer vs exchangerate.devOpen Exchange Rates vs exchangerate.devCurrencylayer vs exchangerate.devCurrencylayer vs ExchangeRate-API
LearnReading source and market_session in your pipelineIndicative vs executable FX rates: what a rates API actually gives youECB reference rates, explained
Live RatesEUR/USDGBP/USDUSD/JPY