Skip to content

DOCSP-34479 - OIDC #537

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

Merged
merged 11 commits into from
Apr 30, 2024
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
144 changes: 144 additions & 0 deletions source/fundamentals/auth.txt
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ Edition are as follows:
- :ref:`MONGODB-CR <mongodb-cr-auth-mechanism>`
- :ref:`MONGODB-AWS <mongodb-aws-auth-mechanism>`
- :ref:`X.509 <x509-auth-mechanism>`
- :ref:`MONGODB-OIDC <java-mongodb-oidc-azure-imds>`

To authenticate using ``Kerberos`` or ``LDAP``, see the
:doc:`Enterprise Authentication Mechanisms guide </fundamentals/enterprise-auth>`.
Expand Down Expand Up @@ -575,3 +576,146 @@ mechanism:
For additional information on configuring your application to use
certificates as well as TLS/SSL options, see our
:doc:`TLS/SSL guide </fundamentals/connection/tls>`.

``MONGODB-OIDC``
~~~~~~~~~~~~~~~~

.. important::

The MONGODB-OIDC authentication mechanism requires MongoDB v7.0 or later running
on a Linux platform.

The following sections describe how to use the MONGODB-OIDC authentication mechanism to
authenticate to various platforms.

For more information about the MONGODB-OIDC authentication mechanism, see
:manual:`OpenID Connect Authentication </core/security-oidc/>` in the MongoDB Server
manual.

.. _java-mongodb-oidc-azure-imds:

Azure IMDS
++++++++++

If your application runs on an Azure VM, or otherwise uses the
`Azure Instance Metadata Service <https://learn.microsoft.com/en-us/azure/virtual-machines/instance-metadata-service>`__
(IMDS), you can authenticate to MongoDB by using the {+driver-short+}'s built-in Azure
support.

You can specify Azure IMDS OIDC authentication on a ``MongoClientSettings`` object either by
using a ``MongoCredential`` object or as part of the connection string. Select the
:guilabel:`Connection String` or :guilabel:`MongoCredential` tab to
see the corresponding syntax.

.. tabs::

.. tab:: Connection String
:tabid: mongodb-azure-imds-connection-string

The following code example shows how to specify Azure IMDS OIDC authenticaton.
Replace the ``<resource>`` placeholder with the percent-encoded application or
service that the OIDC access token is intended for.

.. code-block:: java

MongoClient mongoClient = MongoClients.create("mongodb://<username>@<hostname>:<port>/?authMechanism=MONGODB-OIDC&authMechanismProperties=ENVIRONMENT:azure,TOKEN_RESOURCE:<resource>");

.. tab:: MongoCredential
:tabid: mongodb-azure-mongo-credential

The following code example shows how to specify Azure IMDS OIDC authenticaton.
Replace the ``<username>`` placeholder with the client ID of the Azure managed
identity, and replace the ``<resource>`` placeholder with the percent-encoded
application or service that the OIDC access token is intended for.

.. code-block:: java

MongoCredential credential = MongoCredential.createOidcCredential("<username>")
.withMechanismProperty("ALLOWED_HOSTS", allowedHosts)
Copy link
Contributor Author

Choose a reason for hiding this comment

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

I couldn't information on this property anywhere, beyond it being a List<String>; I'm guessing it's new as part of the OIDC work. It would be good if we could provide some info on it.

Copy link
Collaborator

Choose a reason for hiding this comment

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

It is new, and important, but is only used when a human callback is being used.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

What do we want users to know about it?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

found in auth spec

.withMechanismProperty("TOKEN_RESOURCE", "<resource>")
.withMechanismProperty("ENVIRONMENT", "azure");

MongoClient mongoClient = MongoClients.create(
MongoClientSettings.builder()
.applyToClusterSettings(builder ->
builder.hosts(Arrays.asList(new ServerAddress("<hostname>", <port>))))
.credential(credential)
.build());

.. _java-mongodb-oidc-gcp-imds:

GCP IMDS
++++++++++

If your application runs on a GCP VM, or otherwise uses the
`GCP Instance Metadata Service <https://cloud.google.com/compute/docs/metadata/querying-metadata>`__,
you can authenticate to MongoDB by using {+driver-short+}'s built-in GCP
support.

You can specify GCP IMDS OIDC authentication on a ``MongoClientSettings`` object either by
using a ``MongoCredential`` object or as part of the connection string. Select the
:guilabel:`Connection String` or :guilabel:`MongoCredential` tab to
see the corresponding syntax.

.. tabs::

.. tab:: Connection String
:tabid: mongodb-gcp-imds-connection-string

The following code example shows how to specify GCP IMDS OIDC authentication.
Replace the ``<resource>`` placeholder with the percent-encoded application or
service that the OIDC access token is intended for.

.. code-block:: java

MongoClient mongoClient = MongoClients.create("mongodb://<username>@<hostname>:<port>/?authMechanism=MONGODB-OIDC&authMechanismProperties=ENVIRONMENT:gcp,TOKEN_RESOURCE:<resource>");
Copy link
Collaborator

Choose a reason for hiding this comment

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

Something will need to be said about URI-encoding the resource, once the issue is resolved in this PR.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I followed the PyMongo docs and used "percent-encoded" on line 666 above.


.. tab:: MongoCredential
:tabid: mongodb-gcp-mongo-credential

The following code example shows how to specify GCP IMDS OIDC authentication.
Replace the ``<username>`` placeholder with the client ID of the GCP managed
identity, and replace the ``<resource>`` placeholder with the percent-encoded
application or service that the OIDC access token is intended for.

.. code-block:: java

MongoCredential credential = MongoCredential.createOidcCredential("<username>")
.withMechanismProperty("ALLOWED_HOSTS", allowedHosts)
.withMechanismProperty("TOKEN_RESOURCE", "<resource>")
.withMechanismProperty("ENVIRONMENT", "gcp");

MongoClient mongoClient = MongoClients.create(
MongoClientSettings.builder()
.applyToClusterSettings(builder ->
builder.hosts(Arrays.asList(new ServerAddress("<hostname>", <port>))))
.credential(credential)
.build());

Custom Callback
+++++++++++++++

On some platforms, such as Azure Functions and Azure Kubernetes Service (AKS), you
must define a custom callback method to use OIDC to authenticate.
Your callback method must accept a ``context`` object as a parameter and return
an ``OidcCallbackResult`` object.

The following code example shows how to use the ``"OIDC_CALLBACK"`` property to include
a callback method in your ``MongoCredential`` object. In this example, the callback
retrieves an OIDC token from a file named ``"access-token.dat"`` in the local file system.

.. code-block:: java

MongoCredential credential = new Credential()
.withMechanismProperty("ALLOWED_HOSTS", allowedHosts)
.withMechanismProperty("OIDC_CALLBACK", (context) -> {
Copy link
Contributor Author

Choose a reason for hiding this comment

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

What does this context object look like?

Copy link
Collaborator

Choose a reason for hiding this comment

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

string accessToken = new String(Files.readAllBytes(Paths.get("access-token.dat"));
return new OidcCallbackResult(accessToken, 0);
});

MongoClient mongoClient = MongoClients.create(
MongoClientSettings.builder()
.applyToClusterSettings(builder ->
builder.hosts(Arrays.asList(new ServerAddress("<hostname>", <port>))))
.credential(credential)
.build());