fix(security): reject actuator basic-auth when internal password is unset (GHSA-xfc5-796c-7hr9)#41964
Merged
Merged
Conversation
…nset (GHSA-xfc5-796c-7hr9)
The /actuator/** filter chain compared the supplied Basic Auth password
against APPSMITH_INTERNAL_PASSWORD, which defaults to an empty string when
unset. "".equals("") then matched for any request carrying empty Basic Auth
credentials, granting the INTERNAL authority and bypassing authentication on
the actuator endpoints (reachable on backend port 8080 in Kubernetes
deployments).
Guard the comparison so an unset/empty configured password never authenticates
any caller; all /actuator/** requests then correctly return 401 until an
operator sets APPSMITH_INTERNAL_PASSWORD.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Contributor
WalkthroughThe ChangesSecurity config fix
Estimated code review effort: 2 (Simple) | ~10 minutes Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
salevine
approved these changes
Jul 9, 2026
salevine
left a comment
Contributor
There was a problem hiding this comment.
- No regression test for a published GHSA (flagged by all four reviewers). The repo already has the exact pattern to copy: AuthGuardTest.java in appsmith-server/src/test/.../configurations/, itself created for a prior security fix. Recommended: an ActuatorAuthTest with two contexts — password unset (empty Basic creds → 401) and password set (wrong → 401, correct → 200, no header → 401). Notably, the "password set + correct creds still works" leg has no validation anywhere, including the author's manual curl.
- Release note needed. Deployments that scrape /actuator/prometheus relying on the empty-password hole will start getting 401s. That's the intended fail-closed outcome, but operators need to be told to set APPSMITH_INTERNAL_PASSWORD rather than work around it.
Tracked (follow-up hardening, not this PR): (edited)
subrata71
approved these changes
Jul 9, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
The
/actuator/**management endpoints are protected by HTTP Basic auth that compares the supplied password againstAPPSMITH_INTERNAL_PASSWORD. That variable defaults to an empty string when unset (application-ce.properties:appsmith.internal.password=${APPSMITH_INTERNAL_PASSWORD:}), so the check"".equals("")succeeds for any request sending empty Basic Auth credentials — granting theINTERNALauthority and bypassing authentication on the actuator endpoints.This guards the comparison so an unset/empty configured password never authenticates any caller. All
/actuator/**requests then return401until an operator explicitly setsAPPSMITH_INTERNAL_PASSWORD.Why it matters
prometheusandmetrics(perapplication-ee.properties), plushealthon CE — so the practical pre-fix impact is unauthenticated read access to operational metrics, not secrets.management.endpoints.web.exposure.include(e.g. to includeenv/heapdump).Change
Single-file change in
SecurityConfig.internalWebFilterChain. No new imports (usesString.isEmpty()), so the hunk applies cleanly to EE via the hourly sync.Testing
curl -u 'anyuser:' https://<host>/actuator/prometheus→200401;200only whenAPPSMITH_INTERNAL_PASSWORDis set and matched.🤖 Generated with Claude Code
Summary by CodeRabbit
Warning
Tests have not run on the HEAD 2b58fc3 yet
Wed, 08 Jul 2026 02:34:56 UTC