⚠ This page is served via a proxy. Original site: https://github.com
This service does not collect credentials or authentication data.
Skip to content

Conversation

@mlbiam
Copy link
Contributor

@mlbiam mlbiam commented Dec 31, 2025

Summary

This PR adds feature by supporting a webservice that will provide the list of allowed namespaces in a cluster. It adds a command line flag to allow specifying a URL to pull the namespaces from, in the form {"namespaces":["ns1","ns2"]} that is then stored in the local configuration. If there are namespaces specified by the service, then the default namespace is set to the first in the list.

Related Issue

Fixes #4258

Changes

  • Backend: Added a new configuration parameter
  • Frontend: checks for the namespace URL and loads namespaces from it if provided

Steps to Test

(this was how I developed it)

  1. Deploy OpenUnison with Namespace as a Service
  2. Create a namespace with an unprivileged owner
  3. Login

Screenshots (if applicable)

Notes for the Reviewer

I want to add some more docs too for running Head Lamp in-cluster, but figured that would be better for its own PR

@k8s-ci-robot
Copy link
Contributor

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: mlbiam
Once this PR has been reviewed and has the lgtm label, please assign sniok for approval. For more information see the Code Review Process.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@k8s-ci-robot k8s-ci-robot added cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Dec 31, 2025
@illume illume requested a review from Copilot December 31, 2025 11:42
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds support for a webservice that provides a list of allowed namespaces for a cluster. The backend introduces a new command-line flag me-namespaces-url to specify a URL that returns namespace data in the format {"namespaces":["ns1","ns2"]}. The frontend fetches this data during user authentication and stores it in local cluster settings.

Key Changes

  • Added MeNamespacesURL configuration parameter throughout the backend config chain
  • Frontend fetches namespaces from the configured URL and automatically sets the first namespace as the default
  • The namespaces URL is passed through the /me endpoint response to the frontend

Reviewed changes

Copilot reviewed 5 out of 5 changed files in this pull request and generated 8 comments.

Show a summary per file
File Description
backend/pkg/config/config.go Added MeNamespacesURL configuration parameter and DefaultMeNamespacesURL constant, updated ApplyMeDefaults to handle the new parameter
backend/pkg/auth/auth.go Added NamespacesURL field to MeHandlerOptions, updated HandleMe and writeMeResponse to pass the namespaces URL through to the response
backend/cmd/server.go Added meNamespacesURL field to configuration and incomplete comment block
backend/cmd/headlamp.go Added meNamespacesURL field and logging for the new configuration parameter
frontend/src/components/App/TopBar.tsx Added fetch logic to retrieve namespaces from the configured URL and store them in cluster settings with the first namespace set as default

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 127 to 136
if (json.namespaces && Array.isArray(json.namespaces)) {
currentClusterSettings.allowedNamespaces = json.namespaces;
if (
currentClusterSettings.allowedNamespaces &&
currentClusterSettings.allowedNamespaces.length > 0
) {
currentClusterSettings.defaultNamespace =
currentClusterSettings.allowedNamespaces[0];
}
storeClusterSettings(clusterName, currentClusterSettings);
Copy link

Copilot AI Dec 31, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The namespace values from the API are not validated before being stored in cluster settings. The codebase validates namespace formats in other places using the isValidNamespaceFormat function (see frontend/src/components/App/Settings/util.tsx:17-27). Consider validating each namespace string in the array to ensure they conform to DNS-1123 label format before storing them, to prevent invalid namespace names from breaking the UI.

Copilot uses AI. Check for mistakes.
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there's actually a use case for having an invalid formatted namespace, when there are no allowed namespaces returning a single namespace that can't exist because its invalidly formatted doesn't break anything but also doesn't present the user with excess 403 errros

@k8s-ci-robot k8s-ci-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Jan 6, 2026
mlbiam and others added 20 commits January 6, 2026 13:00
…paces and the default namespace if available
…add-digital-ocean-to-platforms

docs: Update DigitalOcean Kubernetes status to confirmed working
@k8s-ci-robot k8s-ci-robot added size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. and removed size/L Denotes a PR that changes 100-499 lines, ignoring generated files. labels Jan 6, 2026
@k8s-ci-robot k8s-ci-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/XXL Denotes a PR that changes 1000+ lines, ignoring generated files. labels Jan 6, 2026
@sniok
Copy link
Contributor

sniok commented Jan 6, 2026

Hi, thanks for contributing to headlamp!

I want to suggest that this functionality can be implemented as a plugin, if this is something you need soon. If you take just the frontend code you've added to the TopBar and put in the a plugin that should work.


I don't think this solution for distributing settings for headlamp has been properly discussed yet. To be honest I'm more leaning towards having some kind of declarative way of defining this, like a configmap or a secret.

This solution is not very user friendly because it requires administrators to develop a new web service just for the sole reason of providing allowed namespaces.
While there's nothing wrong with this I think that's not going to be convenient for most people who deploy headlamp.

We also want to make this mechanism of sharing configs available to plugins, which this solution won't be able to accommodate.
In current form it doesn't allow to provide different namespaces to different users which I think would be quite useful.

For the reasons listed above I don't think this approach should be in headlamp in the current form.

I'd like to hear what other think about this @yolossn @ashu8912 @illume

@mlbiam
Copy link
Contributor Author

mlbiam commented Jan 6, 2026

@sniok

To be honest I'm more leaning towards having some kind of declarative way of defining this, like a configmap or a secret.

The problem with this a declaritive approach will come in a multitenant environment where access is determined dynamically by the identity provider (generally based on a user's groups).

This solution is not very user friendly because it requires administrators to develop a new web service just for the sole reason of providing allowed namespaces.

i'll say it lines up with the /me configuration. The scope of this change is for running behind a reverse proxy, rather then locally.

In current form it doesn't allow to provide different namespaces to different users which I think would be quite useful.

The reverse proxy is responsible for providing the list of namespaces, generally based on the user's identity making it generally simple to make sure that only the namespaces listed are the ones available to the user. I've already tested this and it works great with OpenUnison, where the service provides different results based on the logged in user.

@sniok
Copy link
Contributor

sniok commented Jan 6, 2026

The reverse proxy is responsible for providing the list of namespaces, generally based on the user's identity making it generally simple to make sure that only the namespaces listed are the ones available to the user. I've already tested this and it works great with OpenUnison, where the service provides different results based on the logged in user.

Okay I misunderstood it, that makes a lot more sense. In that case what if that endpoint was responsible for generic user configuration instead of just allowed namespaces? It could be something like "me User Config URL" that responds with { allowedNamespaces: [1,2,3], otherOptions... } ? That way we could handle some other use cases in the future.

@mlbiam
Copy link
Contributor Author

mlbiam commented Jan 6, 2026

In that case what if that endpoint was responsible for generic user configuration instead of just allowed namespaces?

So change it to config instead of namespaces so it's more generic? I'm OK with that. pretty easy to do

@joaquimrocha
Copy link
Contributor

I agree with @sniok . We have identified a few cases where we need centralized configuration, like "AI engines/endpoints", allowed namespaces, etc.
My rough idea is that this is something that be done via a specific namespace that's readable by all, called "headlamp-tools", and then we can have a specific ConfigMap with configuration. This is a basic idea so I think we should have an RFC for it and discuss with others in the community.
I am happy to start this discussion.

@mlbiam
Copy link
Contributor Author

mlbiam commented Jan 7, 2026

My rough idea is that this is something that be done via a specific namespace that's readable by all, called "headlamp-tools", and then we can have a specific ConfigMap with configuration.

The issue with anything sourced from the API server in this use case is that the allowed namespaces in a multitenant environment will be dynamically generated based on the logged in user. A static configuration won't be able to support that level of configuration. Since the identity provider is what generally "owns" this information, it's best get that from an API or a header, though given the architecture a header won't work with the frontend.

This is a basic idea so I think we should have an RFC for it and discuss with others in the community.

happy to be part of this discussion. to @sniok 's point about making the URL more generic, that makes sense to me. I'd also think adding this to the ME url would be a good idea too. I didn't do that originally because that seems to be based off of an oauth2proxy specific feature, but seems like it would be a better place then its own URL.

@illume
Copy link
Contributor

illume commented Jan 7, 2026

I think this is the issue with the config discussion Joaquim is talking about?

@ashu8912
Copy link
Member

ashu8912 commented Jan 8, 2026

Adding my thoughts:
This works for setups where the identity provider already manages namespace assignments (like OpenUnison), but it won't help the more common case where users log into Kubernetes directly and can't list namespaces due to RBAC.
That said, I think it's still worth considering as an interim solution. It solves a real problem for identity providers that support namespace fetching, and we can work on a more general approach to the allowedNamespaces problem separately.

@illume
Copy link
Contributor

illume commented Jan 8, 2026

It solves a real problem for identity providers that support namespace fetching, and we can work on a more general approach to the allowedNamespaces problem separately.

The identity provider is one really good place to supply allowed namespaces. This is where users and groups are defined, and therefore where allowed namespaces should be set.

Okay I misunderstood it, that makes a lot more sense. In that case what if that endpoint was responsible for generic user configuration instead of just allowed namespaces? It could be something like "me User Config URL" that responds with { allowedNamespaces: [1,2,3], otherOptions... } ? That way we could handle some other use cases in the future.

to @sniok 's point about making the URL more generic, that makes sense to me. I'd also think adding this to the ME url would be a good idea too. I didn't do that originally because that seems to be based off of an oauth2proxy specific feature, but seems like it would be a better place then its own URL.

Yes, I was also wondering about adding the config in the existing me URL. I helped on this, but @skoeva worked on this mostly. @skoeva what do you reckon?

I don’t think this would break anything and would simplify getting config from the identity provider in one place. So it gets my +1 too.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. size/L Denotes a PR that changes 100-499 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Reverse Proxy: support an "allowed namespaces" service

9 participants