-
Notifications
You must be signed in to change notification settings - Fork 304
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Regarding c.KubeSpawner.environment and the EnvVar structure's valueFrom field #306
Regarding c.KubeSpawner.environment and the EnvVar structure's valueFrom field #306
Comments
what you think about in deployment,yaml of your helm chart?
|
@zlanyi This way would inject hub's POD_IP to hub container. What I need is for singleuser container. |
@qzchenwl no, it's only declaration. What do you want to do? |
@zlanyi I want the notebook server to be able to tell others how to connect to it. (make zmq listen on public IP instead of 127.0.0.1) |
I have same problem. |
I think the key issue is that you want to write env in a more complicated form than just key:value where these are strings, we should perhaps try to support something like this though. Hmmm oh wait okay now i was thinking of the helm chart config values under singleuser.env, but hmmm perhaps you can do this from the config anyhow? Hmmmms eh it would be a technical ugly workaround... hmmmm... mindwrangling... kubespawner has a env field, right? can you do something like you do above, but use the extend function instead on c.KubeSpawner.environment ? |
c.KubeSpawner.environment.extend({
"name": "MY_POD_IP",
"valueFrom": {
"fieldRef": {
"fieldPath": "status.podIP"
}
}
}) I did this from my mobile and memory, please fix typo/indentation etc |
Thanks @consideRatio but this does not work for me. |
@abinet ah, so c.KubeSpawner.environment it is a dictionary rather than an array... and that is a limitation because kubespawner have assumed all environment varibles will be hardcoded strings... Okay, I think this will require kubespawner to adjust. Then, until kubespawner is remade, the ugly option I then think may be required is something like this: hub:
extraConfig:
jupyterlab: |
env = [{
"name": "MY_POD_IP",
"valueFrom": {
"fieldRef": {
"fieldPath": "status.podIP"
}
}
}]
env.extend({'name': key, 'value': value} for key, value in c.KubeSpawner.environment.items())
c.KubeSpawner.extra_container_config = {
"env": env
}
|
@consideRatio we are almost there. But |
@abinet oh, hmmm, oh? If that is the case, perhaps you can run this logic in a pre_spawn_hook then?
|
Thank you @consideRatio! Last point was really the hit. Here is my solution for now:
|
Wieee thanks for sharing this solution!! |
FWIW, I think that something like #461 adding jupyterhub:
singleuser:
extraEnv:
DASK_GATEWAY__CLUSTER__OPTIONS__IMAGE: '{JUPYTER_IMAGE_SPEC}'
... that I want to apply to all profiles. Then I have some profiles (e.g. with GPUs) that should have some extra environment variables. It'd be nice to have
to append (or update / overwrite) those extra environment variables, while keeping the common ones. Would something like a |
@TomAugspurger Wouldn't just setting environment act the same way? Since it's a dictionary, it'll just be updated. |
Oh, I might have been mistaken in how it behaves. I probably assumed without testing that it would be replaced completly, rather than updated. |
Hmmm kubespawner overrides will indeed override the configuration field i think. To adjust config based on profile, i suggest hooks. I dont think it will be viable for maintenance and documentation to add more and more dynamics to manage the same config in kubespawner, like env and extra_env and extra_extra_env or similar. At least if its not made in a config generic way. |
Im on mobile, will probive a concrete example. |
This can be set in hub.extraConfig for example. async def pre_spawn_hook(spawner):
auth_state = await spawner.user.get_auth_state()
user_details = auth_state["oauth_user"]
#
spawner.environment.update(
{
"USER_SOMETHING": user_details.get(user_details["something"], ""),
}
)
c.KubeSpawner.pre_spawn_hook = pre_spawn_hook |
Thanks! I'll try that out. |
In case of resources, you can use from kubernetes import client
def modify_pod_hook(spawner, pod):
pod.spec.containers[0].env.append(client.V1EnvVar("MY_POD_IP", None, client.V1EnvVarSource(field_ref = client.V1ObjectFieldSelector(field_path = "status.podIP"))))
pod.spec.containers[0].env.append(client.V1EnvVar("MY_POD_NAME", None, client.V1EnvVarSource(field_ref = client.V1ObjectFieldSelector(field_path = "metadata.name"))))
pod.spec.containers[0].env.append(client.V1EnvVar("MY_CPU_REQUEST", None, client.V1EnvVarSource(resource_field_ref = client.V1ResourceFieldSelector(resource = "requests.cpu"))))
pod.spec.containers[0].env.append(client.V1EnvVar("MY_CPU_LIMIT", None, client.V1EnvVarSource(resource_field_ref = client.V1ResourceFieldSelector(resource = "limits.cpu"))))
pod.spec.containers[0].env.append(client.V1EnvVar("MY_MEMORY_REQUEST", None, client.V1EnvVarSource(resource_field_ref = client.V1ResourceFieldSelector(resource = "requests.memory"))))
pod.spec.containers[0].env.append(client.V1EnvVar("MY_MEMORY_LIMIT", None, client.V1EnvVarSource(resource_field_ref = client.V1ResourceFieldSelector(resource = "limits.memory"))))
return pod
c.KubeSpawner.modify_pod_hook = modify_pod_hook |
I edited @abinet 's code slightly, and got import os
async def modify_pod_hook(spawner, pod):
output = os.popen("dbus-launch --sh-syntax").read().split('\n')
pod.spec.containers[0].env.append("os_asdf", "os_asdf")
return pod
c.KubeSpawner.modify_pod_hook = modify_pod_hook |
Renove the async keyword |
@consideRatio thanks, it worked. It should be a dictionary format including name and value key. import subprocess
def modify_pod_hook(spawner, pod):
pod.spec.containers[0].env.append({"name": "os_asdf", "value": output})
return pod
c.KubeSpawner.modify_pod_hook = modify_pod_hook |
@cointreauu your solution is perfect, but you don't need to import subprocess module :) def modify_pod_hook(spawner, pod):
pod.spec.containers[0].env.append({"name": "os_asdf", "value": "envvalue"})
return pod
c.KubeSpawner.modify_pod_hook = modify_pod_hook |
I tried
But this will overwrite the default env, and cause error. Any way to append env instead of replace all env?
The text was updated successfully, but these errors were encountered: