docs: add me sevrice-to-service auth section
Co-authored-by: Fredrik Adelöw <freben@gmail.com> Signed-off-by: Patrik Oldsberg <poldsberg@gmail.com>
This commit is contained in:
@@ -4,68 +4,4 @@ title: Backend-to-Backend Authentication
|
||||
description: Guide for authenticating API requests between Backstage plugin backends
|
||||
---
|
||||
|
||||
This tutorial describes the steps needed to handle _backend-to-backend
|
||||
authentication_, which allows plugin backends to determine whether a given
|
||||
request originates from a legitimate Backstage backend by verifying a token
|
||||
signed with a shared secret. This system has limited use for now, but will be
|
||||
needed to support the upcoming framework for permissions and authorization (see
|
||||
[the PRFC on the topic](https://github.com/backstage/backstage/pull/7761) for
|
||||
more details).
|
||||
|
||||
Backends have no concept of a Backstage identity, so instead they use a token
|
||||
generated using a shared key stored in config. You can generate a unique key for
|
||||
your app in a terminal, and set the `BACKEND_SECRET` environment variable to the
|
||||
resulting value.
|
||||
|
||||
```bash
|
||||
node -p 'require("crypto").randomBytes(24).toString("base64")'
|
||||
```
|
||||
|
||||
**NOTE**: For ease of development, we auto-generate a key for you if you haven't
|
||||
configured a secret in dev mode. You _must set your own secret_ in order for
|
||||
backend-to-backend authentication to work in production.
|
||||
|
||||
Requests originating from a backend plugin can be authenticated by decorating
|
||||
them with a backend token. Backend tokens can be generated using a
|
||||
`TokenManager`, which can be passed to plugin backends via the
|
||||
`PluginEnvironment`. The `TokenManager` provided in new Backstage instances
|
||||
generated by `create-app` is a stub, which returns empty tokens and accepts any
|
||||
input string as valid. To enable backend-to-backend authentication, you'll need
|
||||
to instantiate a new one using the secret from your config instead:
|
||||
|
||||
```diff
|
||||
// packages/backend/src/index.ts
|
||||
|
||||
function makeCreateEnv(config: Config) {
|
||||
const root = getRootLogger();
|
||||
const reader = UrlReaders.default({ logger: root, config });
|
||||
const discovery = SingleHostDiscovery.fromConfig(config);
|
||||
|
||||
root.info(`Created UrlReader ${reader}`);
|
||||
|
||||
const cacheManager = CacheManager.fromConfig(config);
|
||||
const databaseManager = DatabaseManager.fromConfig(config);
|
||||
- const tokenManager = ServerTokenManager.noop();
|
||||
+ const tokenManager = ServerTokenManager.fromConfig(config, { logger: root });
|
||||
```
|
||||
|
||||
With this `tokenManager`, you can then generate a server token for requests:
|
||||
|
||||
```typescript
|
||||
const { token } = await this.tokenManager.getToken();
|
||||
|
||||
const response = await fetch(pluginBackendApiUrl, {
|
||||
method: 'GET',
|
||||
headers: {
|
||||
...headers,
|
||||
Authorization: `Bearer ${token}`,
|
||||
},
|
||||
});
|
||||
```
|
||||
|
||||
You can use the same `tokenManager` to authenticate tokens supplied on incoming
|
||||
requests:
|
||||
|
||||
```typescript
|
||||
await tokenManager.authenticate(token); // throws if token is invalid
|
||||
```
|
||||
See [new docs](../auth/service-to-service-auth.md)
|
||||
|
||||
Reference in New Issue
Block a user