From 055f51c3fc6055609878df6f3696b0733ad06dbe Mon Sep 17 00:00:00 2001 From: Chris Ostrouchov Date: Fri, 11 Feb 2022 17:21:52 -0500 Subject: [PATCH 1/2] Adding security.shared_users_group option for default users group Closes #957 This adds an option for `security.shared_users_group` which is by default False. If True all users created after this option is set True will be added to the `users` group. If any users were created before this option they must manually be added to this group. --- docs/source/installation/configuration.md | 15 +++++++++++---- qhub/deploy.py | 3 +++ qhub/schema.py | 1 + .../main.tf | 17 +++++++++++++++++ .../variables.tf | 6 ++++++ 5 files changed, 38 insertions(+), 4 deletions(-) diff --git a/docs/source/installation/configuration.md b/docs/source/installation/configuration.md index 395729702d..0fe0e590aa 100644 --- a/docs/source/installation/configuration.md +++ b/docs/source/installation/configuration.md @@ -246,11 +246,12 @@ It's still possible to specify `users` and `groups` in the YAML file - in older If specifying users/groups in this way, you can also manually add more users/groups in Keycloak. However, be aware that if users/groups were initially created based on entries in the YAML file, those users/groups will be destroyed if `qhub deploy` is ever run without those users/groups in the file. They may also be recreated after you delete them manually in Keycloak. -Any user is assigned a `primary_group` and optionally -any number of `secondary_groups`. +Any user is assigned a `primary_group` and optionally any number of +`secondary_groups`. ```yaml security: + shared_users_group: true users: example-user: primary_group: users @@ -266,8 +267,14 @@ security: ``` * The `primary_group` is the group name assigned to files that are -written for the user. -* `groups` are a mapping of group name to an empty map (no entries are required within that map any longer). + written for the user. +* `groups` are a mapping of group name to an empty map (no entries are + required within that map any longer). +* `shared_users_group` is an optional key (default False) which + optionally adds all users to a default group named `users`. Only new + users created after this option is enabled will be added to the + `users` group. You will have to manually add existing users to the + `users` group if you chose to enable this option later. #### Admin and Users Group diff --git a/qhub/deploy.py b/qhub/deploy.py index 834b468146..6da4dd5cca 100644 --- a/qhub/deploy.py +++ b/qhub/deploy.py @@ -620,6 +620,9 @@ def provision_06_kubernetes_keycloak_configuration(stage_outputs, config, check= "realm_display_name", realm_id ), "authentication": config["security"]["authentication"], + "default_project_groups": ["users"] + if config["security"].get("shared_users_group") + else [], }, ) diff --git a/qhub/schema.py b/qhub/schema.py index 9d41ee8d50..ba4890f7f2 100644 --- a/qhub/schema.py +++ b/qhub/schema.py @@ -205,6 +205,7 @@ class Keycloak(Base): class Security(Base): authentication: Authentication + shared_users_group: typing.Optional[bool] keycloak: typing.Optional[Keycloak] diff --git a/qhub/template/stages/06-kubernetes-keycloak-configuration/main.tf b/qhub/template/stages/06-kubernetes-keycloak-configuration/main.tf index 11f742be5b..1964b7308c 100644 --- a/qhub/template/stages/06-kubernetes-keycloak-configuration/main.tf +++ b/qhub/template/stages/06-kubernetes-keycloak-configuration/main.tf @@ -11,3 +11,20 @@ resource "keycloak_group" "groups" { realm_id = keycloak_realm.main.id name = each.value } + +resource "keycloak_group" "project_groups" { + for_each = var.default_project_groups + realm_id = keycloak_realm.main.id + + name = each.value + parent_id = keycloak_group.groups["projects"].id +} + + +resource "keycloak_default_groups" "default" { + realm_id = keycloak_realm.main.id + group_ids = [ + for g in var.default_project_groups: + keycloak_group.project_groups[g].id + ] +} diff --git a/qhub/template/stages/06-kubernetes-keycloak-configuration/variables.tf b/qhub/template/stages/06-kubernetes-keycloak-configuration/variables.tf index b38324029a..fde872793a 100644 --- a/qhub/template/stages/06-kubernetes-keycloak-configuration/variables.tf +++ b/qhub/template/stages/06-kubernetes-keycloak-configuration/variables.tf @@ -18,3 +18,9 @@ variable "authentication" { description = "Authentication configuration for keycloak" type = any } + +variable "default_project_groups" { + description = "Set of groups that should exist by default" + type = set(string) + default = [] +} From 8f1c4e82eed123035479d1100d4f07dbbec88f4a Mon Sep 17 00:00:00 2001 From: Dan Lester Date: Sat, 12 Feb 2022 11:00:36 +0000 Subject: [PATCH 2/2] shared_users_group added on 0.4.0 upgrade; docs for users --- docs/source/dev_guide/minikube.md | 23 --------- docs/source/installation/configuration.md | 58 ++--------------------- docs/source/installation/existing.md | 11 ----- docs/source/installation/management.md | 16 +------ qhub/upgrade.py | 3 ++ 5 files changed, 10 insertions(+), 101 deletions(-) diff --git a/docs/source/dev_guide/minikube.md b/docs/source/dev_guide/minikube.md index 4cc66b69f5..bc2b7ed115 100644 --- a/docs/source/dev_guide/minikube.md +++ b/docs/source/dev_guide/minikube.md @@ -199,29 +199,6 @@ Then, initialize the configuration file `qhub-config.yaml` with: ```shell python -m qhub init local --project=thisisatest --domain github-actions.qhub.dev --auth-provider=password --terraform-state=local ``` -## Generate user password -For each user on the `qhub-config.yaml` file needs a password. -A random password is auto generated for the user `example-user` when -the auth provider `password` is run, the value is then printed to the standard output (stdout). - -In case you would like to change the generated password (optional), You can use [bcrypt](https://pypi.org/project/bcrypt/) to generate your own salted password by using the following _Python command_ script: - -```bash -python -c "import bcrypt; print(bcrypt.hashpw(b'admin', bcrypt.gensalt()).decode('utf-8'))" -``` - -`` can be changed to any desired value. This requires the Python package `bcrypt` to be installed in your virtual environment. The password is added to the `qhub-config.yaml` in the users section. - -```yaml - users: - example-user: - uid: 1000 - ... - password: '$2b$12$lAk2Bhw8mu0QJkSecPiABOX2m87RF8N7vv7rBw9JksOgewI2thUuO' - ... - primary_group: users - -``` ## Deploy and render the infrastructure diff --git a/docs/source/installation/configuration.md b/docs/source/installation/configuration.md index 0fe0e590aa..de7ac6fa60 100644 --- a/docs/source/installation/configuration.md +++ b/docs/source/installation/configuration.md @@ -242,35 +242,9 @@ security: ### User and group management -It's still possible to specify `users` and `groups` in the YAML file - in older versions of QHub, all users had to be specified in this way. +Groups and users of QHub are all defined in Keycloak. As above, access Keycloak as the `root` user, noting that the `root` user is not actually a QHub user - you cannot access the main features of QHub such as JupyterLab with at user. It is only for Keycloak management. -If specifying users/groups in this way, you can also manually add more users/groups in Keycloak. However, be aware that if users/groups were initially created based on entries in the YAML file, those users/groups will be destroyed if `qhub deploy` is ever run without those users/groups in the file. They may also be recreated after you delete them manually in Keycloak. - -Any user is assigned a `primary_group` and optionally any number of -`secondary_groups`. - -```yaml -security: - shared_users_group: true - users: - example-user: - primary_group: users - secondary_groups: - - billing - password: plaintextpasswd - dharhas: - primary_group: admin - groups: - users: - admin: - billing: -``` - -* The `primary_group` is the group name assigned to files that are - written for the user. -* `groups` are a mapping of group name to an empty map (no entries are - required within that map any longer). -* `shared_users_group` is an optional key (default False) which +* `security.shared_users_group` is an optional key (default False) which optionally adds all users to a default group named `users`. Only new users created after this option is enabled will be added to the `users` group. You will have to manually add existing users to the @@ -278,14 +252,10 @@ security: #### Admin and Users Group -The admin group has special significance. If a user's `primary_group` -is admin they will be able to access the jupyterhub admin page. The -admin page allows a user to stop user's servers and launch a given +The admin group has special significance in QHub, and will always be automatically created in Keycloak in every deployment. If a user is a member of the Keycloak `admin` group they will be able to access the jupyterhub admin page. The admin page allows a user to stop user's servers and launch a given user's server and impersonate them. -All users must be a member of the `users` group. - -Both `admin` and `users` groups will be created even if not specified in the YAML file. +If `security.shared_users_group` is `true` then all users will become members of the `users` group. ## Provider Infrastructure @@ -822,25 +792,7 @@ security: client_id: CLIENT_ID client_secret: CLIENT_SECRET - users: - example-user: - primary_group: users - secondary_groups: - - billing - dharhas: - primary_group: admin - tonyfast: - primary_group: admin - prasunanand: - primary_group: admin - aktech: - primary_group: users - secondary_groups: - - admin - groups: - users: - admin: - billing: + shared_users_group: true digital_ocean: region: nyc3 diff --git a/docs/source/installation/existing.md b/docs/source/installation/existing.md index 408c110280..f146b04b82 100644 --- a/docs/source/installation/existing.md +++ b/docs/source/installation/existing.md @@ -124,17 +124,6 @@ security: client_id: client_secret: oauth_callback_url: https:///hub/oauth_callback - users: - example_user: - uid: 1000 - primary_group: admin - secondary_groups: - - users - groups: - users: - gid: 100 - admin: - gid: 101 default_images: jupyterhub: quansight/qhub-jupyterhub:v0.3.13 jupyterlab: quansight/qhub-jupyterlab:v0.3.13 diff --git a/docs/source/installation/management.md b/docs/source/installation/management.md index 37a08a3a1e..85d6ec733a 100644 --- a/docs/source/installation/management.md +++ b/docs/source/installation/management.md @@ -2,21 +2,9 @@ ## Add users to QHub -One of the first things you might want to do is to **add new users** to your QHub. Any type of supported authorization from Auth0 can be used as a username. Below is an example configuration of two users: +One of the first things you might want to do is to **add new users** to your QHub. -```yaml - joeuser@example.com: - uid: 1000000 - primary_group: users - secondary_groups: - - billing - - admin - janeuser@example.com: - uid: 1000001 - primary_group: users -``` - -As seen above, each username has a unique `uid` and a `primary_group`. Optional `secondary_groups` may also be set for each user. This can be done through the Keycloak web console. See [Adding a QHub user](./login.md#adding-a-qhub-user) for details. +This can be done through the Keycloak web console. See [Adding a QHub user](./login.md#adding-a-qhub-user) for details. ## Upgrades and dependencies management diff --git a/qhub/upgrade.py b/qhub/upgrade.py index 98a6013eba..66a11c3683 100644 --- a/qhub/upgrade.py +++ b/qhub/upgrade.py @@ -301,6 +301,9 @@ def _version_specific_upgrade( if "users" in security: del security["users"] if "groups" in security: + if "users" in security["groups"]: + # Ensure the users default group is added to Keycloak + security["shared_users_group"] = True del security["groups"] # Create root password