VYPR
High severity8.2NVD Advisory· Published Apr 15, 2026· Updated Apr 23, 2026

CVE-2026-40104

CVE-2026-40104

Description

XWiki Platform is a generic wiki platform offering runtime services for applications built on top of it. Versions 1.8-rc-1, 17.0.0-rc-1 and 17.5.0-rc-1 and prior include a resource exhaustion vulnerability in REST API endpoints such as /xwiki/rest/wikis/xwiki/spaces/AnnotationCode/pages/AnnotationConfig/objects/AnnotationCode.AnnotationConfig/0/properties, which list all available pages as part of the metadata for database list properties without applying query limits. On large wikis, this can exhaust available server resources. This issue has been patched in versions 16.10.16, 17.4.8 and 17.10.1.

Affected packages

Versions sourced from the GitHub Security Advisory.

PackageAffected versionsPatched versions
org.xwiki.platform:xwiki-platform-oldcoreMaven
>= 1.8-rc-1, < 16.10.1616.10.16
org.xwiki.platform:xwiki-platform-oldcoreMaven
>= 17.0.0-rc-1, < 17.4.817.4.8
org.xwiki.platform:xwiki-platform-oldcoreMaven
>= 17.5.0-rc-1, < 17.10.117.10.1
org.xwiki.platform:xwiki-platform-legacy-oldcoreMaven
>= 1.8-rc-1, < 16.10.1616.10.16
org.xwiki.platform:xwiki-platform-legacy-oldcoreMaven
>= 17.0.0-rc-1, < 17.4.817.4.8
org.xwiki.platform:xwiki-platform-legacy-oldcoreMaven
>= 17.5.0-rc-1, < 17.10.117.10.1

Affected products

1
  • cpe:2.3:a:xwiki:xwiki:*:*:*:*:*:*:*:*
    Range: >=1.8,<16.10.16

Patches

1
47b568c4753a

XWIKI-23550: DBListClass should respect query limit

