Users unable to save items in private tenancy

Versions (relevant - OpenSearch/Dashboard/Server OS/Browser):

OpenSearch 3.2.0

Dashboard: 3.2.0

Describe the issue:

I have a Opensearch cluster that uses TLS authentication to authenticate Dashboards to OpenSearch, Users are authenticated via OpenID. I have enabled Multi tenancy and can see the private tenancy, however when I switch to the private tenant, and create an index / visualisation. It is saved to the global tenant instead of the private.

No index is created for each user

I have seen this post Multitenancy - even with separated roles and tenants everything saved ends up in global - #9 by Anthony however all of my values appear to have been updated, but it still isnt working.

Is anybody able to help troubleshoot this issue?

Configuration:

opensearch-dashboards.yml

server:

name: os_dashboards

host: “0.0.0.0”

basePath: “/search” #!!!This line only needed if using Nginx Reverse Proxy

rewriteBasePath: true #!!!This line only needed if using Nginx Reverse Proxy

opensearch:

requestHeadersAllowlist: [“securitytenant”, “Authorization”]

hosts:

- "https://os01:9200"

- "https://os02:9200"

- "https://os03:9200"

ssl:

  verificationMode: none

  certificateAuthorities: \["/usr/share/opensearch-dashboards/config/certificates/ca/ca.pem"\]

  certificate: "/usr/share/opensearch-dashboards/config/certificates/os-dashboards/os-dashboards.pem"

  key: "/usr/share/opensearch-dashboards/config/certificates/os-dashboards/os-dashboards.key"

#logging:

#dest: /usr/share/opensearch-dashboards/logs/opensearch_dashboards.log

# Encrypt traffic between the browser and OpenSearch-Dashboards

server.ssl:

enabled: true

certificateAuthorities: [“/usr/share/opensearch-dashboards/config/certificates/ca/ca.pem”]

certificate: “/usr/share/opensearch-dashboards/config/certificates/os-dashboards/os-dashboards.pem”

key: “/usr/share/opensearch-dashboards/config/certificates/os-dashboards/os-dashboards.key”

#Enable Machine Learning Features

ml_commons_dashboards:

enabled: true

#Multi Tenancy Settings

opensearch_security:

multitenancy:

enabled: true

tenants:

  enable_global: true

  enable_private: true

  preferred: \["Private", "Global"\]

enable_filter: true

readonly_mode.roles: [“kibana_read_only”]

cookie:

secure: false

allow_client_certificates: true

auth:

#type: \["basicauth", "openid"\]

#multiple_auth_enabled: true

type: "openid"

multiple_auth_enabled: false

openid:

scope: "openid profile email"

client_id: ""

client_secret: ""

connect_url: "Auth URL"

base_redirect_url: "https://hostname/search/"

verify_hostnames: false

header: "Authorization"

opensearch.yml

cluster.name: opensearch-cluster

network.host: 0.0.0.0

bootstrap.memory_lock: “true” # when combined with ulimits memlock settings, disables swapping.

cluster.routing.allocation.disk:

threshold_enabled: true

watermark.low: 93%

watermark.high: 95%

discovery.seed_hosts:

  • ‘os01’

  • ‘os02’

  • ‘os03’

cluster.initial_cluster_manager_nodes:

  • ‘os01’

  • ‘os02’

  • ‘os03’

plugins.security:

# Uncomment the following two lines if you would like to store audit logs within OpenSearch.

# audit:

# type: internal_opensearch

ssl:

http:

  enabled: true

  clientauth_mode: OPTIONAL #Could be OPTIONAL or REQUIRED

  pemtrustedcas_filepath: certificates/ca/ca.pem

transport:

  enabled: true

  pemtrustedcas_filepath: certificates/ca/ca.pem

  enforce_hostname_verification: false

allow_unsafe_democertificates: false

allow_default_init_securityindex: true

authcz.admin_dn:

- 'CN=ADMIN'

nodes_dn:

- 'CN=os01'

- 'CN=os02'

- 'CN=os03,'

restapi:

roles_enabled: \["all_access", "security_rest_api_access"\]

system_indices:

enabled: true

indices: \[".opendistro-alerting-config", ".opendistro-alerting-alert\*", ".opendistro-anomaly-results\*", ".opendistro-anomaly-detector\*", ".opendistro-anomaly-checkpoints", ".opendistro-anomaly-detection-state", ".opendistro-reports-\*", ".opendistro-notifications-\*", ".opendistro-notebooks", ".opendistro-asynchronous-search-response\*"\]

config.yml

-–

# This is the main OpenSearch Security configuration file where authentication

# and authorization is defined.

#

# You need to configure at least one authentication domain in the authc of this file.

# An authentication domain is responsible for extracting the user credentials from

# the request and for validating them against an authentication backend like Active Directory for example.

#

# If more than one authentication domain is configured the first one which succeeds wins.

