Merge branch 'master' into fix-auditor-length
Signed-off-by: John <john.r.k.redwood@gmail.com>
This commit is contained in:
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-techdocs': patch
|
||||
---
|
||||
|
||||
Fixed an issue causing TechDocs to not properly handle initial redirect.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-graph': patch
|
||||
---
|
||||
|
||||
Catalog graph plugin support i18n
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
We are consolidating all css files into a single styles.css in Canon.
|
||||
@@ -1,14 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-backend': major
|
||||
'@backstage/create-app': patch
|
||||
---
|
||||
|
||||
**BREAKING:** The experimental `catalog.useUrlReadersSearch` configuration flag (introduced in v1.36) has been removed.
|
||||
|
||||
The `UrlReaderProcessor` now always uses the `search` method of `UrlReaders`. Built-in `UrlReaderService` implementations have been updated accordingly.
|
||||
If you use custom `UrlReaderService` implementations, you need to adapt their `search` method to correctly handle both specific URLs and potential
|
||||
search patterns (see changes on built-in readers [in the original PR](https://github.com/backstage/backstage/pull/28379/files#diff-68b0452f173ee54bdd40f7b5e047a9cb8bb59200425622c212c217b76dac1d1b)).
|
||||
|
||||
Previous behavior was to call the `search` method only if the parsed Git URL's filename contained a wildcard and use `readUrl` otherwise. Each `UrlReaderService` must implement this logic in the `search` method instead.
|
||||
|
||||
This allows each `UrlReaderService` implementation to check whether it's a search URL (that contains a wildcard pattern) or not using logic that is specific to each provider.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
Add new SearchField component in Canon
|
||||
@@ -1,6 +0,0 @@
|
||||
---
|
||||
'@backstage/config-loader': patch
|
||||
'@backstage/config': patch
|
||||
---
|
||||
|
||||
Loosen the requirements for a key to be considered valid config.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-scaffolder': patch
|
||||
---
|
||||
|
||||
Filter MultiEntityPicker options based on rendered option value
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
Add new `RadioGroup` + `Radio` component to Canon
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-backend-module-incremental-ingestion': patch
|
||||
---
|
||||
|
||||
Fixed bug in `IncrementalIngestionEngine` by adding `burstLength` check when a burst completes
|
||||
@@ -1,6 +0,0 @@
|
||||
---
|
||||
'@backstage/backend-defaults': patch
|
||||
'@backstage/backend-test-utils': minor
|
||||
---
|
||||
|
||||
Add a standard `toString` on credentials objects
|
||||
@@ -0,0 +1,5 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-react': patch
|
||||
---
|
||||
|
||||
Adding `type` as an override to the `convertLegacyEntityCardExtension`
|
||||
@@ -0,0 +1,5 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-backend-module-azure': patch
|
||||
---
|
||||
|
||||
`host` should be optional in `config` schema
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/repo-tools': minor
|
||||
---
|
||||
|
||||
Clear output directory before running `package-docs` and skip all internal packages.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/backend-dynamic-feature-service': patch
|
||||
---
|
||||
|
||||
Fix wrong imports which lead to module initialization failures when enabling dynamic plugins.
|
||||
@@ -1,7 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-scaffolder-node-test-utils': patch
|
||||
'@backstage/plugin-scaffolder-backend': patch
|
||||
'@backstage/plugin-scaffolder-node': patch
|
||||
---
|
||||
|
||||
An internal refactor which adds additional types to experimental checkpoints
|
||||
@@ -1,233 +0,0 @@
|
||||
{
|
||||
"mode": "pre",
|
||||
"tag": "next",
|
||||
"initialVersions": {
|
||||
"example-app": "0.2.110",
|
||||
"@backstage/app-defaults": "1.6.3",
|
||||
"example-app-next": "0.0.24",
|
||||
"app-next-example-plugin": "0.0.24",
|
||||
"example-backend": "0.0.39",
|
||||
"@backstage/backend-app-api": "1.2.4",
|
||||
"@backstage/backend-defaults": "0.11.0",
|
||||
"@backstage/backend-dev-utils": "0.1.5",
|
||||
"@backstage/backend-dynamic-feature-service": "0.7.1",
|
||||
"@backstage/backend-openapi-utils": "0.5.4",
|
||||
"@backstage/backend-plugin-api": "1.4.0",
|
||||
"@backstage/backend-test-utils": "1.6.0",
|
||||
"@backstage/canon": "0.5.0",
|
||||
"@backstage/catalog-client": "1.10.1",
|
||||
"@backstage/catalog-model": "1.7.4",
|
||||
"@backstage/cli": "0.33.0",
|
||||
"@backstage/cli-common": "0.1.15",
|
||||
"@backstage/cli-node": "0.2.13",
|
||||
"@backstage/codemods": "0.1.52",
|
||||
"@backstage/config": "1.3.2",
|
||||
"@backstage/config-loader": "1.10.1",
|
||||
"@backstage/core-app-api": "1.17.1",
|
||||
"@backstage/core-compat-api": "0.4.3",
|
||||
"@backstage/core-components": "0.17.3",
|
||||
"@backstage/core-plugin-api": "1.10.8",
|
||||
"@backstage/create-app": "0.7.0",
|
||||
"@backstage/dev-utils": "1.1.11",
|
||||
"e2e-test": "0.2.29",
|
||||
"@backstage/e2e-test-utils": "0.1.1",
|
||||
"@backstage/errors": "1.2.7",
|
||||
"@backstage/eslint-plugin": "0.1.11",
|
||||
"@backstage/frontend-app-api": "0.11.3",
|
||||
"@backstage/frontend-defaults": "0.2.3",
|
||||
"@backstage/frontend-dynamic-feature-loader": "0.1.2",
|
||||
"@internal/frontend": "0.0.10",
|
||||
"@backstage/frontend-plugin-api": "0.10.3",
|
||||
"@backstage/frontend-test-utils": "0.3.3",
|
||||
"@backstage/integration": "1.17.0",
|
||||
"@backstage/integration-aws-node": "0.1.16",
|
||||
"@backstage/integration-react": "1.2.8",
|
||||
"@internal/opaque": "0.0.1",
|
||||
"@backstage/release-manifests": "0.0.13",
|
||||
"@backstage/repo-tools": "0.14.0",
|
||||
"@internal/scaffolder": "0.0.10",
|
||||
"@techdocs/cli": "1.9.4",
|
||||
"techdocs-cli-embedded-app": "0.2.109",
|
||||
"@backstage/test-utils": "1.7.9",
|
||||
"@backstage/theme": "0.6.6",
|
||||
"@backstage/types": "1.2.1",
|
||||
"@backstage/version-bridge": "1.0.11",
|
||||
"yarn-plugin-backstage": "0.0.6",
|
||||
"@backstage/plugin-api-docs": "0.12.8",
|
||||
"@backstage/plugin-api-docs-module-protoc-gen-doc": "0.1.10",
|
||||
"@backstage/plugin-app": "0.1.10",
|
||||
"@backstage/plugin-app-backend": "0.5.3",
|
||||
"@backstage/plugin-app-node": "0.1.34",
|
||||
"@backstage/plugin-app-visualizer": "0.1.20",
|
||||
"@backstage/plugin-auth-backend": "0.25.1",
|
||||
"@backstage/plugin-auth-backend-module-atlassian-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-auth0-provider": "0.2.4",
|
||||
"@backstage/plugin-auth-backend-module-aws-alb-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-azure-easyauth-provider": "0.2.9",
|
||||
"@backstage/plugin-auth-backend-module-bitbucket-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-bitbucket-server-provider": "0.2.4",
|
||||
"@backstage/plugin-auth-backend-module-cloudflare-access-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-gcp-iap-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-github-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-gitlab-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-google-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-guest-provider": "0.2.9",
|
||||
"@backstage/plugin-auth-backend-module-microsoft-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-oauth2-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-oauth2-proxy-provider": "0.2.9",
|
||||
"@backstage/plugin-auth-backend-module-oidc-provider": "0.4.4",
|
||||
"@backstage/plugin-auth-backend-module-okta-provider": "0.2.4",
|
||||
"@backstage/plugin-auth-backend-module-onelogin-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-pinniped-provider": "0.3.4",
|
||||
"@backstage/plugin-auth-backend-module-vmware-cloud-provider": "0.5.4",
|
||||
"@backstage/plugin-auth-node": "0.6.4",
|
||||
"@backstage/plugin-auth-react": "0.1.16",
|
||||
"@backstage/plugin-bitbucket-cloud-common": "0.3.0",
|
||||
"@backstage/plugin-catalog": "1.31.0",
|
||||
"@backstage/plugin-catalog-backend": "2.1.0",
|
||||
"@backstage/plugin-catalog-backend-module-aws": "0.4.12",
|
||||
"@backstage/plugin-catalog-backend-module-azure": "0.3.6",
|
||||
"@backstage/plugin-catalog-backend-module-backstage-openapi": "0.5.3",
|
||||
"@backstage/plugin-catalog-backend-module-bitbucket-cloud": "0.5.0",
|
||||
"@backstage/plugin-catalog-backend-module-bitbucket-server": "0.5.0",
|
||||
"@backstage/plugin-catalog-backend-module-gcp": "0.3.9",
|
||||
"@backstage/plugin-catalog-backend-module-gerrit": "0.3.3",
|
||||
"@backstage/plugin-catalog-backend-module-gitea": "0.1.1",
|
||||
"@backstage/plugin-catalog-backend-module-github": "0.10.0",
|
||||
"@backstage/plugin-catalog-backend-module-github-org": "0.3.11",
|
||||
"@backstage/plugin-catalog-backend-module-gitlab": "0.7.0",
|
||||
"@backstage/plugin-catalog-backend-module-gitlab-org": "0.2.10",
|
||||
"@backstage/plugin-catalog-backend-module-incremental-ingestion": "0.7.1",
|
||||
"@backstage/plugin-catalog-backend-module-ldap": "0.11.6",
|
||||
"@backstage/plugin-catalog-backend-module-logs": "0.1.11",
|
||||
"@backstage/plugin-catalog-backend-module-msgraph": "0.7.1",
|
||||
"@backstage/plugin-catalog-backend-module-openapi": "0.2.11",
|
||||
"@backstage/plugin-catalog-backend-module-puppetdb": "0.2.11",
|
||||
"@backstage/plugin-catalog-backend-module-scaffolder-entity-model": "0.2.9",
|
||||
"@backstage/plugin-catalog-backend-module-unprocessed": "0.6.1",
|
||||
"@backstage/plugin-catalog-common": "1.1.4",
|
||||
"@backstage/plugin-catalog-graph": "0.4.20",
|
||||
"@backstage/plugin-catalog-import": "0.13.1",
|
||||
"@backstage/plugin-catalog-node": "1.17.1",
|
||||
"@backstage/plugin-catalog-react": "1.19.0",
|
||||
"@backstage/plugin-catalog-unprocessed-entities": "0.2.18",
|
||||
"@backstage/plugin-catalog-unprocessed-entities-common": "0.0.8",
|
||||
"@backstage/plugin-config-schema": "0.1.69",
|
||||
"@backstage/plugin-devtools": "0.1.28",
|
||||
"@backstage/plugin-devtools-backend": "0.5.6",
|
||||
"@backstage/plugin-devtools-common": "0.1.16",
|
||||
"@backstage/plugin-events-backend": "0.5.3",
|
||||
"@backstage/plugin-events-backend-module-aws-sqs": "0.4.12",
|
||||
"@backstage/plugin-events-backend-module-azure": "0.2.21",
|
||||
"@backstage/plugin-events-backend-module-bitbucket-cloud": "0.2.21",
|
||||
"@backstage/plugin-events-backend-module-bitbucket-server": "0.1.2",
|
||||
"@backstage/plugin-events-backend-module-gerrit": "0.2.21",
|
||||
"@backstage/plugin-events-backend-module-github": "0.4.1",
|
||||
"@backstage/plugin-events-backend-module-gitlab": "0.3.2",
|
||||
"@backstage/plugin-events-backend-module-google-pubsub": "0.1.1",
|
||||
"@backstage/plugin-events-backend-module-kafka": "0.1.0",
|
||||
"@backstage/plugin-events-backend-test-utils": "0.1.45",
|
||||
"@backstage/plugin-events-node": "0.4.12",
|
||||
"@internal/plugin-todo-list": "1.0.40",
|
||||
"@internal/plugin-todo-list-backend": "1.0.40",
|
||||
"@internal/plugin-todo-list-common": "1.0.25",
|
||||
"@backstage/plugin-gateway-backend": "1.0.2",
|
||||
"@backstage/plugin-home": "0.8.9",
|
||||
"@backstage/plugin-home-react": "0.1.27",
|
||||
"@backstage/plugin-kubernetes": "0.12.8",
|
||||
"@backstage/plugin-kubernetes-backend": "0.19.7",
|
||||
"@backstage/plugin-kubernetes-cluster": "0.0.26",
|
||||
"@backstage/plugin-kubernetes-common": "0.9.5",
|
||||
"@backstage/plugin-kubernetes-node": "0.3.1",
|
||||
"@backstage/plugin-kubernetes-react": "0.5.8",
|
||||
"@backstage/plugin-mcp-actions-backend": "0.1.0",
|
||||
"@backstage/plugin-notifications": "0.5.6",
|
||||
"@backstage/plugin-notifications-backend": "0.5.7",
|
||||
"@backstage/plugin-notifications-backend-module-email": "0.3.10",
|
||||
"@backstage/plugin-notifications-backend-module-slack": "0.1.2",
|
||||
"@backstage/plugin-notifications-common": "0.0.9",
|
||||
"@backstage/plugin-notifications-node": "0.2.16",
|
||||
"@backstage/plugin-org": "0.6.40",
|
||||
"@backstage/plugin-org-react": "0.1.39",
|
||||
"@backstage/plugin-permission-backend": "0.7.1",
|
||||
"@backstage/plugin-permission-backend-module-allow-all-policy": "0.2.9",
|
||||
"@backstage/plugin-permission-common": "0.9.0",
|
||||
"@backstage/plugin-permission-node": "0.10.1",
|
||||
"@backstage/plugin-permission-react": "0.4.35",
|
||||
"@backstage/plugin-proxy-backend": "0.6.3",
|
||||
"@backstage/plugin-proxy-node": "0.1.5",
|
||||
"@backstage/plugin-scaffolder": "1.32.0",
|
||||
"@backstage/plugin-scaffolder-backend": "2.0.0",
|
||||
"@backstage/plugin-scaffolder-backend-module-azure": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-bitbucket": "0.3.11",
|
||||
"@backstage/plugin-scaffolder-backend-module-bitbucket-cloud": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-bitbucket-server": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-confluence-to-markdown": "0.3.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-cookiecutter": "0.3.11",
|
||||
"@backstage/plugin-scaffolder-backend-module-gcp": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-gerrit": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-gitea": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-github": "0.8.0",
|
||||
"@backstage/plugin-scaffolder-backend-module-gitlab": "0.9.2",
|
||||
"@backstage/plugin-scaffolder-backend-module-notifications": "0.1.11",
|
||||
"@backstage/plugin-scaffolder-backend-module-rails": "0.5.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-sentry": "0.2.10",
|
||||
"@backstage/plugin-scaffolder-backend-module-yeoman": "0.4.11",
|
||||
"@backstage/plugin-scaffolder-common": "1.5.11",
|
||||
"@backstage/plugin-scaffolder-node": "0.9.0",
|
||||
"@backstage/plugin-scaffolder-node-test-utils": "0.3.0",
|
||||
"@backstage/plugin-scaffolder-react": "1.17.0",
|
||||
"@backstage/plugin-search": "1.4.27",
|
||||
"@backstage/plugin-search-backend": "2.0.3",
|
||||
"@backstage/plugin-search-backend-module-catalog": "0.3.5",
|
||||
"@backstage/plugin-search-backend-module-elasticsearch": "1.7.3",
|
||||
"@backstage/plugin-search-backend-module-explore": "0.3.3",
|
||||
"@backstage/plugin-search-backend-module-pg": "0.5.45",
|
||||
"@backstage/plugin-search-backend-module-stack-overflow-collator": "0.3.10",
|
||||
"@backstage/plugin-search-backend-module-techdocs": "0.4.3",
|
||||
"@backstage/plugin-search-backend-node": "1.3.12",
|
||||
"@backstage/plugin-search-common": "1.2.18",
|
||||
"@backstage/plugin-search-react": "1.9.1",
|
||||
"@backstage/plugin-signals": "0.0.20",
|
||||
"@backstage/plugin-signals-backend": "0.3.5",
|
||||
"@backstage/plugin-signals-node": "0.1.21",
|
||||
"@backstage/plugin-signals-react": "0.0.14",
|
||||
"@backstage/plugin-techdocs": "1.13.0",
|
||||
"@backstage/plugin-techdocs-addons-test-utils": "1.0.49",
|
||||
"@backstage/plugin-techdocs-backend": "2.0.3",
|
||||
"@backstage/plugin-techdocs-common": "0.1.1",
|
||||
"@backstage/plugin-techdocs-module-addons-contrib": "1.1.25",
|
||||
"@backstage/plugin-techdocs-node": "1.13.4",
|
||||
"@backstage/plugin-techdocs-react": "1.3.0",
|
||||
"@backstage/plugin-user-settings": "0.8.23",
|
||||
"@backstage/plugin-user-settings-backend": "0.3.3",
|
||||
"@backstage/plugin-user-settings-common": "0.0.1"
|
||||
},
|
||||
"changesets": [
|
||||
"chubby-dots-kiss",
|
||||
"clear-bananas-end",
|
||||
"curly-zoos-thank",
|
||||
"cyan-islands-swim",
|
||||
"dark-cougars-go",
|
||||
"empty-mugs-agree",
|
||||
"empty-poets-give",
|
||||
"gentle-llamas-press",
|
||||
"mean-lemons-dream",
|
||||
"petite-paths-remain",
|
||||
"public-nails-melt",
|
||||
"red-trams-join",
|
||||
"rich-eagles-rule",
|
||||
"shaggy-cobras-rhyme",
|
||||
"sharp-stars-report",
|
||||
"silent-vans-tie",
|
||||
"six-dots-agree",
|
||||
"sixty-ties-matter",
|
||||
"social-insects-cheat",
|
||||
"stupid-donuts-sit",
|
||||
"three-shoes-behave",
|
||||
"tired-bats-attend",
|
||||
"wicked-socks-share",
|
||||
"wise-frogs-talk",
|
||||
"yummy-pugs-battle"
|
||||
]
|
||||
}
|
||||
@@ -1,13 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': minor
|
||||
---
|
||||
|
||||
**BREAKING CHANGES**
|
||||
|
||||
We’re updating our Button component to provide better support for button links.
|
||||
|
||||
- We’re introducing a new `ButtonLink` component, which replaces the previous render prop pattern.
|
||||
- To maintain naming consistency across components, `IconButton` is being renamed to `ButtonIcon`.
|
||||
- Additionally, the render prop will be removed from all button-related components.
|
||||
|
||||
These changes aim to simplify usage and improve clarity in our component API.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-notifications-backend': patch
|
||||
---
|
||||
|
||||
Fix `addTopic` migration when `user_settings` present
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-mcp-actions-backend': patch
|
||||
---
|
||||
|
||||
Fixed the example in the README for generating a static token by adding a subject field
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
We are transforming how we structure our class names and data attributes definitions for all components. They are now all set in the same place.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-scaffolder-backend': patch
|
||||
---
|
||||
|
||||
Replaced deprecated uses of `@backstage/backend-common` with the equivalents in `@backstage/backend-defaults` and `@backstage/backend-plugin-api`.
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
Added placeholder prop to TextField component.
|
||||
@@ -1,6 +0,0 @@
|
||||
---
|
||||
'@backstage/backend-defaults': patch
|
||||
'@backstage/integration': patch
|
||||
---
|
||||
|
||||
UrlReader: Fix handling of access tokens for GitLab readURL requests
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-scaffolder-backend-module-cookiecutter': patch
|
||||
---
|
||||
|
||||
Fixing the typescript issue with using `z.unknown()`
|
||||
@@ -1,21 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-scaffolder-backend-module-github': patch
|
||||
---
|
||||
|
||||
Added support for file deletion to `publish:github:pull-request` action.
|
||||
|
||||
Example usage:
|
||||
|
||||
```diff
|
||||
- action: publish:github:pull-request
|
||||
id: clean-up-pr
|
||||
input:
|
||||
description: This is the description
|
||||
+ filesToDelete:
|
||||
+ - outdated/changelog.md
|
||||
+ - sample-file.txt
|
||||
owner: owner
|
||||
repo: repo
|
||||
title: Title Goes Here
|
||||
|
||||
```
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-catalog-import': patch
|
||||
---
|
||||
|
||||
Fixed bug with error message since ResponseError is now thrown from CatalogClient
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/canon': patch
|
||||
---
|
||||
|
||||
adding export for ButtonLink so it's importable
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/integration-react': patch
|
||||
---
|
||||
|
||||
Separated gitlab `write_repository` and `api` scope to pass checks in `RefreshingAuthSessionManager`
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/plugin-search-backend': patch
|
||||
---
|
||||
|
||||
Error messages should not contain backend SQL query strings in the API response, this change will ensure that messages are logged and empty response is returned to the user
|
||||
@@ -1,6 +0,0 @@
|
||||
---
|
||||
'@backstage/backend-defaults': patch
|
||||
'@backstage/integration': patch
|
||||
---
|
||||
|
||||
Fixed bug where the GitLab user token and GitLab integration token were being merged together
|
||||
@@ -1,5 +0,0 @@
|
||||
---
|
||||
'@backstage/theme': patch
|
||||
---
|
||||
|
||||
Update uncomfortably bright color in recently visited and top visited home page cards
|
||||
+1
-1
@@ -7,7 +7,7 @@
|
||||
**/.git/**
|
||||
**/public/**
|
||||
**/microsite/**
|
||||
**/canon-docs/**
|
||||
**/docs-ui/**
|
||||
**/templates/**
|
||||
**/sample-templates/**
|
||||
playwright.config.ts
|
||||
|
||||
@@ -40,6 +40,7 @@ yarn.lock @backstage/maintainers @backst
|
||||
/packages/repo-tools @backstage/tooling-maintainers
|
||||
/packages/techdocs-cli @backstage/techdocs-maintainers
|
||||
/packages/techdocs-cli-embedded-app @backstage/techdocs-maintainers
|
||||
/packages/ui @backstage/design-system-maintainers
|
||||
/packages/yarn-plugin @backstage/tooling-maintainers
|
||||
/plugins/app @backstage/framework-maintainers
|
||||
/plugins/app-* @backstage/framework-maintainers
|
||||
|
||||
@@ -10,6 +10,7 @@ Airbrakes
|
||||
ajv
|
||||
Alaria
|
||||
Alef
|
||||
allowedHosts
|
||||
allowlisted
|
||||
Anddddd
|
||||
Apdex
|
||||
@@ -43,6 +44,7 @@ bugfixes
|
||||
builtins
|
||||
bundler
|
||||
bundlers
|
||||
bursty
|
||||
callout
|
||||
CDNs
|
||||
Chai
|
||||
@@ -102,6 +104,8 @@ deliverables
|
||||
denormalized
|
||||
dependabot
|
||||
deps
|
||||
dequeue
|
||||
dequeueing
|
||||
deserialization
|
||||
destructured
|
||||
destructuring
|
||||
@@ -111,8 +115,6 @@ devcontainer
|
||||
devcontainers
|
||||
devops
|
||||
devs
|
||||
dequeue
|
||||
dequeueing
|
||||
dialogs
|
||||
disambiguator
|
||||
discoverability
|
||||
@@ -150,8 +152,8 @@ FireHydrant
|
||||
Firekube
|
||||
Firestore
|
||||
Fiverr
|
||||
Flightcontrol
|
||||
flightcontrol
|
||||
Flightcontrol
|
||||
Francesco
|
||||
Frontside
|
||||
Gaurav
|
||||
@@ -175,8 +177,8 @@ Hackathons
|
||||
haproxy
|
||||
hardcoded
|
||||
hardcoding
|
||||
Harness
|
||||
harness
|
||||
Harness
|
||||
Helidon
|
||||
Henneke
|
||||
Heroku
|
||||
@@ -199,9 +201,10 @@ Indal
|
||||
indexable
|
||||
ingestors
|
||||
inlined
|
||||
inlining
|
||||
inlinehilite
|
||||
inlining
|
||||
integrator's
|
||||
intellij
|
||||
interop
|
||||
interoperate
|
||||
iterable
|
||||
@@ -312,8 +315,8 @@ OpenSearch
|
||||
OpenShift
|
||||
openssl
|
||||
orgs
|
||||
Overridable
|
||||
overridable
|
||||
Overridable
|
||||
padding
|
||||
paddings
|
||||
pagerduty
|
||||
@@ -380,10 +383,10 @@ retryable
|
||||
reusability
|
||||
Reusability
|
||||
roadmaps
|
||||
rollbar
|
||||
rollout
|
||||
Roboto
|
||||
rollbar
|
||||
Rollbar
|
||||
rollout
|
||||
Rollup
|
||||
routable
|
||||
Routable
|
||||
@@ -399,9 +402,10 @@ sanitization
|
||||
scaffolded
|
||||
scaffolder
|
||||
Scaffolder
|
||||
scrollbar
|
||||
SCM
|
||||
SCMs
|
||||
scrollable
|
||||
scrollbar
|
||||
sdks
|
||||
seb
|
||||
semlas
|
||||
@@ -409,14 +413,15 @@ semver
|
||||
sendmail
|
||||
serializable
|
||||
Serverless
|
||||
severities
|
||||
shoutout
|
||||
SIG
|
||||
signoff
|
||||
SIGs
|
||||
siloed
|
||||
Sinon
|
||||
snackbars
|
||||
snackbar
|
||||
snackbars
|
||||
Snyk
|
||||
Sonarqube
|
||||
sourcemaps
|
||||
@@ -487,6 +492,7 @@ transpiled
|
||||
transpiler
|
||||
transpilers
|
||||
truthy
|
||||
tsconfig
|
||||
TSDoc
|
||||
typeahead
|
||||
ui
|
||||
@@ -537,7 +543,3 @@ zod
|
||||
Zolotusky
|
||||
zoomable
|
||||
zsh
|
||||
scrollable
|
||||
severities
|
||||
intellij
|
||||
tsconfig
|
||||
|
||||
@@ -23,7 +23,7 @@ jobs:
|
||||
comment-cache-key: ${{ steps.hash.outputs.COMMENT_FILE_HASH }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
disable-sudo: true
|
||||
egress-policy: block
|
||||
|
||||
@@ -14,7 +14,7 @@ jobs:
|
||||
if: ${{ github.event_name != 'pull_request' || github.event.action != 'closed' }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -23,7 +23,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ jobs:
|
||||
name: Test ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ jobs:
|
||||
name: Install ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -64,7 +64,7 @@ jobs:
|
||||
name: Verify ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -131,6 +131,10 @@ jobs:
|
||||
- name: build canon
|
||||
run: yarn --cwd packages/canon build
|
||||
|
||||
# For now BUI has a custom build script and needs to be built separately
|
||||
- name: build BUI
|
||||
run: yarn --cwd packages/ui build
|
||||
|
||||
- name: verify type dependencies
|
||||
run: yarn lint:type-deps
|
||||
|
||||
|
||||
@@ -10,7 +10,7 @@ jobs:
|
||||
timeout-minutes: 10
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -20,7 +20,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -23,7 +23,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -135,7 +135,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -246,7 +246,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -114,6 +114,10 @@ jobs:
|
||||
- name: build canon
|
||||
run: yarn --cwd packages/canon build
|
||||
|
||||
# For now BUI has a custom build script and needs to be built separately
|
||||
- name: build BUI
|
||||
run: yarn --cwd packages/ui build
|
||||
|
||||
- name: verify type dependencies
|
||||
run: yarn lint:type-deps
|
||||
|
||||
@@ -151,7 +155,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -16,7 +16,7 @@ jobs:
|
||||
if: github.repository == 'backstage/backstage'
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -20,7 +20,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@ jobs:
|
||||
steps:
|
||||
# Inspired by https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#using-data-from-the-triggering-workflow
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ jobs:
|
||||
if: github.repository == 'backstage/backstage' && ( github.event.pull_request || github.event.issue.pull_request )
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -4,11 +4,11 @@ on:
|
||||
branches: [master]
|
||||
|
||||
jobs:
|
||||
sync-canon-docs:
|
||||
sync-docs-ui:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -26,11 +26,11 @@ jobs:
|
||||
with:
|
||||
cache-prefix: ${{ runner.os }}-v20.x
|
||||
|
||||
- name: Checkout backstage/canon-docs
|
||||
- name: Checkout backstage/docs-ui
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
with:
|
||||
repository: backstage/canon-docs
|
||||
path: canon-external-docs
|
||||
repository: backstage/docs-ui
|
||||
path: bui-external-docs
|
||||
token: ${{ secrets.GH_SERVICE_ACCOUNT_TOKEN }}
|
||||
|
||||
- name: Configure Git
|
||||
@@ -39,22 +39,22 @@ jobs:
|
||||
git config --global user.name 'Github Canon Docs workflow'
|
||||
|
||||
- name: Install dependencies
|
||||
working-directory: canon-docs
|
||||
working-directory: docs-ui
|
||||
run: yarn install
|
||||
|
||||
- name: Build Canon Docs
|
||||
working-directory: canon-docs
|
||||
- name: Build Docs UI
|
||||
working-directory: docs-ui
|
||||
run: |
|
||||
yarn build
|
||||
|
||||
- name: Replace contents of canon-external-docs repo with docs build output
|
||||
working-directory: canon-external-docs
|
||||
- name: Replace contents of bui-external-docs repo with docs build output
|
||||
working-directory: bui-external-docs
|
||||
run: |
|
||||
git rm -rf .
|
||||
cp -R ../canon-docs/dist/. .
|
||||
cp -R ../docs-ui/dist/. .
|
||||
|
||||
- name: Commit to canon-storybook repo
|
||||
working-directory: canon-external-docs
|
||||
working-directory: bui-external-docs
|
||||
run: |
|
||||
git add .
|
||||
git commit -am "Canon Docs build for backstage/backstage@${{ github.sha }}"
|
||||
|
||||
@@ -10,7 +10,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -11,7 +11,7 @@ jobs:
|
||||
if: github.actor == 'dependabot[bot]' && github.repository == 'backstage/backstage'
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -11,7 +11,7 @@ jobs:
|
||||
if: github.actor == 'renovate[bot]' && github.repository == 'backstage/backstage'
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -14,7 +14,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -20,7 +20,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -42,7 +42,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ jobs:
|
||||
name: E2E Linux ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ jobs:
|
||||
name: E2E Linux ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ jobs:
|
||||
name: Techdocs
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ jobs:
|
||||
name: E2E Windows ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -33,7 +33,7 @@ jobs:
|
||||
name: E2E Windows ${{ matrix.node-version }}
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -14,7 +14,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ jobs:
|
||||
name: Microsite
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -137,7 +137,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -240,7 +240,7 @@ jobs:
|
||||
name: Microsite
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ jobs:
|
||||
name: Storybook
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ jobs:
|
||||
name: Storybook
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
@@ -49,10 +49,10 @@ jobs:
|
||||
run: yarn install --immutable
|
||||
working-directory: storybook
|
||||
|
||||
# Only for verification, the canon one is what we upload to Chromatic
|
||||
# Only for verification, the BUI one is what we upload to Chromatic
|
||||
- run: yarn build-storybook
|
||||
|
||||
- run: yarn --cwd packages/canon build-storybook
|
||||
- run: yarn --cwd packages/ui build-storybook
|
||||
|
||||
- uses: chromaui/action@1cfa065cbdab28f6ca3afaeb3d761383076a35aa # v11
|
||||
with:
|
||||
@@ -60,5 +60,5 @@ jobs:
|
||||
# projectToken intentionally shared to allow collaborators to run Chromatic on forks
|
||||
# https://www.chromatic.com/docs/custom-ci-provider#run-chromatic-on-external-forks-of-open-source-projects
|
||||
projectToken: chpt_dab72dc0f97d55b
|
||||
workingDir: packages/canon
|
||||
workingDir: packages/ui
|
||||
storybookBuildDir: storybook-static
|
||||
|
||||
@@ -29,7 +29,7 @@ jobs:
|
||||
|
||||
steps:
|
||||
- name: Harden Runner
|
||||
uses: step-security/harden-runner@cb605e52c26070c328afc4562f0b4ada7618a84e # v2.10.4
|
||||
uses: step-security/harden-runner@6c439dc8bdf85cadbbce9ed30d1c7b959517bc49 # v2.12.2
|
||||
with:
|
||||
egress-policy: audit
|
||||
|
||||
|
||||
+4
-4
@@ -1,10 +1,10 @@
|
||||
.yarn
|
||||
dist
|
||||
microsite
|
||||
canon-docs/.next
|
||||
canon-docs/public
|
||||
canon-docs/out
|
||||
packages/canon/css
|
||||
docs-ui/.next
|
||||
docs-ui/public
|
||||
docs-ui/out
|
||||
packages/ui/css
|
||||
coverage
|
||||
*.hbs
|
||||
templates
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
canon.backstage.io
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 14 KiB |
File diff suppressed because one or more lines are too long
@@ -1,34 +0,0 @@
|
||||
const fs = require('fs');
|
||||
const path = require('path');
|
||||
const { bundle } = require('lightningcss');
|
||||
|
||||
const source = '../../packages/canon/src/css';
|
||||
const destination = '../public';
|
||||
|
||||
const source1 = path.join(__dirname, `${source}/styles.css`);
|
||||
const destination1 = path.join(__dirname, `${destination}/styles.css`);
|
||||
|
||||
// Function to bundle and copy the CSS file
|
||||
const bundleAndCopyFile = async (source, destination) => {
|
||||
try {
|
||||
const result = await bundle({
|
||||
filename: source,
|
||||
minify: true,
|
||||
});
|
||||
|
||||
fs.writeFileSync(destination, result.code);
|
||||
console.log('File bundled and copied successfully!');
|
||||
} catch (err) {
|
||||
console.error('Error bundling file:', err);
|
||||
}
|
||||
};
|
||||
|
||||
// Initial bundle and copy
|
||||
Promise.all([bundleAndCopyFile(source1, destination1)])
|
||||
.then(() => {
|
||||
// Add an empty line after all operations are complete - It looks better in the terminal :)
|
||||
console.log('');
|
||||
})
|
||||
.catch(err => {
|
||||
console.error('Error in processing files:', err);
|
||||
});
|
||||
@@ -1,43 +0,0 @@
|
||||
import { changelog } from '@/utils/changelog';
|
||||
import { MDXRemote } from 'next-mdx-remote-client/rsc';
|
||||
import { formattedMDXComponents } from '@/mdx-components';
|
||||
|
||||
export function Changelog() {
|
||||
// Group changelog entries by version
|
||||
const groupedChangelog = changelog.reduce((acc, entry) => {
|
||||
if (!acc[entry.version]) {
|
||||
acc[entry.version] = [];
|
||||
}
|
||||
acc[entry.version].push(entry);
|
||||
return acc;
|
||||
}, {} as Record<string, typeof changelog>);
|
||||
|
||||
// Sort versions in descending order
|
||||
const sortedVersions = Object.keys(groupedChangelog).sort((a, b) =>
|
||||
b.localeCompare(a),
|
||||
);
|
||||
|
||||
const content = sortedVersions
|
||||
.map(version => {
|
||||
const entries = groupedChangelog[version];
|
||||
|
||||
return `## Version ${version}
|
||||
|
||||
${entries
|
||||
.map(e => {
|
||||
const prs =
|
||||
e.prs.length > 0 &&
|
||||
e.prs
|
||||
.map(
|
||||
pr =>
|
||||
`[#${pr}](https://github.com/backstage/backstage/pull/${pr})`,
|
||||
)
|
||||
.join(', ');
|
||||
return `- ${e.description} ${prs}`;
|
||||
})
|
||||
.join('\n')}`;
|
||||
})
|
||||
.join('\n');
|
||||
|
||||
return <MDXRemote components={formattedMDXComponents} source={content} />;
|
||||
}
|
||||
@@ -1,39 +0,0 @@
|
||||
import styles from './Sidebar.module.css';
|
||||
import { Docs } from './docs';
|
||||
import { Playground } from './playground';
|
||||
import Link from 'next/link';
|
||||
import { ScrollArea } from '@base-ui-components/react/scroll-area';
|
||||
|
||||
export const Sidebar = () => {
|
||||
return (
|
||||
<div className={styles.sidebar}>
|
||||
<ScrollArea.Root className={styles.root}>
|
||||
<ScrollArea.Viewport className={styles.viewport}>
|
||||
<div className={styles.content}>
|
||||
<div className={styles.logoContainer}>
|
||||
<Link href="/">
|
||||
<svg
|
||||
width="89"
|
||||
height="27"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
className={styles.logo}
|
||||
>
|
||||
<path d="M77.414 9.71h3.036v2.992l-.264-.022c.279-.88.748-1.65 1.408-2.31.675-.66 1.533-.99 2.574-.99 1.086 0 1.9.352 2.442 1.056.558.689.836 1.598.836 2.728v7.502H84.41v-6.6c0-.66-.117-1.159-.352-1.496-.234-.338-.623-.506-1.166-.506-.601 0-1.122.271-1.562.814a4.321 4.321 0 0 0-.88 1.848v5.94h-3.036V9.71ZM69.868 21.04c-1.13 0-2.142-.257-3.036-.77a5.547 5.547 0 0 1-2.068-2.09c-.484-.895-.726-1.892-.726-2.992 0-1.115.242-2.112.726-2.992a5.503 5.503 0 0 1 2.068-2.112c.88-.514 1.892-.77 3.036-.77 1.144 0 2.156.256 3.036.77a5.347 5.347 0 0 1 2.046 2.112c.498.88.748 1.87.748 2.97 0 1.114-.25 2.12-.748 3.014a5.343 5.343 0 0 1-2.068 2.09c-.88.513-1.885.77-3.014.77Zm0-2.618c.557 0 1.048-.132 1.474-.396a2.79 2.79 0 0 0 .99-1.144c.234-.499.352-1.064.352-1.694 0-.63-.118-1.188-.352-1.672a2.764 2.764 0 0 0-.99-1.166c-.426-.279-.917-.418-1.474-.418-.558 0-1.05.14-1.474.418a2.764 2.764 0 0 0-.99 1.166c-.22.484-.33 1.041-.33 1.672 0 .63.11 1.195.33 1.694.234.484.564.865.99 1.144.425.264.916.396 1.474.396ZM52.385 9.71h3.036v2.992l-.264-.022c.279-.88.748-1.65 1.408-2.31.675-.66 1.533-.99 2.574-.99 1.085 0 1.9.352 2.442 1.056.557.689.836 1.598.836 2.728v7.502h-3.036v-6.6c0-.66-.117-1.159-.352-1.496-.235-.338-.623-.506-1.166-.506-.601 0-1.122.271-1.562.814a4.321 4.321 0 0 0-.88 1.848v5.94h-3.036V9.71ZM43.904 20.952c-1.026 0-1.87-.308-2.53-.924-.66-.616-.99-1.416-.99-2.398 0-1.115.418-2.01 1.254-2.684.85-.69 2.105-1.034 3.762-1.034h2.75l-.924.352v-.462c0-.572-.176-1.02-.528-1.342-.352-.338-.931-.506-1.738-.506-.69 0-1.386.154-2.09.462-.704.308-1.29.69-1.76 1.144v-2.882c.47-.352 1.1-.66 1.892-.924a7.942 7.942 0 0 1 2.486-.396c1.599 0 2.78.41 3.542 1.232.778.806 1.166 1.914 1.166 3.322v5.742c0 .176.008.352.022.528.03.161.066.322.11.484h-3.014v-3.3l.044 1.386a4.044 4.044 0 0 1-1.32 1.606c-.572.396-1.283.594-2.134.594Zm.858-2.156c.558 0 1.049-.206 1.474-.616.44-.426.77-.954.99-1.584v-.792h-1.562c-.762 0-1.334.146-1.716.44-.381.278-.572.674-.572 1.188 0 .41.125.74.374.99.264.25.602.374 1.012.374ZM34.66 21.04c-1.525 0-2.874-.345-4.047-1.034-1.174-.704-2.09-1.68-2.75-2.926-.646-1.247-.968-2.662-.968-4.246 0-1.584.322-2.992.968-4.224.66-1.232 1.576-2.193 2.75-2.882 1.173-.704 2.522-1.056 4.048-1.056.968 0 1.818.11 2.552.33.748.22 1.356.506 1.826.858v3.498c-.396-.484-.96-.895-1.694-1.232-.719-.338-1.51-.506-2.376-.506-.939 0-1.775.22-2.508.66-.719.44-1.284 1.056-1.694 1.848-.396.792-.594 1.694-.594 2.706 0 1.026.198 1.943.594 2.75.41.792.975 1.408 1.694 1.848.733.44 1.57.66 2.508.66.88 0 1.68-.162 2.398-.484.718-.323 1.276-.726 1.672-1.21v3.41a5.686 5.686 0 0 1-1.87.902c-.704.22-1.54.33-2.508.33ZM11.275 6.271c.276.526.019 1.152-.464 1.498a5.846 5.846 0 0 0 1.004 10.082c.454.205.789.632.789 1.13v6.206a.837.837 0 0 1-.838.837C5.33 26.024.112 20.804.112 14.366V.862C.112.399.487.024.95.024c4.483 0 8.376 2.533 10.325 6.247Z" />
|
||||
<path d="M14.037 16.729a4.237 4.237 0 0 0 4.234-4.24 4.237 4.237 0 0 0-4.234-4.242 4.237 4.237 0 0 0-4.234 4.241 4.237 4.237 0 0 0 4.234 4.24Z" />
|
||||
</svg>
|
||||
</Link>
|
||||
</div>
|
||||
<div className={styles.menu}>
|
||||
<Docs />
|
||||
<Playground />
|
||||
</div>
|
||||
</div>
|
||||
</ScrollArea.Viewport>
|
||||
<ScrollArea.Scrollbar className={styles.scrollbar}>
|
||||
<ScrollArea.Thumb className={styles.thumb} />
|
||||
</ScrollArea.Scrollbar>
|
||||
</ScrollArea.Root>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
@@ -1,27 +0,0 @@
|
||||
.root {
|
||||
margin-top: 40px;
|
||||
}
|
||||
|
||||
.list {
|
||||
display: flex;
|
||||
gap: var(--canon-space-6);
|
||||
border-bottom: 1px solid var(--border);
|
||||
position: relative;
|
||||
margin-bottom: var(--canon-space-6);
|
||||
}
|
||||
|
||||
.tab {
|
||||
all: unset;
|
||||
cursor: pointer;
|
||||
padding-bottom: 8px;
|
||||
}
|
||||
|
||||
.indicator {
|
||||
position: absolute;
|
||||
bottom: -1px;
|
||||
left: var(--active-tab-left);
|
||||
width: var(--active-tab-width);
|
||||
height: 1px;
|
||||
background-color: var(--primary);
|
||||
transition: all 0.2s ease-in-out;
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
# Catalog Read-Write Split
|
||||
|
||||
This article gives an overview of how you might split your catalog deployment into two - one which handles only reads (the read part of the API), and another that handles everything else (the write part of the API, and processing and ingestion etc).
|
||||
|
||||
This is useful for several reasons:
|
||||
|
||||
- The performance characteristics and scaling needs of those two concerns typically differ significantly
|
||||
- Moving the bursty processing and ingestion load on a separate deployment can make the important read part of the API have more deterministic response times
|
||||
- It opens up for easier cross region deployment of read nodes, while having write nodes in a single "home" region
|
||||
- It also opens up for primary/secondary split of the underlying database, with streaming replication
|
||||
|
||||
## Overview
|
||||
|
||||
This is a rough overview of what we will go through:
|
||||
|
||||
- Ensure that all frontend code uses `catalogApiRef`, and all backend code uses `catalogServiceRef`, for talking to the catalog
|
||||
- Add a separate discovery name for the write deployment
|
||||
- Register both frontend and backend implementations of the catalog client that know to send traffic to the right discovery name as needed
|
||||
- Set up the backend itself with dedicated read and write configuration
|
||||
- Split the deployment into two
|
||||
- Follow up with a database split, if desired
|
||||
|
||||
## 1. Prerequisite: Establish usage of catalog client refs
|
||||
|
||||
First, ensure that all of your code uses _injected_ catalog clients for its catalog communications needs instead of making their own with `new`. For frontend code that means leveraging `catalogApiRef`, and for backend it means leveraging `catalogServiceRef`. This is what enables the sort of wholesale injection of custom behaviors that we are about to do, and is a strongly recommended best practice either way.
|
||||
|
||||
- ✅ Search through your projects and ensure that there are no `new CatalogClient` calls. If you find any, consider rewriting that code to instead having the client injected through leveraging the corresponding ref.
|
||||
|
||||
- ✅ Search through your projects and ensure that you do _not_ import the `catalogServiceRef` that specifically is in the `@backstage/plugin-catalog-node/alpha` export. That one has been deprecated for a long time and will not be targeted by this guide. If you find any, consider rewriting that code to instead inject the client from `@backstage/plugin-catalog-node` (note the lack of `/alpha`).
|
||||
|
||||
> [!TIP]
|
||||
> If you find usages of `new CatalogClient` in tests, you can normally leave those as-is. You can however consider to later try out the `catalogApiMock` from `@backstage/plugin-catalog-react/testUtils` for frontend tests, and `catalogServiceMock` from `@backstage/plugin-catalog-node/testUtils` for backend tests. These allow you to inject a client that behaves like a complete fake catalog backend with entities in it, without complex mocking.
|
||||
|
||||
## 2. Decide your deployment split structure
|
||||
|
||||
We will be defining a fake plugin ID called `catalog-write`. In addition to your current single catalog deployment you will add a second one that receives traffic for `catalog-write`. You need to decide upon what your ingress to those two deployments will look like. This is highly company dependent, so we cannot give general guidance.
|
||||
|
||||
This guide will however NOT split the code base into two. It will instead change your catalog backend code in such a way that it can support either deployment. This is all very flexible and you can tweak it as you see fit, but that's what worked well for us.
|
||||
|
||||
This guide will assume that when all is said and done, requests for the `catalog` plugin ID resolve to the URL `https://catalog-read.example.net/api/catalog`, and requests for the `catalog-write` plugin ID resolve to the URL `https://catalog-write.example.net/api/catalog`. This is just for illustration and you shall change these to their actual correct values at your company.
|
||||
|
||||
- ✅ Copy the contents of [the `app-config.yaml` file](./workspace/app-config.yaml) to your own. We will assume that these exact settings are applied both to your frontend and your catalog (read AND write) deployment. For now, if you are applying this guide step by step rather than all at once, you can set the URLs in there to point to your good old pre-split deployment and only update them again after the split.
|
||||
|
||||
> [!TIP]
|
||||
> As a future refactor, you could instead break out this behavior into a custom injected discovery implementation in a library that all your projects can import. That takes a few more steps and is left as a separate exercise. If you already have such a library in your internal NPM, feel free to put it there to begin with and import from there.
|
||||
|
||||
## 3. Get split-aware catalog clients in place
|
||||
|
||||
Now let's put clients in place whose methods send traffic to either `catalog` or `catalog-write` as needed.
|
||||
|
||||
- ✅ Copy [the `catalogApi.ts` file](./workspace/packages/app/src/catalogApi.ts) into your `packages/app/src` directory of the project where you develop your Backstage frontend. Then reference that file's API factory in your `packages/app/src/apis.ts` file, [as illustrated here](./workspace/packages/app/src/apis.ts).
|
||||
|
||||
- ✅ Copy [the `catalogService.ts` file](./workspace/packages/backend/src/catalogService.ts) into your `packages/backend/src` directory of the project where you develop your Software Catalog backend. We will reference the file itself in the step below.
|
||||
|
||||
After step 4 below is complete, these will be automatically picked up and used by all callers.
|
||||
|
||||
> [!TIP]
|
||||
> As a future refactor, you could instead break out these clients into a node and a react library that all your projects can import. That takes a few more steps and is left as a separate exercise. If you already have such libraries in your internal NPM, feel free to put them there to begin with and import from there.
|
||||
|
||||
## 4. Split the catalog backend
|
||||
|
||||
We'll now perform the actual split of the catalog backend. You will make separate config files that apply to each, and adapt the backend code to handle both cases seamlessly.
|
||||
|
||||
- ✅ Duplicate your deployment. It's highly company dependent how this is done. Some may for example duplicate some declarative `Deployment` and `Service` k8s manifests etc, but it depends.
|
||||
|
||||
- ✅ Copy [the `app-config.catalog-read.yaml`] and [the `app-config.catalog-write.yaml`] files into your project root. You must set up your read and write deployments to load their respective files with the `--config` flag, _in addition to_ the `app-config.yaml` file and possibly `app-config.production.yaml` that they already loaded.
|
||||
|
||||
- ✅ Copy [the `config.d.ts`](./workspace/config.d.ts) file to your catalog backend directory at `packages/backend`. You should refer to it in the `package.json`'s `"files"` and `"configSchema"` fields [as per usual](https://backstage.io/docs/conf/defining).
|
||||
|
||||
- ✅ Update your `packages/backend/src/index.ts` file to match [the proposed structure here](./workspace/packages/backend/src/index.ts). Note how it applies the custom catalog service we copied in the previous step, and has a separate section for write-only concerns.
|
||||
|
||||
## 5. Region and database split
|
||||
|
||||
After the above is deployed and working, you are well set up for some next step.
|
||||
|
||||
- Scaling your readers across multiple regions and add geo-aware routing to them, while keeping writers in a "home" region
|
||||
- Splitting the database server into a primary that the write nodes connect to, and regional secondaries with streaming replication from the primary
|
||||
|
||||
But all of this is left as an exercise for the reader.
|
||||
|
||||
## 6. Help make this smoother
|
||||
|
||||
Congratulations on successfully performing your split!
|
||||
|
||||
We would love [some help](https://github.com/backstage/backstage/blob/master/CONTRIBUTING.md) with making this process easier for others. For example, if read nodes could automatically transparently proxy traffic to write nodes as needed, we would need far less fiddling with clients at a relatively small extra cost.
|
||||
@@ -0,0 +1,12 @@
|
||||
# This file should be given to the catalog read nodes.
|
||||
|
||||
backend:
|
||||
database:
|
||||
# disable running database migrations for every plugin/module
|
||||
skipMigrations: true
|
||||
|
||||
catalog:
|
||||
role: read
|
||||
|
||||
# disable processing engine
|
||||
processingInterval: false
|
||||
@@ -0,0 +1,4 @@
|
||||
# This file should be given to the catalog write nodes.
|
||||
|
||||
catalog:
|
||||
role: write
|
||||
@@ -0,0 +1,19 @@
|
||||
# This is in your regular app-config.
|
||||
|
||||
# This introduces a made-up "catalog-write" plugin ID that the frontend catalog
|
||||
# API implementation can use to resolve where to find the write nodes.
|
||||
discovery:
|
||||
endpoints:
|
||||
#
|
||||
# TODO: Replace with actual URLs
|
||||
#
|
||||
# NOTE: Each target can also be an object with "internal" and "external"
|
||||
# keys with different URLs, if they should be different when called by
|
||||
# backends and the frontend, respectively.
|
||||
#
|
||||
- target: https://catalog-read.example.net/api/catalog
|
||||
plugins:
|
||||
- catalog
|
||||
- target: https://catalog-write.example.net/api/catalog
|
||||
plugins:
|
||||
- catalog-write
|
||||
@@ -0,0 +1,5 @@
|
||||
export interface Config {
|
||||
catalog: {
|
||||
role: 'read' | 'write';
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
import { AnyApiFactory } from '@backstage/core-plugin-api';
|
||||
import { catalogApiFactory } from './catalogApi';
|
||||
|
||||
// This file is already present in a typical Backstage app. We are just adding
|
||||
// the catalog API factory here to ensure that the frontend sends requests to
|
||||
// the correct set of catalog nodes depending on whether it's a read or a write
|
||||
// operation.
|
||||
export const apis: AnyApiFactory[] = [
|
||||
// ...other APIs here...
|
||||
catalogApiFactory,
|
||||
];
|
||||
@@ -0,0 +1,174 @@
|
||||
import {
|
||||
AddLocationRequest,
|
||||
AddLocationResponse,
|
||||
CatalogApi,
|
||||
CatalogClient,
|
||||
CatalogRequestOptions,
|
||||
GetEntitiesByRefsRequest,
|
||||
GetEntitiesByRefsResponse,
|
||||
GetEntitiesRequest,
|
||||
GetEntitiesResponse,
|
||||
GetEntityAncestorsRequest,
|
||||
GetEntityAncestorsResponse,
|
||||
GetEntityFacetsRequest,
|
||||
GetEntityFacetsResponse,
|
||||
GetLocationsResponse,
|
||||
Location,
|
||||
QueryEntitiesRequest,
|
||||
QueryEntitiesResponse,
|
||||
ValidateEntityResponse,
|
||||
} from '@backstage/catalog-client';
|
||||
import { CompoundEntityRef, Entity } from '@backstage/catalog-model';
|
||||
import {
|
||||
createApiFactory,
|
||||
DiscoveryApi,
|
||||
discoveryApiRef,
|
||||
FetchApi,
|
||||
fetchApiRef,
|
||||
} from '@backstage/core-plugin-api';
|
||||
import { catalogApiRef } from '@backstage/plugin-catalog-react';
|
||||
|
||||
/**
|
||||
* Implements the catalog client for frontends, by using a custom service
|
||||
* discovery to achieve read/write segregation.
|
||||
*/
|
||||
export class ReadWriteSplitCatalogClient implements CatalogApi {
|
||||
#write: CatalogApi;
|
||||
#read: CatalogApi;
|
||||
|
||||
constructor(options: { discoveryApi: DiscoveryApi; fetchApi: FetchApi }) {
|
||||
this.#read = new CatalogClient({
|
||||
fetchApi: options.fetchApi,
|
||||
discoveryApi: {
|
||||
// This uses the normal "catalog" plugin ID
|
||||
getBaseUrl: () => options.discoveryApi.getBaseUrl('catalog'),
|
||||
},
|
||||
});
|
||||
this.#write = new CatalogClient({
|
||||
fetchApi: options.fetchApi,
|
||||
discoveryApi: {
|
||||
// This uses the made-up "catalog-write" plugin ID (see app-config.yaml
|
||||
// which defines a custom discovery endpoint for this)
|
||||
getBaseUrl: () => options.discoveryApi.getBaseUrl('catalog-write'),
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
getEntities(
|
||||
request?: GetEntitiesRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<GetEntitiesResponse> {
|
||||
return this.#read.getEntities(request, options);
|
||||
}
|
||||
|
||||
getEntitiesByRefs(
|
||||
request: GetEntitiesByRefsRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<GetEntitiesByRefsResponse> {
|
||||
return this.#read.getEntitiesByRefs(request, options);
|
||||
}
|
||||
|
||||
queryEntities(
|
||||
request?: QueryEntitiesRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<QueryEntitiesResponse> {
|
||||
return this.#read.queryEntities(request, options);
|
||||
}
|
||||
|
||||
getEntityAncestors(
|
||||
request: GetEntityAncestorsRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<GetEntityAncestorsResponse> {
|
||||
return this.#read.getEntityAncestors(request, options);
|
||||
}
|
||||
|
||||
getEntityByRef(
|
||||
entityRef: string | CompoundEntityRef,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<Entity | undefined> {
|
||||
return this.#read.getEntityByRef(entityRef, options);
|
||||
}
|
||||
|
||||
removeEntityByUid(
|
||||
uid: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#write.removeEntityByUid(uid, options);
|
||||
}
|
||||
|
||||
refreshEntity(
|
||||
entityRef: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#write.refreshEntity(entityRef, options);
|
||||
}
|
||||
|
||||
getEntityFacets(
|
||||
request: GetEntityFacetsRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<GetEntityFacetsResponse> {
|
||||
return this.#read.getEntityFacets(request, options);
|
||||
}
|
||||
|
||||
getLocations(
|
||||
request?: {},
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<GetLocationsResponse> {
|
||||
return this.#read.getLocations(request, options);
|
||||
}
|
||||
|
||||
getLocationById(
|
||||
id: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#read.getLocationById(id, options);
|
||||
}
|
||||
|
||||
getLocationByRef(
|
||||
locationRef: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#read.getLocationByRef(locationRef, options);
|
||||
}
|
||||
|
||||
addLocation(
|
||||
location: AddLocationRequest,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<AddLocationResponse> {
|
||||
return this.#write.addLocation(location, options);
|
||||
}
|
||||
|
||||
removeLocationById(
|
||||
id: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#write.removeLocationById(id, options);
|
||||
}
|
||||
|
||||
getLocationByEntity(
|
||||
entityRef: string | CompoundEntityRef,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#read.getLocationByEntity(entityRef, options);
|
||||
}
|
||||
|
||||
validateEntity(
|
||||
entity: Entity,
|
||||
locationRef: string,
|
||||
options?: CatalogRequestOptions,
|
||||
): Promise<ValidateEntityResponse> {
|
||||
return this.#write.validateEntity(entity, locationRef, options);
|
||||
}
|
||||
}
|
||||
|
||||
// You should pass this to createApp.
|
||||
export const catalogApiFactory = createApiFactory({
|
||||
api: catalogApiRef,
|
||||
deps: { discoveryApi: discoveryApiRef, fetchApi: fetchApiRef },
|
||||
factory: ({ discoveryApi, fetchApi }) => {
|
||||
return new ReadWriteSplitCatalogClient({
|
||||
discoveryApi,
|
||||
fetchApi,
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -0,0 +1,231 @@
|
||||
import {
|
||||
AuthService,
|
||||
coreServices,
|
||||
createServiceFactory,
|
||||
DiscoveryService,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import {
|
||||
AddLocationRequest,
|
||||
AddLocationResponse,
|
||||
CatalogApi,
|
||||
CatalogClient,
|
||||
CatalogRequestOptions,
|
||||
GetEntitiesByRefsRequest,
|
||||
GetEntitiesByRefsResponse,
|
||||
GetEntitiesRequest,
|
||||
GetEntitiesResponse,
|
||||
GetEntityAncestorsRequest,
|
||||
GetEntityAncestorsResponse,
|
||||
GetEntityFacetsRequest,
|
||||
GetEntityFacetsResponse,
|
||||
GetLocationsResponse,
|
||||
Location,
|
||||
QueryEntitiesRequest,
|
||||
QueryEntitiesResponse,
|
||||
ValidateEntityResponse,
|
||||
} from '@backstage/catalog-client';
|
||||
import { CompoundEntityRef, Entity } from '@backstage/catalog-model';
|
||||
import {
|
||||
CatalogService,
|
||||
CatalogServiceRequestOptions,
|
||||
catalogServiceRef,
|
||||
} from '@backstage/plugin-catalog-node';
|
||||
|
||||
/**
|
||||
* Implements the catalog client for backends, by using a custom service
|
||||
* discovery to achieve read/write segregation.
|
||||
*/
|
||||
export class ReadWriteSplitCatalogService implements CatalogService {
|
||||
readonly #auth: AuthService;
|
||||
readonly #catalogRead: CatalogApi;
|
||||
readonly #catalogWrite: CatalogApi;
|
||||
|
||||
constructor(options: { auth: AuthService; discovery: DiscoveryService }) {
|
||||
this.#auth = options.auth;
|
||||
this.#catalogRead = new CatalogClient({
|
||||
discoveryApi: {
|
||||
// This uses the normal "catalog" plugin ID
|
||||
getBaseUrl: () => options.discovery.getBaseUrl('catalog'),
|
||||
},
|
||||
});
|
||||
this.#catalogWrite = new CatalogClient({
|
||||
discoveryApi: {
|
||||
// This uses the made-up "catalog-write" plugin ID (see app-config.yaml
|
||||
// which defines a custom discovery endpoint for this)
|
||||
getBaseUrl: () => options.discovery.getBaseUrl('catalog-write'),
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
async getEntities(
|
||||
request: GetEntitiesRequest | undefined,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<GetEntitiesResponse> {
|
||||
return this.#catalogRead.getEntities(
|
||||
request,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getEntitiesByRefs(
|
||||
request: GetEntitiesByRefsRequest,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<GetEntitiesByRefsResponse> {
|
||||
return this.#catalogRead.getEntitiesByRefs(
|
||||
request,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async queryEntities(
|
||||
request: QueryEntitiesRequest | undefined,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<QueryEntitiesResponse> {
|
||||
return this.#catalogRead.queryEntities(
|
||||
request,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getEntityAncestors(
|
||||
request: GetEntityAncestorsRequest,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<GetEntityAncestorsResponse> {
|
||||
return this.#catalogRead.getEntityAncestors(
|
||||
request,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getEntityByRef(
|
||||
entityRef: string | CompoundEntityRef,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<Entity | undefined> {
|
||||
return this.#catalogRead.getEntityByRef(
|
||||
entityRef,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async removeEntityByUid(
|
||||
uid: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#catalogWrite.removeEntityByUid(
|
||||
uid,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async refreshEntity(
|
||||
entityRef: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#catalogWrite.refreshEntity(
|
||||
entityRef,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getEntityFacets(
|
||||
request: GetEntityFacetsRequest,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<GetEntityFacetsResponse> {
|
||||
return this.#catalogRead.getEntityFacets(
|
||||
request,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getLocations(
|
||||
options: CatalogRequestOptions,
|
||||
): Promise<GetLocationsResponse> {
|
||||
return this.#catalogRead.getLocations(options);
|
||||
}
|
||||
|
||||
async getLocationById(
|
||||
id: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#catalogRead.getLocationById(
|
||||
id,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getLocationByRef(
|
||||
locationRef: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#catalogRead.getLocationByRef(
|
||||
locationRef,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async addLocation(
|
||||
location: AddLocationRequest,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<AddLocationResponse> {
|
||||
return this.#catalogWrite.addLocation(
|
||||
location,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async removeLocationById(
|
||||
id: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<void> {
|
||||
return this.#catalogWrite.removeLocationById(
|
||||
id,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async getLocationByEntity(
|
||||
entityRef: string | CompoundEntityRef,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<Location | undefined> {
|
||||
return this.#catalogRead.getLocationByEntity(
|
||||
entityRef,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async validateEntity(
|
||||
entity: Entity,
|
||||
locationRef: string,
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<ValidateEntityResponse> {
|
||||
return this.#catalogWrite.validateEntity(
|
||||
entity,
|
||||
locationRef,
|
||||
await this.#getOptions(options),
|
||||
);
|
||||
}
|
||||
|
||||
async #getOptions(
|
||||
options: CatalogServiceRequestOptions,
|
||||
): Promise<CatalogRequestOptions> {
|
||||
return this.#auth.getPluginRequestToken({
|
||||
onBehalfOf: options.credentials,
|
||||
targetPluginId: 'catalog',
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
// You should register this in your backend.
|
||||
export const catalogService = createServiceFactory({
|
||||
service: catalogServiceRef,
|
||||
deps: {
|
||||
auth: coreServices.auth,
|
||||
discovery: coreServices.discovery,
|
||||
},
|
||||
async factory({ auth, discovery }) {
|
||||
return new ReadWriteSplitCatalogService({
|
||||
auth,
|
||||
discovery,
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -0,0 +1,34 @@
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import {
|
||||
coreServices,
|
||||
createBackendFeatureLoader,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { catalogService } from './catalogService';
|
||||
|
||||
const backend = createBackend();
|
||||
|
||||
backend.add(import('@backstage/plugin-catalog-backend'));
|
||||
backend.add(catalogService);
|
||||
// Here at the root level, you can add more features that you want to apply to
|
||||
// BOTH the read and write nodes, as needed.
|
||||
|
||||
backend.add(
|
||||
createBackendFeatureLoader({
|
||||
deps: { config: coreServices.rootConfig },
|
||||
async *loader({ config }) {
|
||||
if (config.getString('catalog.role') !== 'write') {
|
||||
return;
|
||||
}
|
||||
|
||||
// Here inside the loader, you can add more features that you want to
|
||||
// apply to ONLY the write nodes, as needed. This is where providers and
|
||||
// processors go, for example. The incremental ingestion provider line
|
||||
// below is just an example.
|
||||
yield import(
|
||||
'@backstage/plugin-catalog-backend-module-incremental-ingestion'
|
||||
);
|
||||
},
|
||||
}),
|
||||
);
|
||||
|
||||
backend.start();
|
||||
@@ -1,6 +1,6 @@
|
||||
# Canon Docs
|
||||
# Backstage UI Docs
|
||||
|
||||
Canon is our internal UI library built for Backstage. We built this website to document the library and its components. You can view this website [here](https://canon.backstage.io).
|
||||
Backstage UI is our internal UI library built for Backstage. We built this website to document the library and its components. You can view this website [here](https://ui.backstage.io).
|
||||
|
||||
## How to run locally
|
||||
|
||||
@@ -1,12 +1,15 @@
|
||||
{
|
||||
"name": "canon-docs",
|
||||
"name": "docs-ui",
|
||||
"version": "0.1.0",
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"build": "npm run build:css && next build",
|
||||
"build:css": "node scripts/build-css.js",
|
||||
"prebuild": "yarn sync:css",
|
||||
"build": "next build",
|
||||
"lint": "next lint",
|
||||
"start": "npm run build:css && next dev"
|
||||
"prestart": "yarn sync:css",
|
||||
"start": "concurrently \"yarn sync:css:watch\" \"next dev\"",
|
||||
"sync:css": "node scripts/sync-css.js",
|
||||
"sync:css:watch": "node scripts/sync-css.js --watch"
|
||||
},
|
||||
"resolutions": {
|
||||
"@types/react": "19.1.8",
|
||||
@@ -14,6 +17,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@codemirror/lang-sass": "^6.0.2",
|
||||
"@codemirror/view": "^6.34.4",
|
||||
"@lezer/highlight": "^1.2.1",
|
||||
"@mdx-js/loader": "^3.1.0",
|
||||
"@mdx-js/react": "^3.1.0",
|
||||
@@ -25,6 +29,7 @@
|
||||
"motion": "^12.4.1",
|
||||
"next": "15.3.4",
|
||||
"next-mdx-remote-client": "^2.1.2",
|
||||
"prop-types": "^15.8.1",
|
||||
"react": "19.1.0",
|
||||
"react-dom": "19.1.0",
|
||||
"react-frame-component": "^5.2.7",
|
||||
@@ -36,6 +41,8 @@
|
||||
"@types/node": "^20",
|
||||
"@types/react": "19.1.8",
|
||||
"@types/react-dom": "19.1.6",
|
||||
"chokidar": "^3.6.0",
|
||||
"concurrently": "^8.2.2",
|
||||
"eslint": "^8",
|
||||
"eslint-config-next": "15.3.4",
|
||||
"lightningcss": "^1.28.2",
|
||||
@@ -0,0 +1 @@
|
||||
ui.backstage.io
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user