https://github.com/xwiki/xwiki-platformMichael HamannOct 23, 2025via ghsa
2 files changed · +70 1
  • xwiki-platform-core/xwiki-platform-oldcore/src/main/java/com/xpn/xwiki/objects/classes/DBListClass.java+10 1 modified
    @@ -32,7 +32,9 @@
     import org.slf4j.Logger;
     import org.slf4j.LoggerFactory;
     import org.xwiki.component.util.DefaultParameterizedType;
    +import org.xwiki.query.Query;
     import org.xwiki.query.QueryBuilder;
    +import org.xwiki.security.SecurityConfiguration;
     import org.xwiki.security.authorization.AuthorExecutor;
     
     import com.xpn.xwiki.XWiki;
    @@ -118,13 +120,20 @@ public List<ListItem> getDBList(XWikiContext context)
             List<ListItem> list = getCachedDBList(context);
             if (list == null) {
                 try {
    +                SecurityConfiguration securityConfiguration = Utils.getComponent(SecurityConfiguration.class);
                     DefaultParameterizedType dbListQueryBuilderType =
                         new DefaultParameterizedType(null, QueryBuilder.class, DBListClass.class);
                     QueryBuilder<DBListClass> dbListQueryBuilder = Utils.getComponent(dbListQueryBuilderType);
                     // Execute the query with the rights of the class last author.
                     AuthorExecutor authorExecutor = Utils.getComponent(AuthorExecutor.class);
                     list = makeList(authorExecutor.call(() -> {
    -                    return dbListQueryBuilder.build(this).execute();
    +                    Query query = dbListQueryBuilder.build(this);
    +                    int configuredLimit = securityConfiguration.getQueryItemsLimit();
    +                    // Limit unlimited queries or queries with a high limit to the configured limit.
    +                    if (configuredLimit > 0 && (query.getLimit() <= 0 || query.getLimit() > configuredLimit)) {
    +                        query.setLimit(configuredLimit);
    +                    }
    +                    return query.execute();
                     }, getOwnerDocument().getAuthorReference(), getDocumentReference()));
                 } catch (Exception e) {
                     LOGGER.warn("Failed to get the Database List values. Root cause is [{}].",
    
  • xwiki-platform-core/xwiki-platform-oldcore/src/test/java/com/xpn/xwiki/objects/classes/DBListClassTest.java+60 0 modified
    @@ -21,9 +21,18 @@
     
     import java.util.ArrayList;
     import java.util.List;
    +import java.util.concurrent.Callable;
     
     import org.junit.jupiter.api.BeforeEach;
     import org.junit.jupiter.api.Test;
    +import org.junit.jupiter.params.ParameterizedTest;
    +import org.junit.jupiter.params.provider.CsvSource;
    +import org.xwiki.model.reference.DocumentReference;
    +import org.xwiki.query.Query;
    +import org.xwiki.query.QueryBuilder;
    +import org.xwiki.security.SecurityConfiguration;
    +import org.xwiki.security.authorization.AuthorExecutor;
    +import org.xwiki.test.junit5.mockito.MockComponent;
     
     import com.xpn.xwiki.XWikiContext;
     import com.xpn.xwiki.doc.XWikiDocument;
    @@ -34,7 +43,12 @@
     
     import static org.junit.jupiter.api.Assertions.assertEquals;
     import static org.mockito.ArgumentMatchers.any;
    +import static org.mockito.ArgumentMatchers.anyInt;
     import static org.mockito.Mockito.doAnswer;
    +import static org.mockito.Mockito.mock;
    +import static org.mockito.Mockito.never;
    +import static org.mockito.Mockito.verify;
    +import static org.mockito.Mockito.when;
     
     /**
      * Unit tests for {@link DBListClass}.
    @@ -48,6 +62,15 @@ class DBListClassTest
         @InjectMockitoOldcore
         private MockitoOldcore oldcore;
     
    +    @MockComponent
    +    private QueryBuilder<DBListClass> queryBuilder;
    +
    +    @MockComponent
    +    private SecurityConfiguration securityConfiguration;
    +
    +    @MockComponent
    +    private AuthorExecutor authorExecutor;
    +
         @BeforeEach
         void before()
         {
    @@ -399,4 +422,41 @@ void testReturnColWithInvalidQuery()
             assertEquals("-", dblc.returnCol("do something", true));
             assertEquals("-", dblc.returnCol("do something", false));
         }
    +
    +    @ParameterizedTest
    +    @CsvSource({
    +        "10, 20, false",
    +        "20, 10, true",
    +        "0, 0, false",
    +        "0, -1, false",
    +        "20, -1, false",
    +        "0, 20, true"
    +    })
    +    void getDBListLimit(int queryLimit, int configuredLimit, boolean setLimit) throws Exception
    +    {
    +        Query mockQuery = mock();
    +        when(mockQuery.getLimit()).thenReturn(queryLimit);
    +        when(mockQuery.execute()).thenReturn(List.of());
    +        when(this.securityConfiguration.getQueryItemsLimit()).thenReturn(configuredLimit);
    +
    +        when(this.authorExecutor.call(any(), any(), any())).then(invocation -> {
    +            Callable<?> callable = invocation.getArgument(0);
    +            return callable.call();
    +        });
    +
    +        XWikiDocument ownerDocument = new XWikiDocument(new DocumentReference("wiki", "space", "page"));
    +        DBListClass dbListClass = new DBListClass();
    +        dbListClass.setOwnerDocument(ownerDocument);
    +
    +        when(this.queryBuilder.build(dbListClass)).thenReturn(mockQuery);
    +
    +        dbListClass.getDBList(this.oldcore.getXWikiContext());
    +
    +        if (setLimit) {
    +            verify(mockQuery).setLimit(configuredLimit);
    +        } else {
    +            verify(mockQuery, never()).setLimit(anyInt());
    +        }
    +        verify(mockQuery).execute();
    +    }
     }
    

Vulnerability mechanics

Generated by null/stub on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.

References

5

News mentions

0

No linked articles in our index yet.