Calling product APIs from a remote

I’m trying to call a Confluence API from a Forge Remote backend following these instructions.

The problem is that when my remote backend calls the Confluence API with the token, the response is always 404. If I allow anonymous access to the space and remove the token from the request headers, I get a response, so the URL is correct. I have tried both systemToken and userToken, but the result is the same.

According to the api documentation the required scope is read:page:confluence which I have added to the manifest.

What could be wrong?

The manifest:

modules:
  macro:
    - key: forge-remote-hello-world
      resource: main
      render: native
      resolver:
        endpoint: remote-endpoint
      title: Hello World
  function:
    - key: resolver
      handler: index.handler
  endpoint:
      - key: remote-endpoint
        remote: remote-app-node
        route:
          path: /frc-event
        auth:
          appSystemToken:
            enabled: true
          appUserToken:
            enabled: true
resources:
  - key: main
    path: src/frontend/index.jsx
app:
  runtime:
    name: nodejs22.x
  id: ari:cloud:ecosystem::app/a92cd42d-b37f-4098-8d5a-bc90c63fd74a
permissions:
  scopes:
    - read:comment:confluence
    - read:confluence-content.summary
    - read:confluence-content.all
    - read:page:confluence
    - search:confluence
    - read:app-system-token
    - read:app-user-token
    - storage:app
remotes:
  - key: remote-app-node
    baseUrl: https://xyz.ngrok.io
    auth:
      appSystemToken:
        enabled: true
      appUserToken:
        enabled: true

The remote backend:

import express from 'express';

const app = express()
const port = 5005

app.post('/frc-event', handler);
app.listen(port, () => console.log(`Listening on http://localhost:${port}`));

async function handler(req, res) {
  const systemToken = req.headers['x-forge-oauth-system'];
  const userToken = req.headers['x-forge-oauth-user'];

  const response = await fetchFromConfluence(userToken, 'https://xyz.atlassian.net')
  console.log(response);
  res.json({ success: true });
}

async function fetchFromConfluence(token, apiBaseUrl) {
  console.log(token);
  const headers = {
    Accept: 'application/json',
    Authorization: `Bearer ${token}`
  }

  return await fetch(`${apiBaseUrl}/wiki/api/v2/pages/1907097601`, { headers });
}

1 Like

Hi @ErkkiLepre, are you able to set apiBaseUrl to the value of the claim from the Forge Invocation Token? Constructing the base URL by hand is sometimes error prone, it could be a path parameter that is missing or something.

1 Like

Thanks. This solved it.

What the documentation wasn’t clear on, was that the baseUrl is not https://instance.atlassian.net, but https://api.atlassian.com/ex/confluence/<cloudId>, and that it’s recommended to be read form the FIT.

1 Like