Checkpoints
Create policies
/ 30
Create and manage policies using CLI commands
/ 35
Policies for Secrets
/ 35
Interacting with Vault Policies
This lab was developed with our partner, Hashicorp. Your personal information may be shared with Hashicorp, the lab sponsor, if you have opted in to receive product updates, announcements, and offers in your Account Profile.
GSP1004
Overview
Vault uses policies to govern the behavior of clients and instrument Role-Based Access Control (RBAC) by specifying access privileges (authorization). Policies provide a declarative way to grant or forbid access to certain paths and operations. In this hands-on lab you'll learn how to write and use Vault policies.
Objectives
In this lab, you will:
- Create Vault policies
- Manage Vault policies
- Associate Vault policies
- Verify and test Vault policies
Setup and requirements
Before you click the Start Lab button
Read these instructions. Labs are timed and you cannot pause them. The timer, which starts when you click Start Lab, shows how long Google Cloud resources will be made available to you.
This hands-on lab lets you do the lab activities yourself in a real cloud environment, not in a simulation or demo environment. It does so by giving you new, temporary credentials that you use to sign in and access Google Cloud for the duration of the lab.
To complete this lab, you need:
- Access to a standard internet browser (Chrome browser recommended).
- Time to complete the lab---remember, once you start, you cannot pause a lab.
How to start your lab and sign in to the Google Cloud console
-
Click the Start Lab button. If you need to pay for the lab, a pop-up opens for you to select your payment method. On the left is the Lab Details panel with the following:
- The Open Google Cloud console button
- Time remaining
- The temporary credentials that you must use for this lab
- Other information, if needed, to step through this lab
-
Click Open Google Cloud console (or right-click and select Open Link in Incognito Window if you are running the Chrome browser).
The lab spins up resources, and then opens another tab that shows the Sign in page.
Tip: Arrange the tabs in separate windows, side-by-side.
Note: If you see the Choose an account dialog, click Use Another Account. -
If necessary, copy the Username below and paste it into the Sign in dialog.
{{{user_0.username | "Username"}}} You can also find the Username in the Lab Details panel.
-
Click Next.
-
Copy the Password below and paste it into the Welcome dialog.
{{{user_0.password | "Password"}}} You can also find the Password in the Lab Details panel.
-
Click Next.
Important: You must use the credentials the lab provides you. Do not use your Google Cloud account credentials. Note: Using your own Google Cloud account for this lab may incur extra charges. -
Click through the subsequent pages:
- Accept the terms and conditions.
- Do not add recovery options or two-factor authentication (because this is a temporary account).
- Do not sign up for free trials.
After a few moments, the Google Cloud console opens in this tab.
Activate Cloud Shell
Cloud Shell is a virtual machine that is loaded with development tools. It offers a persistent 5GB home directory and runs on the Google Cloud. Cloud Shell provides command-line access to your Google Cloud resources.
- Click Activate Cloud Shell at the top of the Google Cloud console.
When you are connected, you are already authenticated, and the project is set to your Project_ID,
gcloud
is the command-line tool for Google Cloud. It comes pre-installed on Cloud Shell and supports tab-completion.
- (Optional) You can list the active account name with this command:
- Click Authorize.
Output:
- (Optional) You can list the project ID with this command:
Output:
gcloud
, in Google Cloud, refer to the gcloud CLI overview guide.
Task 1. Install Vault
- In Cloud Shell, add the HashiCorp GPG key:
- Add the official HashiCorp Linux repository:
- Update and install Vault:
Verify the installation
After installing Vault, verify the installation worked by checking that the Vault binary is available.
- Execute the
vault
command to verify the installation:
You should see help output similar to the following:
Task 2. Start the Vault server
With Vault installed, the next step is to start a Vault server.
Vault operates as a client/server application. The Vault server is the only piece of the Vault architecture that interacts with the data storage and backends. All operations done via the Vault CLI interact with the server over a TLS connection.
In this lab, you will start and interact with the Vault server running in development mode.
This dev-mode server requires no further setup, and your local vault CLI will be authenticated to talk to it. This makes it easy to experiment with Vault or start a Vault instance for development. Every feature of Vault is available in "dev" mode. The -dev
flag just short-circuits a lot of setup to insecure defaults.
Starting the dev server
First, start a Vault dev server. The dev server is a built-in, pre-configured server that is not very secure but useful for playing with Vault locally.
- To start the Vault dev server, run:
You should see output relating to your Vault server configuration. Notice that Unseal Key and Root Token values are displayed:
localhost
without TLS, and automatically unseals and shows you the unseal key and root access key.
Now that you have the Vault development server running, you can continue setting up access to it.
-
Open a new Cloud Shell tab.
-
Copy and run the export
VAULT_ADDR ..
. command from the terminal output. This will configure the Vault client to talk to the dev server:
The Vault CLI determines which Vault servers to send requests using the VAULT_ADDR
environment variable.
Verify the server is running
- Verify the server is running by running the
vault status
command:
If it ran successfully, the output should look like the following:
Great! You've started your first Vault development server. You can now continue on to the next section, where you will learn how to write Vault policies.
Task 3. Vault policies
Vault creates a root policy during initialization. The root policy is capable of performing every operation for all paths. This policy is assigned to the root token that displays when initialization completes. This provides an initial superuser to enable secrets engines, define policies, and configure authentication methods.
Vault also creates a default policy. The default policy defines a common set of capabilities that enable a token the ability to reflect and manage itself. This policy is also assigned to the root token, and is attached to all tokens by default.
Policy syntax
Policies are written in HCL or JSON and describe which paths in Vault a user or machine is allowed to access. A policy defines a list of paths. Each path expresses the capabilities that are allowed. Capabilities for a path must be granted, as Vault defaults to denying capabilities to paths to ensure that it is secure by default.
The basic format of a policy is as follows:
Here is a very simple policy which grants read capabilities to the path "secret/foo"
:
When this policy is assigned to a token, the token can read from "secret/foo"
. However, the token cannot update or delete "secret/foo"
, since the capabilities do not allow it. Because policies are deny by default, the token would have no other access in Vault. This means that an empty Vault policy grants no permission in the system.
Capabilities
A policy defines one or more paths and a list of permitted capabilities. Each path must define one or more capabilities which provide fine-grained control over permitted (or denied) operations. As you'll see in the examples below, capabilities are always specified as a list of strings, even if there is only one capability. Most of these capabilities map to the HTTP verbs supported by the Vault API. The list of capabilities are:
Policy Capability | Associated HTTP Verbs |
---|---|
create | POST/PUT |
read | GET |
update | POST/PUT |
delete | DELETE |
list | LIST |
patch | PATCH |
sudo | - |
deny | - |
The sudo capability allows access to paths that are root-protected (refer to the Root protected endpoints tutorial section). The deny capability disables access to the path. When combined with other capabilities it always takes precedence.
Policy examples
A more detailed policy to grant all access on "secret/*
" could be defined as follows:
If you want to define further restrictions, this could be accomplished by adding the following deny
capability:
Even though you allowed secret/*
, this additional line above explicitly denies secret/super-secret
. This takes denial precedence.
Policies can also specify allowed, disallowed, and required parameters. Here the key "secret/restricted"
can only contain "foo
" (any value) and "bar
" (one of "zip
" or "zap
").
Policies use path-based matching to test the set of capabilities against a request. A policy path
may specify an exact path to match, or it could specify a glob pattern which instructs Vault to use a prefix match.
For example, this policy permits reading only "secret/foo"
or "secret/foo/bar"
.
Moreover, this policy permits reading everything under "secret/bar"
. An attached token could read "secret/bar/zip"
, "secret/bar/zip/zap"
, but not "secret/bars/zip"
.
In addition, this policy would permit reading everything prefixed with "zip-"
. An attached token could read "secret/zip-zap"
or "secret/zip-zap/zong"
, but not "secret/zip/zap
.
Lastly, a + can be used to denote any number of characters bounded within a single path segment. The following would permit reading the "teamb"
path under any top-level path under secret/
.
And this one would permit reading secret/foo/bar/teamb
, secret/bar/foo/teamb
, etc.
As you can see, Vault's architecture is similar to a filesystem. Every action in Vault has a corresponding path and capability - even Vault's internal core configuration endpoints live under the "sys/"
path. Policies define access to these paths and capabilities, which controls a token's access to credentials in Vault.
Templated policies
The policy syntax allows for doing variable replacement in some policy strings with values available to the token. Currently identity
information can be injected, and currently the path
keys in policies allow injection. For now, you don't need to worry about entities or aliases—this is simply included for reference later.
Parameters
Name | Description |
---|---|
identity.entity.id |
The entity's ID |
identity.entity.name |
The entity's name |
identity.entity.metadata.<metadata key> |
Metadata associated with the entity for the given key |
identity.entity.aliases.<mount accessor>.id |
Entity alias ID for the given mount |
identity.entity.aliases.<mount accessor>.name |
Entity alias name for the given mount |
identity.entity.aliases.<mount accessor>.metadata.<metadata key> |
Metadata associated with the alias for the given mount and metadata key |
identity.entity.aliases.<mount accessor>.custom_metadata.<custom_metadata key> |
Custom metadata associated with the alias for the given mount and custom metadata key |
identity.groups.ids.<group id>.name |
The group name for the given group ID |
identity.groups.names.<group name>.id |
The group ID for the given group name |
identity.groups.ids.<group id>.metadata.<metadata key> |
Metadata associated with the group for the given key |
identity.groups.names.<group name>.metadata.<metadata key> |
Metadata associated with the group for the given key |
Examples
The following policy creates a section of the KVv2 Secret Engine to a specific user:
For more information on templated policies, you can check out the Templated Policies documentation.
Verify built-in policy capabilities
Now that you've seen how policies are written, let's quickly check out the capabilities of the root and default policies.
- In your open Cloud Shell tab, execute the following command to log in to Vault with your root token:
You should see the following output:
- Since the root policy allows you to do anything in Vault, run a basic command to verify that this is the case:
Your output should resemble the following:
Now you'll try to run the same command as a user with only the default
policy attached.
- Start by enabling the
userpass
auth method and creating a new user:
- Next, log in to Vault with the new user you created:
You should receive the following:
- Run the same command from earlier to check the policy capabilities:
You should receive the following error:
As you can see here, Vault is making a GET API request to the path sys/mounts
. Since you're receiving a permission denied error, you can't access the path and list the secrets engines. Now it's time to write your first policy to get access to this path and list the secrets engines!
Task 4. Create a policy
Since Vault centrally secures, stores, and controls access to secrets across distributed infrastructure and applications, it is critical to control permissions before any user or machine can gain access.
The solution to this is to restrict the use of root policy, and write fine-grained policies to practice least privileged. For example, if an app gets Google Cloud credentials from Vault, write policy grants to read from Google Cloud secrets engine but not to delete, etc.
Policies are attached to tokens and roles to enforce client permissions on Vault. Now that you've seen how policies are defined syntactically, it's time to write your first Vault policy.
Log in to the Vault web UI
- First, click on the web preview icon on the toolbar of Cloud Shell.
-
Click Change port.
-
Change the Port Number to
8200
and click Change and Preview.
- You should be redirected to the Vault sign in page.
- Enter your Root Token that you saved earlier in the lab and click Sign In.
Your Vault development server should resemble the following.
Now that you're logged in to the development server web UI, you can continue on to the next section.
Create a new policy
- Click the Policies tab from the home page. You should see the
default
androot
ACL policies.
-
Click Create ACL policy.
-
Start by naming your policy
demo-policy
.
You can now start writing your policy. Recall in the previous section, you were unable to access the sys/mounts
path to read the secrets engines. You'll go ahead and add that now.
- In the Policy box, add the following placeholder code:
- Now, let's first update the
path
to thesys/mounts
path you were trying to access earlier:
- Next, you'll add a capability. Since Vault is attempting to make a GET API call on this path, you'll need to have the
read
capability. Addread
to the capabilities list:
Your policy should resemble the following:
- Click Create policy.
Now, you'll need to associate this policy with the example-user
you created earlier.
- Click the Access tab and then click on the
userpass
authentication method.
- Click on the three dots next to the
example-user
user and select Edit user.
-
Under the password field, click Tokens to open up the submenu.
-
Under Generated Token's Policies, add the policy you just created (
demo-policy
) and click Add.
- Click Save.
Great! You've created a new policy and associated it with the example-user
.
- Navigate back to Cloud Shell and run the following command again:
You'll notice the same error as before:
Why did it error after you've added the policy to the user? This is because once you associate a new policy with a user, that policy won't be associated with the existing token for that user. To fix this, you'll need to generate a new token for that user so that new policy can be attached to that token.
- Run the following command to log in and generate a new token for
example-user
:
default
policy and demo-policy
attached.
- Now, try listing the secrets engines one more time:
Your output should now resemble the following:
- You can also check the capabilities of the token by using the
vault token capabilities
command. Run the following to verify your policy on thesys/mounts
path:
You should get the following output:
- Next, check the token capabilities for the
sys/policies/acl
path:
You should get the following output:
- To verify this, try to run the following command to list the policies:
You should receive the following error:
As you can see here, you're getting a permission denied error for a GET API request on the sys/policies/acl
path. Also notice the additional list=true
on the path; you will need to add this capability as well. Let's fix this by updating the existing policy.
- Navigate back to the
demo-policy
you created in the Vault UI.
-
Click Edit policy.
-
In the Policy box, add the following placeholder code under the existing policy you wrote:
- Again, let's first update the
path
to thesys/policies/acl
path you were trying to access:
- Now you'll add the capability. Since Vault is attempting to make a GET API call on this path, you'll need to add the
read
capability again. Additionally, the attempt passed in thelist=true
to the URL, so you'll need to add this capability as well.
Your updated policy should now resemble the following:
-
Click Save.
-
Navigate back to Cloud Shell and run the following command again:
Your output should now resemble:
- Run the following command to copy the values of the policies to a text file:
- Lastly, check the token capabilities again for the
sys/policies/acl
path:
You should get the following output:
- Run the following command to copy the values of the policies to a text file. Make sure to replace
<your token>
with the value of your token:
- Run the following commands to copy both the
policies
andtoken_capabilities
text files to a pre-created Cloud Storage bucket to track your progress:
As you can see, when you modified the existing policy associated with the user, the changes were reflected without generating a new token. This is because the contents of policies are parsed in real-time whenever the token is used. As a result, if a policy is modified, the modified rules will be enforced the next time a token, with that policy attached, is used to make a call to Vault.
Great! You successfully created a policy that granted read access to the sys/mounts
path and associated it with a user. You then added an additional policy to grant read and list access to the sys/policies
path.
Click Check my progress to verify the objective.
Task 5. Managing policies
Policies are authored (written) in your editor of choice. They can be authored in HCL or JSON, and the syntax is described in detail above. Once saved, policies must be uploaded to Vault before they can be used.
In the previous section, you used the UI to write and manage a a policy. This section will cover the CLI commands to manage policies.
- First, make sure to run the following in Cloud Shell to log in to Vault with your root token:
Listing policies
- Run the following command to list all registered policies in Vault:
You should see the following output:
Creating policies
Policies can be created (uploaded) via the CLI, UI, or via the API. In the previous section, you simply used the UI to create the HCL file.
To create a new policy in Vault, you would use the following command:
- You can test this out by first creating a basic policy file with the following command:
- Check that your file was created correctly:
- Now, create a new policy named
example-policy
with thevault policy write
command:
If it was successful, you should see the following output:
In this example, the name of the policy is "example-policy". You can think of this name as a pointer or symlink to the policy ACLs. Tokens are attached policies by name, which are then mapped to the set of rules corresponding to that name.
Updating policies
Existing policies may be updated to change permissions via the CLI or via the API. To update an existing policy in Vault, you will follow the same steps as creating a policy, but use an existing policy name.
- First, run the following command to update and overwrite your existing policy file to be able to list auth methods:
- Check that your file was created correctly:
- Update your policy:
Great! You've successfully updated a policy using the CLI.
- Run the following command to copy the policy file to a pre-created Cloud Storage bucket to track your progress:
Click Check my progress to verify the objective.
Deleting policies
Existing policies may be deleted via the CLI, UI, or API. To delete a policy, you would run the following:
- Let's try this in practice. Run the following command to delete the policy you just created:
If it was successful, you should have seen the following output:
- List your policies with the following command:
You should see the following output:
Great! You've successfully deleted the example-policy
.
Task 6. Associating policies
Vault can automatically associate a set of policies to a token based on an authorization. This configuration varies significantly between authentication backends. For simplicity, this example will use Vault's built-in userpass auth method.
- Run the following command to create the user
firstname-lastname
in Vault with a list of associated policies:
This creates an authentication mapping to the policy such that, when the user authenticates successfully to Vault, they will be given a token which has the list of policies attached.
- Authenticate with Vault by running the following:
You should see the following output:
Since the provided information is correct, Vault will generate a token, assign the list of configured policies to the token, and return that token to the authenticated user.
Tokens
Tokens have two sets of policies: identity policies, which are computed based on the entity and its groups, and token policies, which are either defined based on the login method or, in the case of explicit token creates via the API, are an input to the token creation. What follows concerns token policies exclusively: a token's identity policies cannot be controlled except by modifying the underlying entities, groups, and group memberships.
- First, log back in to Vault with your root token:
- Tokens are associated with their policies at creation time. Run the following to create a token with the
dev-readonly
andlogs
policies:
You should see the following output:
Normally the only policies that may be specified are those which are present in the current token's (i.e. the new token's parent's) token policies. However, root users can assign any policies.
There is no way to modify the policies associated with a token once the token has been issued. The token must be revoked and a new one acquired to receive a new set of policies.
However, the contents of policies are parsed in real-time whenever the token is used. As a result, if a policy is modified, the modified rules will be enforced the next time a token, with that policy attached, is used to make a call to Vault.
Task 7. Policies for secrets
In this section, you'll create Vault policies to grant users different levels of access within Vault and test them.
- In Cloud Shell, start by creating a few different users with different policies:
Now that you've created some new users, you'll create the policies that you've already associated with them. You'll first start with the admin policy, which should be able to have full access to all the secrets in Vault.
Create the admin policy
For the purposes of this lab, an admin user must be able to:
- Read system health check
- Create and manage ACL policies broadly across Vault
- Enable and manage authentication methods broadly across Vault
- Manage the Key-Value secrets engine enabled at
secret/
path
-
Navigate to the Policies tab in the Vault UI. You should see the
default
,demo-policy
, androot
policies. -
Click Create ACL policy.
-
Start by naming your policy
admin
. -
In the Policy box, add the following policy code:
Your policy should resemble the following:
- Click Create policy.
Create the appdev policy
For the purposes of this lab, an appdev user must be able to:
- Create, read, and update secrets engines
- Manage the Key-Value secrets engine enabled at
secret/appdev/
path
-
Navigate back to the ACL Policies page.
-
Click Create ACL policy.
-
Start by naming your policy
appdev
. -
In the Policy box, add the following policy code:
- Click Create policy.
Create the security policy
For the purposes of this lab, a security user must be able to:
- Create and manage ACL policies broadly across Vault
- Manage secrets engines
- Manage the Key-Value secrets engine enabled at
secret/
path - Not have access to read or list secrets on the
secret/admin
path
-
Navigate back to the ACL Policies page.
-
Click Create ACL policy.
-
Start by naming your policy
security
. -
In the Policy box, add the following policy code:
- Click Create policy.
Create secrets
Now that you've created the different policies, it's time to create some secrets.
- Navigate back to Cloud Shell and run the following commands to create some secrets in the
secret/security
path:
- Create some secrets in the
secret/appdev
path:
- Create some secrets in the
secret/admin
path:
Verify security for appdev
Now that you've created some secrets, let's verify that these policies are being enforced. You'll first log in as the app-dev
user and see what you have access to.
- Run the following command to log in as
app-dev
user:
- Now, try to fetch the
appdev/first
secret:
You should see the following output:
- Fetch the secret located at
secret/appdev/beta-app/second
:
You should see the following output:
- Create a new secret:
- Destroy the secret:
- Attempt to get a secret from
secret/security
:
You should receive the following error:
- Attempt to list all the secrets at
secret/
:
You should again receive an error:
Great! You were able to fetch and create secrets in the secret/appdev
path, and verified that you were not able to access secrets outside of it.
Verify policy for security
- Run the following command to log in as
security
user:
- Now, try to fetch the
security/first
secret:
You should see the following output:
- Fetch the secret located at
secret/security/second
:
You should see the following output:
- Create a new secret in
secret/security/supersecure
:
- Destroy the secret:
- Attempt to read a secret from
secret/appdev
:
You should receive the following output:
- Attempt to list all of the secrets at
secret/
:
You should receive the following output:
- Enable a new secrets engine:
- Attempt to look at the
secret/admin/first
secret:
You should receive the following error:
- Attempt to list the secrets at
secret/admin
:
Again, you should receive an error:
Great! You are able to fetch and create secrets in the secret/
path, enable a secrets engine, and were denied access to the secret/admin
path as specified in the policy.
Verify policy for admin
- Run the following command to log in as
admin
user:
- Now, try to fetch the
admin/first
secret:
You should see the following output:
- Fetch a secret located at
secret/security/first
:
You should see the following output:
- Create a new secret:
- Destroy the secret:
- Attempt to get secrets from the
secret/appdev
:
You should receive the following output:
- Attempt to list all of the secrets at
secret/appdev
:
You should receive the following output:
- List all of the policies:
You should receive the following output:
- Run the following command to copy the values of the policies to a text file and upload it to the Cloud Storage bucket:
- Enable the
gcp
auth method:
- Lastly, list the authentication methods enabled:
Great, you have verified that you have the admin priviledges associated with the policy you wrote.
Click Check my progress to verify the objective.
Paths
As you may have seen in the policy code that was provided for the security
user, there were a couple topics introduced that you haven't seen before: data/
and metadata/
.
The metadata/
path endpoint returns a list of key names at the specified location. Furthermore, the values themselves are not accessible with this command. Writing and reading versions are prefixed with data/
. Listing, reading, and destroying are as follows:
-
Writing and Reading Versions -
data/
-
Listing Keys -
metadata/
-
Reading versions -
metadata/
-
Destroy Versions of Secret -
destroy/
-
Destroy all versions of metadata for a key -
metadata/
For example, if you are trying to deny access to a secret at secret/example
, you would need to format it with the following data/
:
If you want to deny list access to secret/examples
, you would need format with the following metadata/
:
Task 8. Fine-grained control
In addition to the standard set of capabilities, Vault offers finer-grained control over permissions at a given path. The capabilities associated with a path take precedence over permissions on parameters.
Parameter constraints
In Vault, data is represented as key=value
pairs. Vault policies can optionally further restrict paths based on the keys and data at those keys when evaluating the permissions for a path. The optional finer-grained control options are:
-
required_parameters
- A list of parameters that must be specified. -
allowed_parameters
- A list of keys and values that are permitted on the given path. -
denied_parameters
- Denylists a list of parameter and values. Any values specified here take precedence overallowed_parameters
For more information on fine-grained control, you can check out the Fine-Grained Control documentation.
Congratulations!
As you can see, policies are an important part of Vault. While using the root token is easiest to get up and running, you will want to restrict access to Vault very quickly, and the policy system is the way to do this.
The syntax and function of policies is easy to understand and work with, and because auth methods all must map to the central policy system, you only have to learn this policy system.
In this lab, you created and managed policies, associated them with users and tokens, and verified the permissions of them.
Next steps / Learn more
Check out the following for more information on Vault
- Vault Getting Started tutorials
- Vault documentation
- Vault Policy Documentation
- Vault Policies tutorial
Google Cloud training and certification
...helps you make the most of Google Cloud technologies. Our classes include technical skills and best practices to help you get up to speed quickly and continue your learning journey. We offer fundamental to advanced level training, with on-demand, live, and virtual options to suit your busy schedule. Certifications help you validate and prove your skill and expertise in Google Cloud technologies.
Manual last updated April 28, 2023
Lab last tested April 28, 2023
Copyright 2024 Google LLC All rights reserved. Google and the Google logo are trademarks of Google LLC. All other company and product names may be trademarks of the respective companies with which they are associated.