My custom content created is not appearing in search results - neither quick nor advanced search

I’ve built a Forge app which is storing its contents with custom content entities via REST API v2 as described here: https://developer.atlassian.com/cloud/confluence/rest/v2/api-group-custom-content/#api-group-custom-content

My sanitized manifest.yml looks like:

app:
  runtime:
    name: nodejs22.x
    memoryMB: 256
    architecture: arm64
  id: <my-app-id>
permissions:
  scopes:
    - 'read:confluence-props'
    - 'write:confluence-props'
    - 'read:custom-content:confluence'
    - 'write:custom-content:confluence'
    - 'delete:custom-content:confluence'
modules:
  confluence:spacePage:
    - key: 'space-page'
      render: 'native'
      resource: 'space-page'
      title: 'Glossary'
      resolver:
        function: 'resolver'
      route: 'glossary'

  confluence:customContent:
    - key: 'entry-page'
      render: 'native'
      resource: 'entry-page'
      title: 'Glossary Entry'
      bodyType: 'storage'
      supportedContainerTypes:
        - 'space'
      supportedChildTypes:
        - 'attachment'
      supportedSpacePermissions:
        - 'read'
        - 'create'
        - 'delete'
      indexing: true
      preventDuplicateTitle: true

  function:
    - key: 'resolver'
      handler: 'index.handler'

resources:
  - key: 'space-page'
    path: 'src/frontend/space-page/index.tsx'
  - key: 'entry-page'
    path: 'src/frontend/entry-page/index.tsx'

As you can see, the indexing:true setting for confluence:customContent is enabled. In my (backend) resolver, which gets called via invoke("...") I am having a creation call for the custom entity like:

const contentResponse = await api.asUser().requestConfluence(
      route`/wiki/api/v2/custom-content`,
      {
        method: 'POST',
        body: JSON.stringify({
          spaceId: context.extension.space.id,
          type: getTypeFromProductContext(context),

          title: entryModel.term,
          body: {
            representation: 'atlas_doc_format',
            value: JSON.stringify(
              buildAdfBodyForEntry(entryModel),
            ),
          },
        }),
        headers: {
          'Accept': 'application/json',
          'Content-Type': 'application/json',
        },
      },
    );

Everything works as expected, I’m using the term property as title for the custom content and put a valid ADF document into the body of the custom content. Additionally, I’m also saving the JSON structure as corresponding content property.

I’ve also tried to fetch the custom content via the REST API with both methods, asUser() and asApp() and a CQL query just like:

const response = await api.asApp().requestConfluence(
      route`/rest/api/content/search/?cql=type = "forge:<APP_ID>:<ENV_ID>:<MODULE_KEY>" AND space = "<SPACE_ID>"`,
      {
        headers: {
          Accept: 'application/json',
        },
      },
    );

This also returns the custom content entities in results block.

So my question is: Why are these custom-content entities, which should be indexable just like pages, blog posts etc., not showing up in the search results of confluence? Thanks for your help!

Can you get the entities in a REST call outside of Forge, like through cURL? What is in the response?

Thanks for asking @AaronCollier. Yes, I can also retrieve the entities outside of the forge app when using curl like, tried it with this code:

EMAIL="<MY_EMAIL>"
API_TOKEN="<MY_TOKEN>"
SITE="<MY_SITE>"
CUSTOM_CONTENT_TYPE="forge:<APP_ID>:<ENV_ID>:<MODULE>"
SPACE_KEY="<MY_SPACE>"

curl -G \
  -u "${EMAIL}:${API_TOKEN}" \
  -H 'Accept: application/json' \
  --data-urlencode "cql=type = \"${CUSTOM_CONTENT_TYPE}\" AND space = \"${SPACE_KEY}\"" \
  "https://${SITE}/wiki/rest/api/search" | jq .

This also yields all created custom-content entities. As you asked for the response, here it is:

{
  "results": [
    {
      "content": {
        "id": "<CUSTOM_CONTENT_ID>",
        "type": "forge:<APP_ID>:<ENV_ID>:<MODULE>",
        "status": "current",
        "title": "Test Term",
        "childTypes": {},
        "macroRenderedOutput": {},
        "restrictions": {},
        "_expandable": {
          "container": "",
          "metadata": "",
          "extensions": "",
          "operations": "",
          "children": "",
          "history": "/rest/api/content/<CUSTOM_CONTENT_ID>/history",
          "ancestors": "",
          "body": "",
          "version": "",
          "descendants": "",
          "space": "/rest/api/space/<SPACE_KEY>"
        },
        "_links": {
          "webui": "/display/<SPACE_KEY>/customcontent/<CUSTOM_CONTENT_ID>",
          "self": "<SITE>/wiki/rest/api/content/<CUSTOM_CONTENT_ID>"
        }
      },
      "title": "Test Term",
      "excerpt": "Test contents...",
      "url": "/display/<SPACE_KEY>/customcontent/<CUSTOM_CONTENT_ID>",
      "resultGlobalContainer": {
        "title": "<MY_NAME>",
        "displayUrl": "/spaces/<SPACE_KEY>"
      },
      "breadcrumbs": [],
      "entityType": "content",
      "iconCssClass": "icon-forge-079f54a8-353a-43cd-ad15-904b234b7edd-ae590b17-bc10-443f-a487-9ba0a05156ea-entry-page",
      "lastModified": "2025-08-13T14:08:00.000Z",
      "friendlyLastModified": "Aug 13, 2025",
      "score": 0.0
    },
    ...
  ],
  "start": 0,
  "limit": 25,
  "size": 7,
  "totalSize": 7,
  "cqlQuery": "type = \"forge:<APP_ID>:<ENV_ID>:<MODULE>\" AND space = \"<SPACE_KEY>\"",
  "searchDuration": 181,
  "_links": {
    "base": "<SITE>/wiki",
    "context": "/wiki",
    "self": "<SITE>/wiki/rest/api/search?cql=type+%3d+%22forge%3a<APP_ID>%3a<ENV_ID>%3a<MODULE>%22+AND+space+%3d+%22<SPACE_KEY>%22"
  }
}

You can’t use CQL to search a space by its ID. Use the space key instead like your curl example.

@rcsr Thanks for pointing out, this was a type while sanitizing the output, I did use the space key, otherwise I wouldn’t have gotten any results back…