diff options
author | Mike Crute <mike@crute.us> | 2021-11-16 21:50:31 -0800 |
---|---|---|
committer | Mike Crute <mike@crute.us> | 2021-11-17 07:56:17 -0800 |
commit | 73ab23b5f74174ec6b6a988103306eeec389d5a8 (patch) | |
tree | ed56d604a22d36ca9bf658064442d29f0e0a18b0 /README.md | |
parent | cc58a3da7d647de8520e33dc4356672d2ed1a366 (diff) | |
download | cloud-identity-broker-73ab23b5f74174ec6b6a988103306eeec389d5a8.tar.bz2 cloud-identity-broker-73ab23b5f74174ec6b6a988103306eeec389d5a8.tar.xz cloud-identity-broker-73ab23b5f74174ec6b6a988103306eeec389d5a8.zip |
Add some docs
Diffstat (limited to 'README.md')
-rw-r--r-- | README.md | 205 |
1 files changed, 203 insertions, 2 deletions
@@ -1,6 +1,207 @@ | |||
1 | # Cloud Identity Broker | 1 | # Cloud Identity Broker |
2 | 2 | ||
3 | // TODO: https://docs.gitlab.com/ee/api/jobs.html#get-job-tokens-job | 3 | This is a cloud identity broker. Identity brokers exist to bridge |
4 | // TODO: Admin UI | 4 | authentication from one system into authentication to another system. In the |
5 | case of this broker it bridges GitHub and GitLab authentication into temporary | ||
6 | credentials for cloud providers. The broker has an interactive API that can be | ||
7 | used in a web browser as well as a JSON/REST API that can be consumed | ||
8 | programmatically. | ||
5 | 9 | ||
10 | The reason this broker exists is to provide one secured location for long-lived | ||
11 | cloud provider credentials that can be easily consumed from development | ||
12 | environments and build systems while limiting the scope of access and time frame | ||
13 | of access those systems have to cloud resources. This helps to increase the | ||
14 | security of those accounts and reduce the risk of abuse. All access through the | ||
15 | broker is chained to an authenticated and authorized user account and all | ||
16 | access through those user accounts are logged for auditing. All credentials | ||
17 | returned by the broker have a strict time limit after which they are useless. | ||
6 | 18 | ||
19 | This broker started life as a piece of internal infrastructure specific to AWS | ||
20 | that has been re-written and open sourced with the goal to support multiple | ||
21 | clouds. | ||
22 | |||
23 | For documentation the REST API look at the `README_BROKER.md` file. | ||
24 | |||
25 | ## Contributing | ||
26 | |||
27 | Contributions are welcomed. Please send contributions to mike-at-crute-dot-us | ||
28 | either through email in `git format-patch` format or send a link to a git repo | ||
29 | and branch name that the author can pull and merge. | ||
30 | |||
31 | If you're reading this on one of the author's git forge accounts (GitHub, | ||
32 | GitLab, sr.ht, etc...) feel free to open a pull/merge request with your | ||
33 | changes. | ||
34 | |||
35 | The author reserves the right to request changes to contributions before | ||
36 | merging them or to not merge them at all but will endeavour to be reasonable in | ||
37 | those requests. | ||
38 | |||
39 | ## Building | ||
40 | |||
41 | This requires Go 1.17 or newer to build. Provided that a simple `make` should | ||
42 | create a `cloud-identity-broker` binary that's ready to use. | ||
43 | |||
44 | The built binary embeds all of the templates in production mode and will | ||
45 | require nothing more than the binary itself to run, if running in `--debug` | ||
46 | mode then the `templates` folder must be available. | ||
47 | |||
48 | ## Running | ||
49 | |||
50 | It's complicated, so probably don't? | ||
51 | |||
52 | The application requires some bits of infrastructure to be in place for it to | ||
53 | run but then can be exposed directly to the internet or put behind a reverse | ||
54 | proxy. You will need: | ||
55 | |||
56 | - [Mongodb](https://www.mongodb.com/) | ||
57 | - [Vault](https://www.hashicorp.com/products/vault) | ||
58 | - [GitHub Oauth Application](https://docs.github.com/en/developers/apps/building-oauth-apps/creating-an-oauth-app) | ||
59 | - [SSL certificates](https://letsencrypt.org/). | ||
60 | |||
61 | Once the requisite infrastructure (see below) is configured, run the binary | ||
62 | like so: | ||
63 | |||
64 | ``` | ||
65 | VAULT_ROLE_ID="..." \ | ||
66 | VAULT_SECRET_ID="..." \ | ||
67 | VAULT_ADDR="https://your-vault-addr:8200" \ | ||
68 | ./cloud-identity-broker \ | ||
69 | --mongodb-uri="mongodb://your-mongodb-host:27017/your-db-name?authSource=admin" \ | ||
70 | --mongodb-vault-path="database/static-creds/your-cred-name" \ | ||
71 | --github-oauth-vault-path="service/service-name/github-oauth" \ | ||
72 | web | ||
73 | ``` | ||
74 | |||
75 | ### SSL Certificates | ||
76 | |||
77 | SSL certificates of a cipher type compatible with Go's SSL library are required | ||
78 | to run the binary, even in development mode. Obtain those certificates however | ||
79 | you would normal do so. | ||
80 | |||
81 | Both a key and certificate are required to be stored in the directory | ||
82 | identified by `--tls-cache-dir` (which defaults to `./ssl/`). Both files should | ||
83 | be of PEM format with the certificate named `cert.pem` and the key named | ||
84 | `key.pem`. | ||
85 | |||
86 | ### Vault Setup | ||
87 | |||
88 | Configure Vault per the manufacturers instructions. Create an AppRole for the | ||
89 | identity broker and provide the credentials to the binary using the standard | ||
90 | Vault environment variables. | ||
91 | |||
92 | The binary will need access to a set of GitHub Oauth client credentials for a | ||
93 | GitHub Oauth application that is used to authenticate users to the broker. | ||
94 | Setup an application on GitHub and store the client ID and client secret in a | ||
95 | JSON document in Vault the vault KV backend with the following format: | ||
96 | |||
97 | ``` | ||
98 | { | ||
99 | "client-id": "your client id", | ||
100 | "client-secret": "your client secret" | ||
101 | } | ||
102 | ``` | ||
103 | |||
104 | Provide the path to this material with the `--github-oauth-vault-path` command | ||
105 | line argument. You should omit the `kv/data/` prefix to the path. | ||
106 | |||
107 | For each AWS cloud account to which the broker provides access a JSON document | ||
108 | must be stored in the Vault KV backend. The format of this document is as | ||
109 | follows. The path to this document is provided (with the `kv/data/` prefix | ||
110 | omitted) in the `VaultMaterial` field of the `Account` record for the account | ||
111 | in Mongodb. | ||
112 | |||
113 | ``` | ||
114 | { | ||
115 | "AccessKeyId": "...", | ||
116 | "SecretAccessKey": "...", | ||
117 | "Roles": { | ||
118 | "account-short-name": { | ||
119 | "ARN": "arn:aws:iam::...:role/...", | ||
120 | "ExternalId": "..." | ||
121 | } | ||
122 | } | ||
123 | } | ||
124 | ``` | ||
125 | |||
126 | The fields are: | ||
127 | |||
128 | - `AccessKeyId` which is the access key ID of an IAM user that can assume roles | ||
129 | in the target account. | ||
130 | - `SecretAccessKey` is the secret key for the IAM user identified by the access | ||
131 | key ID. | ||
132 | - `Roles` is a mapping of account `ShortName` to an AWS ARN and ExternalId used | ||
133 | for assuming roles. The `ARN` is the role to be assumed and the `ExternalId` | ||
134 | is the External ID configured in the role trust policy. | ||
135 | |||
136 | Note that this application does **not** use the AWS Vault backend to assume | ||
137 | roles due to limitations AWS places on roles assumed using assumed role | ||
138 | credentials and not user credentials. | ||
139 | |||
140 | Finally the broker will need access to a Mongodb credential. Currently this | ||
141 | requires a static credential but in the future a dynamic credential will be | ||
142 | acceptable. Create this credential and pass it in the `--mongodb-vault-path` | ||
143 | argument. It should have the form `database/static-creds/your-cred-name`. | ||
144 | |||
145 | ### Mongodb Setup | ||
146 | |||
147 | The application needs a Mongodb database with at least a `users` collection | ||
148 | created. The rest are optional. | ||
149 | |||
150 | To create the `users` collection insert a record to the collection that | ||
151 | contains your GitHub username as the `_id` field and has `IsAdmin` set to true. | ||
152 | For example: | ||
153 | |||
154 | ``` | ||
155 | db.users.insert({ "_id": "mcrute", "IsAdmin": true }) | ||
156 | ``` | ||
157 | |||
158 | This is adequate to allow login via GitHub for the named user. All other fields | ||
159 | will be populated automatically by the app. | ||
160 | |||
161 | To create allowed AWS accounts for use in the broker add them to the `accounts` | ||
162 | collection. Those records have the following form: | ||
163 | |||
164 | ``` | ||
165 | { | ||
166 | "_id": "acocunt-short-name", | ||
167 | "AccountNumber": 12345, | ||
168 | "AccountType": "aws", | ||
169 | "ConsoleSessionDuration": 21600000000000, | ||
170 | "DefaultRegion": "us-west-2", | ||
171 | "Name": "Some Description", | ||
172 | "Users": [ | ||
173 | "username1", | ||
174 | "username2" | ||
175 | ], | ||
176 | "VaultMaterial": "some/path/as/above" | ||
177 | } | ||
178 | ``` | ||
179 | |||
180 | - `_id` is the short name of the account. This must also map into a Vault | ||
181 | material per above. | ||
182 | - `AccountNumber` is the AWS account number for the account being brokered. | ||
183 | - `AccountType` is the string `aws` for now | ||
184 | - `ConsoleSessionDuration` is the number of nanoseconds a console session can | ||
185 | exist before timing out. (Nanoseconds are silly, yes; it's a serialized | ||
186 | time.Time) | ||
187 | - `DefaultRegion` is the region considered default, this is just used as an | ||
188 | indicator in the JSON API. | ||
189 | - `Name` a longer form, descriptive name of the account. | ||
190 | - `Users` a case-sensitive list of GitHub user names that have access to this | ||
191 | account | ||
192 | - `VaultMaterial` the path to the Vault material that contains the account | ||
193 | credentials document, as above. | ||
194 | |||
195 | ## To Do | ||
196 | |||
197 | - Allow GitLab CI jobs to auth using [job tokens](https://docs.gitlab.com/ee/api/jobs.html#get-job-tokens-job) | ||
198 | - Implement an Admin UI, all admin ops are directly on the DB at the moment | ||
199 | - Support dynamic mongodb credentials | ||
200 | - Support for other clouds | ||
201 | - GCP | ||
202 | - OCI | ||
203 | - Azure | ||
204 | |||
205 | ## Contributors | ||
206 | |||
207 | - [Mike Crute](https://mike.crute.us) | ||