Skip to content

Commit

Permalink
By default, in dev-realm.json, map only realm roles into access token…
Browse files Browse the repository at this point in the history
… in cryptomator and cryptomator hub clients, but not client roles. Separate roles in MinIO: bucket creation (cryptomator and cryptomatorhub cliients) and bucket access (for cryptomatorvaults client) (#10 #41)
  • Loading branch information
chenkins committed Nov 20, 2023
1 parent 041fdfb commit 5fc0185
Show file tree
Hide file tree
Showing 9 changed files with 104 additions and 73 deletions.
47 changes: 25 additions & 22 deletions backend/CIPHERDUCK.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,53 +28,56 @@ This is not a problem as we leave the claim specifying the vault unset or pointi

```shell
mc alias set myminio http://127.0.0.1:9000 minioadmin minioadmin
mc admin policy create myminio cipherduck src/main/resources/cipherduck/setup/minio/cipherduckpolicy.json
mc admin policy create myminio cipherduckcreatebucket src/main/resources/cipherduck/setup/minio/createbucketpolicy.json
mc admin policy create myminio cipherduckaccessbucket src/main/resources/cipherduck/setup/minio/accessbucketpolicy.json
```

Add a new OIDC provider using the policy:

TODO https://github.com/chenkins/cipherduck-hub/issues/41 after introducing cryptomatorvaults client, we can separate
vault creation and vault access policy in minio

```shell
mc idp openid add myminio cryptomator \
config_url="https://testing.hub.cryptomator.org/kc/realms/cipherduck/.well-known/openid-configuration" \
client_id="cryptomator" \
client_secret="ignore-me" \
role_policy="cipherduck"
role_policy="cipherduckcreatebucket"
mc idp openid add myminio cryptomatorhub \
config_url="https://testing.hub.cryptomator.org/kc/realms/cipherduck/.well-known/openid-configuration" \
client_id="cryptomatorhub" \
client_secret="ignore-me" \
role_policy="cipherduck"
role_policy="cipherduckcreatebucket"
mc idp openid add myminio cryptomatorvaults \
config_url="https://testing.hub.cryptomator.org/kc/realms/cipherduck/.well-known/openid-configuration" \
client_id="cryptomatorvaults" \
client_secret="ignore-me" \
role_policy="cipherduck"
role_policy="cipherduckaccessbucket"
mc admin service restart myminio
```

Extract the policy ARN:

```shell
mc idp openid ls myminio feature/cipherduck
╭───────────────────────────────────────────────────────────────────────╮
│ On? Name RoleARN │
│ 🔴 (default) │
│ 🟢 cryptomator arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE │
│ 🟢 cryptomatorhub arn:minio:iam:::role/HGKdlY4eFFsXVvJmwlMYMhmbnDE │
╰───────────────────────────────────────────────────────────────────────╯


mc idp openid info myminio feature/cipherduck
╭───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│ client_id: cryptomator (environment) │
│ config_url: https://login1.staging.cryptomator.cloud/realms/cipherduck/.well-known/openid-configuration (environment)│
│ enable: on │
│ roleARN: arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE │
│role_policy: cryptomator (environment) │
╰───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯
mc idp openid ls myminio feature/cipherduck
╭──────────────────────────────────────────────────────────────────────────╮
│ On? Name RoleARN │
│ 🔴 (default) │
│ 🟢 cryptomator arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE │
│ 🟢 cryptomatorhub arn:minio:iam:::role/HGKdlY4eFFsXVvJmwlMYMhmbnDE │
│ 🟢 cryptomatorvaults arn:minio:iam:::role/Hdms6XDZ6oOpuWYI3gu4gmgHN94 │
╰──────────────────────────────────────────────────────────────────────────╯


mc idp openid info myminio cryptomator feature/cipherduck
╭─────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│ client_id: cryptomator │
│client_secret: ignore-me │
│ config_url: https://testing.hub.cryptomator.org/kc/realms/cipherduck/.well-known/openid-configuration │
│ enable: on │
│ roleARN: arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE │
│ role_policy: cipherduckcreatebucket │
╰─────────────────────────────────────────────────────────────────────────────────────────────────────────╯

```

### Hub configuration
Expand Down
13 changes: 4 additions & 9 deletions backend/config/application.properties
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,9 @@ backends.backends[0].bucket-prefix=cipherduck
backends.backends[0].region=eu-central-1
backends.backends[0].regions=eu-west-1,eu-west-2,eu-west-3,eu-north-1,eu-south-1,eu-south-2,eu-central-1,eu-central-2
backends.backends[0].with-path-style-access-enabled=true
# (role for cryptomatorhub client)
# (role for cryptomatorhub client -> bucket creation from hub frontend)
backends.backends[0].sts-role-arn-hub=arn:minio:iam:::role/HGKdlY4eFFsXVvJmwlMYMhmbnDE
# (role for cryptomator client)
# (role for cryptomator client -> bucket creation from Desktop client)
backends.backends[0].sts-role-arn-client=arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE
backends.backends[0].sts-endpoint=http://minio:9000
#
Expand All @@ -38,13 +38,8 @@ backends.backends[0].jwe.provider=s3-sts-http
backends.backends[0].jwe.hostname=minio
backends.backends[0].jwe.port=9000
backends.backends[0].jwe.sts-endpoint=http://minio:9000
#
#
# (2) bookmark aka. Host
# (2a) bookmark direct fields:
# (2b) boookmark custom properties:
# role for cryptomator client
backends.backends[0].jwe.sts-role-arn=arn:minio:iam:::role/IqZpDC5ahW_DCAvZPZA4ACjEnDE
# (role for cryptomatorvaults client -> after token-exchange)
backends.backends[0].jwe.sts-role-arn=arn:minio:iam:::role/Hdms6XDZ6oOpuWYI3gu4gmgHN94
#
#
################
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,6 @@

import com.fasterxml.jackson.annotation.JsonProperty;

import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Optional;

Expand Down Expand Up @@ -45,7 +43,6 @@ public interface StorageConfig {
VaultJWEBackend jwe();



}


Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,6 @@
@ApplicationScoped
public class KeycloakGrantAccessToVault {


// TODO https://github.com/chenkins/cipherduck-hub/issues/41 clean-up dev-realm.json: do we need everything in realm-management?

private static final Logger LOG = Logger.getLogger(KeycloakGrantAccessToVault.class);

public static void keycloakPrepareVault(final SyncerConfig syncerConfig, final String vaultId, final StorageConfig storageConfig, final String userOrGroupId, final String clientId) {
Expand Down
2 changes: 1 addition & 1 deletion backend/src/main/resources/application.properties
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ hub.keycloak.oidc.cryptomator-vaults-client-id=cryptomatorvaults
%dev.quarkus.keycloak.devservices.port=8180
%dev.quarkus.keycloak.devservices.service-name=quarkus-cryptomator-hub
%dev.quarkus.keycloak.devservices.image-name=ghcr.io/cryptomator/keycloak:22.0.5
# TODO https://github.com/chenkins/cipherduck-hub/issues/41 add to Dockerfile as well?
# TODO review add to Dockerfile as well?
# https://github.com/quarkusio/quarkus/blob/596d9ae7a76cf529d24594a82b7c540030799dac/extensions/oidc/deployment/src/main/java/io/quarkus/oidc/deployment/devservices/keycloak/DevServicesConfig.java#L30
# https://github.com/quarkusio/quarkus/blob/main/extensions/oidc/deployment/src/main/java/io/quarkus/oidc/deployment/devservices/keycloak/KeycloakDevServicesProcessor.java#L110
# https://github.com/cryptomator/cryptomator.github.io/blob/52ac36a1db04ce1aa6db41f0aeb0a0f2b76b68b5/assets/js/hubsetup.js#L112
Expand Down
Original file line number Diff line number Diff line change
@@ -1,26 +1,6 @@
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"s3:CreateBucket",
"s3:GetBucketPolicy"
],
"Resource": [
"arn:aws:s3:::cipherduck*/"
]
},
{
"Effect": "Allow",
"Action": [
"s3:PutObject"
],
"Resource": [
"arn:aws:s3:::cipherduck*/*/",
"arn:aws:s3:::cipherduck*/vault.cryptomator"
]
},
{
"Effect": "Allow",
"Action": [
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"s3:CreateBucket",
"s3:GetBucketPolicy"
],
"Resource": [
"arn:aws:s3:::cipherduck*/"
]
},
{
"Effect": "Allow",
"Action": [
"s3:PutObject"
],
"Resource": [
"arn:aws:s3:::cipherduck*/*/",
"arn:aws:s3:::cipherduck*/vault.cryptomator"
]
}
]
}
59 changes: 45 additions & 14 deletions backend/src/main/resources/dev-realm.json
Original file line number Diff line number Diff line change
Expand Up @@ -302,20 +302,22 @@
"jsonType.label": "String",
"multivalued": "true"
}
},
{
"name": "client roles",
"protocol": "openid-connect",
"protocolMapper": "oidc-usermodel-client-role-mapper",
"consentRequired": false,
"config": {
"access.token.claim": "true",
"claim.name": "resource_access.${client_id}.roles",
"jsonType.label": "String",
"multivalued": "true",
"usermodel.clientRoleMapping.clientId": "cryptomatorhub"
}
}
],
"defaultClientScopes": [
"aud",
"web-origins",
"phone",
"profile",
"vaults",
"email"
],
"optionalClientScopes": [
"acr",
"address",
"roles",
"offline_access",
"microprofile-jwt"
]
},
{
Expand All @@ -337,7 +339,36 @@
"attributes": {
"pkce.code.challenge.method": "S256"
},
"directAccessGrantsEnabled": false
"directAccessGrantsEnabled": false,
"protocolMappers": [
{
"name": "realm roles",
"protocol": "openid-connect",
"protocolMapper": "oidc-usermodel-realm-role-mapper",
"consentRequired": false,
"config": {
"access.token.claim": "true",
"claim.name": "realm_access.roles",
"jsonType.label": "String",
"multivalued": "true"
}
}
],
"defaultClientScopes": [
"aud",
"web-origins",
"phone",
"profile",
"vaults",
"email"
],
"optionalClientScopes": [
"acr",
"address",
"offline_access",
"microprofile-jwt",
"roles"
]
},
{
"id": "367e3049-23ee-4714-a7ed-75e61d027d02",
Expand Down
5 changes: 4 additions & 1 deletion frontend/src/components/CreateVaultS3.vue
Original file line number Diff line number Diff line change
Expand Up @@ -503,7 +503,8 @@ async function createVault() {
return;
}
// TODO review what happens if bucket creation fails after successful vault creation? - merge with PUT vault service?
// N.B. the access tokens for cryptomator and cryptomator hub clients do only have realm roles added to them, but not client roles.
// We use client roles for vaults shared with a user. So this setup prevents access tokens from growing with new vaults.
const token = await authPromise.then(auth => auth.bearerToken());
// https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/clients/client-sts/classes/stsclient.html
Expand All @@ -515,6 +516,7 @@ async function createVault() {
// https://docs.aws.amazon.com/AWSJavaScriptSDK/v3/latest/clients/client-sts/classes/assumerolewithwebidentitycommand.html
// https://docs.aws.amazon.com/STS/latest/APIReference/API_AssumeRoleWithWebIdentity.html
// N.B. almost zero trust: add inline policy to pass only credentials allowing for creating the specified bucket in the backend
const assumeRoleWithWebIdentityArgs = {
// Required. The OAuth 2.0 access token or OpenID Connect ID token that is provided by the
// identity provider.
Expand Down Expand Up @@ -554,6 +556,7 @@ async function createVault() {
.send(new AssumeRoleWithWebIdentityCommand(assumeRoleWithWebIdentityArgs));
const rootDirHash = await vaultKeys.value.hashDirectoryId('');
// TODO review what happens if bucket creation fails after successful vault creation? - merge with PUT vault service?
await backend.storage.put(vaultId, {
vaultId: vaultId,
storageConfigId: config.id,
Expand Down

0 comments on commit 5fc0185

Please sign in to comment.