# If all authentication domains fail then the request is unauthenticated.

# In this case an exception is thrown and/or the HTTP status is set to 401.

#

# After authentication authorization (authz) will be applied. There can be zero or more authorizers which collect

# the roles from a given backend for the authenticated user.

#

# Both, authc and auth can be enabled/disabled separately for REST and TRANSPORT layer. Default is true for both.

# http_enabled: true

# transport_enabled: true

#

# For HTTP it is possible to allow anonymous authentication. If that is the case then the HTTP authenticators try to

# find user credentials in the HTTP request. If credentials are found then the user gets regularly authenticated.

# If none can be found the user will be authenticated as an “anonymous” user. This user has always the username “anonymous”

# and one role named “anonymous_backendrole”.

# If you enable anonymous authentication all HTTP authenticators will not challenge.

#

#

# Note: If you define more than one HTTP authenticators make sure to put non-challenging authenticators like “proxy” or “clientcert”

# first and the challenging one last.

# Because it’s not possible to challenge a client with two different authentication methods (for example

# Kerberos and Basic) only one can have the challenge flag set to true. You can cope with this situation

# by using pre-authentication, e.g. sending a HTTP Basic authentication header in the request.

#

# Default value of the challenge flag is true.

#

#

# HTTP

# basic (challenging)

# proxy (not challenging, needs xff)

# kerberos (challenging)

# clientcert (not challenging, needs https)

# jwt (not challenging)

# host (not challenging) #DEPRECATED, will be removed in a future version.

# host based authentication is configurable in roles_mapping

# Authc

# internal

# noop

# ldap

# Authz

# ldap

# noop

_meta:

type: “config”

config_version: 2

config:

dynamic:

\# Set filtered_alias_mode to 'disallow' to forbid more than 2 filtered aliases per index

\# Set filtered_alias_mode to 'warn' to allow more than 2 filtered aliases per index but warns about it (default)

\# Set filtered_alias_mode to 'nowarn' to allow more than 2 filtered aliases per index silently

#filtered_alias_mode: warn

#do_not_fail_on_forbidden: false



kibana:

  multitenancy_enabled: true

  private_tenant_enabled: true

  default_tenant: "Global"

  server_username: os_dashboards

  index: '.opensearch_dashboards'

authc:

  basic_internal_auth_domain:

    description: "Authenticate via HTTP Basic against internal users database"

    http_enabled: true

    transport_enabled: true

    order: 4

    http_authenticator:

      type: basic

      challenge: true

    authentication_backend:

      type: intern

  clientcert_auth_domain:

    description: "Authenticate via SSL client certificates"

    http_enabled: true

    transport_enabled: true

    order: 2

    http_authenticator:

      type: clientcert

      config:

        username_attribute: cn #optional, if omitted DN becomes username

      challenge: false

    authentication_backend:

      type: noop

  openid_auth_domain:

    http_enabled: true

    transport_enabled: true

    order: 1

    http_authenticator:

      type: openid

      challenge: false

      config:

        subject_key: preferred_username

        roles_key: groups

        openid_connect_url: Auth URL

        openid_connect_idp:

          enable_ssl: false

          verify_hostnames: false

    authentication_backend:

      type: noop

roles_mapping.yml

_meta:

type: “rolesmapping”

config_version: 2

kibana_server:

reserved: true

users:

- "os-dashboards"

Relevant Logs or Screenshots:

Hi, when posting configurations, please use the code button and not the quote button.

Use yaml format in the dropdown.

That makes is possible to read your configuration.

kibana_server:
  reserved: true
  users:
    - "os-dashboards"

Br Sebastian

@Evergreen1270 Its very difficult to read the above configuration blocks, as the indentation is incorrect. But in general, it would appear that opensearch_dashboards is attempting to authenticate using certificate, however only openid is configured as possible authentication method. I would recommend to add client_auth as secondary authentication method.

Can you then use curl with OSD certificate and key and check which role is assigned, using the following:

curl -k \
  --cert /path/client.crt \
  --key /path/client.key \
  --cacert /path/root-ca.pem \
  https://<opensearch>:9200/_plugins/_security/authinfo

A more thorough test would be to enable basic_auth instead of openID/client_auth, and test with basic authentication, to see if the issue persists. (using kibanaserver/kibanaserver as username/password for OSD)
If this works, then add client_auth, and then add openID and remove basic_auth. This would indicate at which stage the issue is appearing.

1 Like

I am sorry for the poor formatting. The code button doesnt appear for me in the menu.

I have managed to get this working. I made the following changes

In the config.yml for opensearch, updated the server_username and index to be

server_username: os-dashboards  
index: ".kibana"

I also adjusted the order in which authentication is checked to have SSL auth first (Not sure if this made a difference)

Thanks for the tips, helped me better understand what is taking place under the hood which lead me in the right direction.

1 Like