Setup your Identity Provider with SAML
Auth service works with an identity provider to authenticate users. Before configuring the Auth service for SAML authentication, you need to set up an identity provider. In this tutorial, we'll use Auth0 as an example of an identity provider.
Here is a diagram to explain the flow of the authentication process.
- Complete Quickstart first If you haven't yet built the Inventory Management System app from our template.
- See Core concepts to get an overview of Workspace, Organization, Application and Service.
Tutorial steps
- Setting up Auth0
- Setting up Auth service
- Apply the change using
tailorctl
1. Setting up Auth0
If you don't have an Auth0 account, sign up for a free account at Auth0.
After creating an account, navigate to Applications
and select your application. Select Addons
tab to enable SAML2 WEB APP
.
After enabling the SAML2 WEB APP
, click on the addon and select settings tab, enter http://tailorctl.tailor.tech:8086/callback
into the Application Callback URL
.
Enter the following setting in the Settings
section. Here, we are using an email address as a user identifier. You can update the settings to use a different identifier.
Scroll to the bottom of the tab and save the settings.
<span><span style="color: var(--shiki-color-text)">{</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-function)">"nameIdentifierFormat"</span><span style="color: var(--shiki-token-function)">:</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string-expression)">"urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress"</span><span style="color: var(--shiki-token-string)">,</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-function)">"nameIdentifierProbes"</span><span style="color: var(--shiki-token-function)">:</span><span style="color: var(--shiki-color-text)"> [</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-function)">"http://schemas.xmlsoap.org/ws/2005/05/identity/claims/emailaddress"</span></span>
<span><span style="color: var(--shiki-color-text)"> ]</span></span>
<span><span style="color: var(--shiki-color-text)">}</span></span>
<span></span>
Now, we are ready to set up the Auth service.
2. Setting up Auth service
You can locate auth.cue
file in the services/auth
directory within your application.
This file contains the configuration for the Auth service.
<span><span style="color: var(--shiki-token-keyword)">package</span><span style="color: var(--shiki-color-text)"> auth</span></span>
<span></span>
<span><span style="color: var(--shiki-token-keyword)">import</span><span style="color: var(--shiki-color-text)"> (</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">github.com/tailor-platform/tailorctl/schema/v2/auth</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">github.com/tailor-platform/tailorctl/schema/v2/secretmanager</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">tailor.build/template/environment</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">tailor.build/template/services/tailordb</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> tailordbType </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">tailor.build/template/services/tailordb/type</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)">)</span></span>
<span></span>
<span><span style="color: var(--shiki-color-text)">auth.#Spec </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> Namespace: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">my-auth</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> IdProviderConfigs: [</span></span>
<span><span style="color: var(--shiki-color-text)"> auth.#IDProviderConfig </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> Name: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">ims-auth</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> Config: auth.#SAML </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> MetadataURL: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)"><metadata_url></span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> SpCertBase64: secretmanager.#SecretValue </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> VaultName: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">default</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> SecretKey: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">saml-cert</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> }</span></span>
<span><span style="color: var(--shiki-color-text)"> SpKeyBase64: secretmanager.#SecretValue </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> VaultName: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">default</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> SecretKey: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">saml-key</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> }</span></span>
<span><span style="color: var(--shiki-color-text)"> }</span></span>
<span><span style="color: var(--shiki-color-text)"> }</span><span style="color: var(--shiki-token-punctuation)">,</span></span>
<span><span style="color: var(--shiki-color-text)"> ]</span></span>
<span><span style="color: var(--shiki-color-text)"> UserProfileProvider: auth.#UserProfileProviderType.TailorDB</span></span>
<span><span style="color: var(--shiki-color-text)"> UserProfileProviderConfig: auth.#TailorDBProviderConfig </span><span style="color: var(--shiki-token-keyword)">&</span><span style="color: var(--shiki-color-text)"> {</span></span>
<span><span style="color: var(--shiki-color-text)"> Namespace: tailordb.Namespace</span></span>
<span><span style="color: var(--shiki-color-text)"> Type: tailordbType.User.Name</span></span>
<span><span style="color: var(--shiki-color-text)"> UsernameField: </span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">email</span><span style="color: var(--shiki-color-text)">"</span></span>
<span><span style="color: var(--shiki-color-text)"> AttributesFields: [</span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-token-string-expression)">userAttributes</span><span style="color: var(--shiki-color-text)">"</span><span style="color: var(--shiki-color-text)">]</span></span>
<span><span style="color: var(--shiki-color-text)"> }</span></span>
<span><span style="color: var(--shiki-color-text)">}</span></span>
<span></span>
To locate your MetadataURL
, scroll to the bottom of the Settings
page of the application and click on Advanced Settings
. Then, select the Endpoints
tab and locate SAML Metadata URL
.
Replace the MetadataURL
in auth.cue
with your Auth0 values.
To create your own certificate and key and store it in vault, follow the steps mentioned below.
- You need to create an RSA private key to create your certificate signing request (CSR). To create your private key, use the openssl genrsa command:
<span><span style="color: var(--shiki-token-function)">openssl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">genrsa</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-constant)">2048</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-keyword)">></span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">privatekey.pem</span></span>
<span></span>
- A CSR is a file you send to a certificate authority (CA) to apply for a digital server certificate. To create a CSR, use the openssl req command:
<span><span style="color: var(--shiki-token-function)">openssl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">req</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-new</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-key</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">privatekey.pem</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-out</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">csr.pem</span></span>
<span></span>
- To sign the certificate, use the openssl x509 command:
<span><span style="color: var(--shiki-token-function)">openssl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">x509</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-req</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-days</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-constant)">365</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-in</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">csr.pem</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-signkey</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">privatekey.pem</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-out</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">public.crt</span></span>
<span></span>
Next, you need to store your SpCertBase64
and SpKeyBase64
in the secret manager.
To store the secret, you need to create a vault and a key in the secret manager.
Create a vault
named default
by running the following command.
<span><span style="color: var(--shiki-token-function)">tailorctl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">workspace</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">vault</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">create</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--name</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">default</span></span>
<span></span>
Your vault name can only contain lowercase letters (a-z), numbers (0-9), and hyphens (-). It must start and end with a letter or number and be between 2 and 62 characters long.
Run the following commands to store SAML certificate and key in the vault.
<span><span style="color: var(--shiki-token-function)">tailorctl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">workspace</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">vault</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">secret</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">create</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--name</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">saml-cert</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--vault</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">default</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--value</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string-expression)">$(</span><span style="color: var(--shiki-token-function)">cat</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-string)">public.crt</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-keyword)">|</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-function)">base64</span><span style="color: var(--shiki-token-string-expression)">)</span></span>
<span><span style="color: var(--shiki-token-function)">tailorctl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">workspace</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">vault</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">secret</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">create</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--name</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">saml-key</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--vault</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">default</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">--value</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string-expression)">$(</span><span style="color: var(--shiki-token-function)">cat</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-string)">privatekey.pem</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-keyword)">|</span><span style="color: var(--shiki-token-string-expression)"> </span><span style="color: var(--shiki-token-function)">base64</span><span style="color: var(--shiki-token-string-expression)">)</span></span>
<span></span>
3. Apply the change using tailorctl
Generate new workspace CUE file and apply the Auth changes.
<span><span style="color: var(--shiki-token-function)">tailorctl</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">workspace</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">apply</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">-m</span><span style="color: var(--shiki-color-text)"> </span><span style="color: var(--shiki-token-string)">./workspace.cue</span></span>
<span></span>
You can now use your Auth service to manage access to resources.
Learn more
- In the Create user tutorial, we explain how to create users in your application.