Merge branch 'backstage:master' into master

This commit is contained in:
Piotr Piątkiewicz
2024-06-12 16:08:26 +02:00
committed by GitHub
542 changed files with 9209 additions and 2126 deletions
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/cli-node': patch
---
Added new plugin metadata fields to `BackstagePackageJson` type.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/backend-plugin-api': patch
---
In tests, return `null` rather than throwing an error when trying to get the `ExtensionPoint.T` property, so that tests asserting the property are not easily broken.
+13
View File
@@ -0,0 +1,13 @@
---
'@backstage/plugin-auth-node': patch
---
Updated scope management for OAuth providers, where the `createOAuthAuthenticator` now accepts a new collection of `scopes` options:
- `scopes.persist` - Whether scopes should be persisted, replaces the `shouldPersistScopes` option.
- `scopes.required` - A list of required scopes that will always be requested.
- `scopes.transform` - A function that can be used to transform the scopes before they are requested.
The `createOAuthProviderFactory` has also received a new `additionalScopes` option, and will also read `additionalScopes` from the auth provider configuration. Both of these can be used to add additional scopes that should always be requested.
A significant change under the hood that this new scope management brings is that providers that persist scopes will now always merge the already granted scopes with the requested ones. The previous behavior was that the full authorization flow would not include existing scopes, while the refresh flow would only include the existing scopes.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/backend-test-utils': patch
---
The type `MockDirectoryOptions` was renamed to `CreateMockDirectoryOptions` so that it's clear these options are exclusive to the mock directory factory.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-atlassian-provider': minor
---
**BREAKING**: The `scope` and `scopes` config options have been removed and replaced by the standard `additionalScopes` config. In addition, the `offline_access`, `read:jira-work`, and `read:jira-user` scopes have been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-bitbucket-provider': patch
---
Added support for the new shared `additionalScopes` configuration. In addition, the `account` scope has been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-github-provider': patch
---
Added support for the new shared `additionalScopes` configuration. In addition, the `read:user` scope has been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-gitlab-provider': patch
---
Added support for the new shared `additionalScopes` configuration. In addition, the `read_user` scope has been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-google-provider': patch
---
Added support for the new shared `additionalScopes` configuration. In addition, the `openid`, `userinfo.email`, and `userinfo.profile` scopes have been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-microsoft-provider': patch
---
Added support for the new shared `additionalScopes` configuration.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-oauth2-provider': minor
---
**BREAKING**: The `scope` config option have been removed and replaced by the standard `additionalScopes` config.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-oidc-provider': minor
---
**BREAKING**: The `scope` config option have been removed and replaced by the standard `additionalScopes` config. In addition, `openid`, `profile`, and `email` scopes have been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-okta-provider': patch
---
Added support for the new shared `additionalScopes` configuration, which means it can now also be specified as an array. In addition, the `openid`, `email`, `profile`, and `offline_access` scopes have been set to required and will always be present.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-pinniped-provider': patch
---
**BREAKING**: The `scope` config option have been removed and replaced by the standard `additionalScopes` config. In addition, the `openid`, `pinniped:request-audience`, `username`, and `offline_access` scopes have been set to required and will always be present.
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-vmware-cloud-provider': minor
---
**BREAKING**: The `scope` config option have been removed and replaced by the standard `additionalScopes` config. In addition, `openid`, and `offline_access` scopes have been set to required and will always be present.
+12
View File
@@ -0,0 +1,12 @@
---
'@backstage/integration': minor
---
**BREAKING** Removed deprecated code from when casing was changed from `GitHub` to `Github` nearly two years ago. The following items have been removed:
- `getGitHubFileFetchUrl` (use `getGithubFileFetchUrl` instead)
- `GitHubIntegrationConfig` (use `GithubIntegrationConfig` instead)
- `GitHubIntegration` (use `GithubIntegration` instead)
- `readGitHubIntegrationConfig` (use `readGithubIntegrationConfig` instead)
- `readGitHubIntegrationConfigs` (use `readGithubIntegrationConfigs` instead)
- `replaceGitHubUrlType` (use `replaceGithubUrlType` instead)
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-scaffolder-backend': patch
---
Fixing issues with log redaction in the scaffolder logs
+15
View File
@@ -0,0 +1,15 @@
---
'@backstage/backend-plugin-api': patch
---
Deprecated all of the `UrlReader` related type names and replaced them with prefixed versions. Please update your imports.
- `ReadTreeOptions` was renamed to `UrlReaderReadTreeOptions`
- `ReadTreeResponse` was renamed to `UrlReaderReadTreeResponse`
- `ReadTreeResponseDirOptions` was renamed to `UrlReaderReadTreeResponseDirOptions`
- `ReadTreeResponseFile` was renamed to `UrlReaderReadTreeResponseFile`
- `ReadUrlResponse` was renamed to `UrlReaderReadUrlResponse`
- `ReadUrlOptions` was renamed to `UrlReaderReadUrlOptions`
- `SearchOptions` was renamed to `UrlReaderSearchOptions`
- `SearchResponse` was renamed to `UrlReaderSearchResponse`
- `SearchResponseFile` was renamed to `UrlReaderSearchResponseFile`
+136
View File
@@ -0,0 +1,136 @@
---
'@backstage/plugin-scaffolder-backend-module-confluence-to-markdown': patch
'@backstage/plugin-auth-backend-module-cloudflare-access-provider': patch
'@backstage/plugin-catalog-backend-module-scaffolder-entity-model': patch
'@backstage/plugin-search-backend-module-stack-overflow-collator': patch
'@backstage/plugin-catalog-backend-module-incremental-ingestion': patch
'@backstage/plugin-auth-backend-module-azure-easyauth-provider': patch
'@backstage/plugin-permission-backend-module-allow-all-policy': patch
'@backstage/plugin-scaffolder-backend-module-bitbucket-server': patch
'@backstage/plugin-auth-backend-module-oauth2-proxy-provider': patch
'@backstage/plugin-auth-backend-module-vmware-cloud-provider': patch
'@backstage/plugin-scaffolder-backend-module-bitbucket-cloud': patch
'@backstage/plugin-catalog-backend-module-backstage-openapi': patch
'@backstage/plugin-catalog-backend-module-bitbucket-server': patch
'@backstage/plugin-scaffolder-backend-module-notifications': patch
'@backstage/plugin-auth-backend-module-atlassian-provider': patch
'@backstage/plugin-auth-backend-module-bitbucket-provider': patch
'@backstage/plugin-auth-backend-module-microsoft-provider': patch
'@backstage/plugin-catalog-backend-module-bitbucket-cloud': patch
'@backstage/plugin-scaffolder-backend-module-cookiecutter': patch
'@backstage/plugin-auth-backend-module-onelogin-provider': patch
'@backstage/plugin-auth-backend-module-pinniped-provider': patch
'@backstage/plugin-events-backend-module-bitbucket-cloud': patch
'@backstage/plugin-auth-backend-module-aws-alb-provider': patch
'@backstage/plugin-auth-backend-module-gcp-iap-provider': patch
'@backstage/plugin-auth-backend-module-github-provider': patch
'@backstage/plugin-auth-backend-module-gitlab-provider': patch
'@backstage/plugin-auth-backend-module-google-provider': patch
'@backstage/plugin-auth-backend-module-oauth2-provider': patch
'@backstage/plugin-catalog-unprocessed-entities-common': patch
'@backstage/plugin-scaffolder-backend-module-bitbucket': patch
'@backstage/plugin-search-backend-module-elasticsearch': patch
'@backstage/plugin-auth-backend-module-guest-provider': patch
'@backstage/plugin-catalog-backend-module-unprocessed': patch
'@backstage/plugin-notifications-backend-module-email': patch
'@backstage/plugin-auth-backend-module-oidc-provider': patch
'@backstage/plugin-auth-backend-module-okta-provider': patch
'@backstage/plugin-catalog-backend-module-github-org': patch
'@backstage/plugin-catalog-backend-module-gitlab-org': patch
'@backstage/plugin-scaffolder-backend-module-gerrit': patch
'@backstage/plugin-scaffolder-backend-module-github': patch
'@backstage/plugin-scaffolder-backend-module-gitlab': patch
'@backstage/plugin-scaffolder-backend-module-sentry': patch
'@backstage/plugin-scaffolder-backend-module-yeoman': patch
'@backstage/plugin-catalog-backend-module-puppetdb': patch
'@backstage/plugin-scaffolder-backend-module-azure': patch
'@backstage/plugin-scaffolder-backend-module-gitea': patch
'@backstage/plugin-scaffolder-backend-module-rails': patch
'@backstage/plugin-api-docs-module-protoc-gen-doc': patch
'@backstage/plugin-catalog-backend-module-msgraph': patch
'@backstage/plugin-catalog-backend-module-openapi': patch
'@backstage/plugin-search-backend-module-techdocs': patch
'@backstage/plugin-techdocs-module-addons-contrib': patch
'@backstage/plugin-catalog-backend-module-gerrit': patch
'@backstage/plugin-catalog-backend-module-github': patch
'@backstage/plugin-catalog-backend-module-gitlab': patch
'@backstage/plugin-events-backend-module-aws-sqs': patch
'@backstage/plugin-search-backend-module-catalog': patch
'@backstage/plugin-search-backend-module-explore': patch
'@backstage/plugin-catalog-backend-module-azure': patch
'@backstage/plugin-catalog-unprocessed-entities': patch
'@backstage/plugin-events-backend-module-gerrit': patch
'@backstage/plugin-events-backend-module-github': patch
'@backstage/plugin-events-backend-module-gitlab': patch
'@backstage/plugin-catalog-backend-module-ldap': patch
'@backstage/plugin-events-backend-module-azure': patch
'@backstage/plugin-catalog-backend-module-aws': patch
'@backstage/plugin-catalog-backend-module-gcp': patch
'@backstage/plugin-scaffolder-node-test-utils': patch
'@backstage/plugin-techdocs-addons-test-utils': patch
'@backstage/plugin-events-backend-test-utils': patch
'@backstage/plugin-search-backend-module-pg': patch
'@backstage/plugin-bitbucket-cloud-common': patch
'@backstage/plugin-notifications-backend': patch
'@backstage/plugin-user-settings-backend': patch
'@backstage/plugin-notifications-common': patch
'@backstage/plugin-user-settings-common': patch
'@backstage/plugin-search-backend-node': patch
'@backstage/plugin-kubernetes-backend': patch
'@backstage/plugin-kubernetes-cluster': patch
'@backstage/plugin-notifications-node': patch
'@backstage/plugin-permission-backend': patch
'@backstage/plugin-scaffolder-backend': patch
'@backstage/plugin-kubernetes-common': patch
'@backstage/plugin-permission-common': patch
'@backstage/plugin-scaffolder-common': patch
'@backstage/plugin-devtools-backend': patch
'@backstage/plugin-kubernetes-react': patch
'@backstage/plugin-permission-react': patch
'@backstage/plugin-scaffolder-react': patch
'@backstage/plugin-techdocs-backend': patch
'@backstage/plugin-catalog-backend': patch
'@backstage/plugin-devtools-common': patch
'@backstage/plugin-kubernetes-node': patch
'@backstage/plugin-permission-node': patch
'@backstage/plugin-scaffolder-node': patch
'@backstage/plugin-signals-backend': patch
'@backstage/plugin-app-visualizer': patch
'@backstage/plugin-catalog-common': patch
'@backstage/plugin-catalog-import': patch
'@backstage/plugin-events-backend': patch
'@backstage/plugin-search-backend': patch
'@backstage/plugin-techdocs-react': patch
'@backstage/plugin-catalog-graph': patch
'@backstage/plugin-catalog-react': patch
'@backstage/plugin-config-schema': patch
'@backstage/plugin-notifications': patch
'@backstage/plugin-proxy-backend': patch
'@backstage/plugin-search-common': patch
'@backstage/plugin-signals-react': patch
'@backstage/plugin-techdocs-node': patch
'@backstage/plugin-user-settings': patch
'@backstage/plugin-auth-backend': patch
'@backstage/plugin-catalog-node': patch
'@backstage/plugin-search-react': patch
'@backstage/plugin-signals-node': patch
'@backstage/plugin-app-backend': patch
'@backstage/plugin-events-node': patch
'@backstage/plugin-auth-react': patch
'@backstage/plugin-home-react': patch
'@backstage/plugin-kubernetes': patch
'@backstage/plugin-scaffolder': patch
'@backstage/plugin-auth-node': patch
'@backstage/plugin-org-react': patch
'@backstage/plugin-api-docs': patch
'@backstage/plugin-app-node': patch
'@backstage/plugin-devtools': patch
'@backstage/plugin-techdocs': patch
'@backstage/plugin-catalog': patch
'@backstage/plugin-signals': patch
'@backstage/plugin-search': patch
'@backstage/plugin-home': patch
'@backstage/plugin-org': patch
---
Added additional plugin metadata to `package.json`.
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/plugin-auth-backend-module-microsoft-provider': patch
---
Minor internal type updates
+8
View File
@@ -0,0 +1,8 @@
---
'@backstage/backend-defaults': minor
---
**BREAKING**: The `workdir` argument have been removed from The `GerritUrlReader` constructor.
**BREAKING**: The Gerrit `readTree` implementation will now only use the Gitiles api. Support
for using git to clone the repo has been removed.
+41 -1
View File
@@ -181,16 +181,23 @@
"@backstage/plugin-techdocs-node": "1.12.4",
"@backstage/plugin-techdocs-react": "1.2.4",
"@backstage/plugin-user-settings": "0.8.6",
"@backstage/plugin-user-settings-backend": "0.2.17"
"@backstage/plugin-user-settings-backend": "0.2.17",
"yarn-plugin-backstage": "0.0.0",
"@backstage/plugin-auth-backend-module-onelogin-provider": "0.0.0",
"@backstage/plugin-user-settings-common": "0.0.0"
},
"changesets": [
"beige-eagles-cheat",
"blue-hairs-marry",
"brave-apples-move",
"breezy-badgers-train",
"breezy-planets-sparkle",
"brown-bananas-talk",
"calm-cars-serve",
"calm-files-sort",
"calm-plums-wink",
"chilled-planes-sniff",
"clever-kids-return",
"clever-radios-yawn",
"cold-seas-end",
"create-app-1716302437",
@@ -207,12 +214,16 @@
"empty-tables-ring",
"famous-monkeys-count",
"forty-adults-roll",
"forty-experts-live",
"four-adults-mix",
"friendly-keys-fold",
"gentle-baboons-peel",
"gentle-llamas-cross",
"gold-teachers-wink",
"great-clouds-hang",
"great-cougars-guess",
"green-apricots-invite",
"honest-badgers-ring",
"honest-pandas-chew",
"itchy-spoons-cry",
"large-months-decide",
@@ -220,6 +231,17 @@
"late-students-live",
"light-rice-argue",
"little-cooks-approve",
"long-llamas-push-atlassian",
"long-llamas-push-bitbucket",
"long-llamas-push-github",
"long-llamas-push-gitlab",
"long-llamas-push-google",
"long-llamas-push-microsoft",
"long-llamas-push-oauth2",
"long-llamas-push-oidc",
"long-llamas-push-okta",
"long-llamas-push-pinniped",
"long-llamas-push-vmware-cloud",
"loud-pumpkins-bow",
"lovely-hats-pay",
"lucky-taxis-rule",
@@ -227,9 +249,13 @@
"many-windows-attack",
"mean-laws-lay",
"moody-buttons-hope",
"nasty-roses-flash",
"neat-rivers-share",
"nervous-kings-change",
"nervous-queens-fly",
"new-masks-occur",
"new-numbers-hug",
"nice-kangaroos-occur",
"nice-pants-shave",
"nine-hairs-kick",
"nine-ties-type",
@@ -239,37 +265,51 @@
"orange-pianos-eat",
"perfect-bikes-invite",
"polite-otters-talk",
"popular-boxes-press",
"popular-carrots-love",
"pretty-berries-live",
"pretty-spoons-knock",
"proud-readers-move",
"purple-mugs-beg",
"rare-frogs-beam",
"real-ghosts-return",
"rich-teachers-agree",
"rude-kings-press",
"rude-snakes-clap",
"selfish-pugs-lick",
"serious-yaks-sit",
"seven-geese-raise",
"shaggy-jokes-promise",
"shaggy-mugs-kiss",
"shaggy-zebras-mate",
"six-llamas-give",
"slimy-fans-raise",
"slow-dolls-type",
"smooth-gifts-nail",
"soft-flies-live",
"sour-colts-juggle",
"spicy-brooms-hang",
"spicy-camels-happen",
"spicy-ears-raise",
"spotty-plants-switch",
"spotty-ravens-perform",
"strong-moose-work",
"stupid-tigers-bake",
"swift-islands-leave",
"tall-bananas-reflect",
"tall-lies-fetch",
"tall-pumas-teach",
"tasty-horses-breathe",
"tender-seas-listen",
"thirty-plums-shout",
"tiny-pandas-return",
"twelve-pumpkins-fold",
"twenty-masks-dance",
"warm-bees-hope",
"warm-mayflies-yell",
"weak-gifts-occur",
"wet-crabs-guess",
"wild-coats-doubt",
"wild-doors-cheat",
"wild-ears-walk",
"wise-beers-doubt",
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/create-app': patch
---
Fixed a broken link to the node-postgres documentation
+6
View File
@@ -0,0 +1,6 @@
---
'@backstage/backend-defaults': patch
'@backstage/backend-common': patch
---
Moved over all URL reader functionality from `@backstage/backend-common` to `@backstage/backend-defaults/urlReader`. Please update your imports.
+7
View File
@@ -0,0 +1,7 @@
---
'@backstage/integration-react': patch
'@backstage/backend-common': patch
'@backstage/integration': patch
---
Fix AWS CodeCommit integration by allowing to change the host
+5
View File
@@ -0,0 +1,5 @@
---
'@backstage/cli': patch
---
Added a new `--publish` flag to the `repo fix` command. This command will validate and if possible generate the metadata required for publishing packages with the Backstage CLI. In addition, a check has been added that the `backstage.pluginId` and `backstage.pluginPackage(s)` fields are present when packing a package for publishing.
+7
View File
@@ -0,0 +1,7 @@
---
'@backstage/integration': minor
---
**BREAKING**: `gitilesBaseUrl` is now mandatory for the Gerrit integration. The
ability to override this requirement using the `DISABLE_GERRIT_GITILES_REQUIREMENT`
environment variable has been removed.
@@ -90,7 +90,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@b4ffde65f46336ab88eb53be808477a3936bae11 # v4
uses: actions/checkout@a5ac7e51b41094c92402da3b24376905380afc29 # v4
# Identify comment to be updated
- name: Find comment for API Changes
+1 -1
View File
@@ -33,7 +33,7 @@ jobs:
registry-url: https://registry.npmjs.org/
- name: yarn install
uses: backstage/actions/yarn-install@a674369920067381b450d398b27df7039b7ef635 # v0.6.5
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: linux-v18
@@ -34,7 +34,7 @@ jobs:
ref: 'refs/pull/${{ github.event.pull_request.number }}/merge'
- name: fetch base
run: git fetch --depth 1 origin ${{ github.base_ref }}
- uses: backstage/actions/changeset-feedback@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
- uses: backstage/actions/changeset-feedback@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
name: Generate feedback
with:
diff-ref: 'origin/master'
+3 -3
View File
@@ -41,7 +41,7 @@ jobs:
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
@@ -77,7 +77,7 @@ jobs:
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
@@ -222,7 +222,7 @@ jobs:
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+1 -1
View File
@@ -13,7 +13,7 @@ jobs:
with:
egress-policy: audit
- uses: backstage/actions/cron@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
- uses: backstage/actions/cron@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
app-id: ${{ secrets.BACKSTAGE_GOALIE_APPLICATION_ID }}
private-key: ${{ secrets.BACKSTAGE_GOALIE_PRIVATE_KEY }}
+1 -1
View File
@@ -37,7 +37,7 @@ jobs:
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+1 -1
View File
@@ -27,7 +27,7 @@ jobs:
node-version: 18.x
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v18.x
+2 -2
View File
@@ -82,7 +82,7 @@ jobs:
node-version: ${{ matrix.node-version }}
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
@@ -166,7 +166,7 @@ jobs:
node-version: ${{ matrix.node-version }}
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+1 -1
View File
@@ -40,7 +40,7 @@ jobs:
const prNumber = artifact.name.slice('pr_number-'.length)
core.setOutput('pr-number', prNumber);
- uses: backstage/actions/re-review@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
- uses: backstage/actions/re-review@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
app-id: ${{ secrets.BACKSTAGE_GOALIE_APPLICATION_ID }}
private-key: ${{ secrets.BACKSTAGE_GOALIE_PRIVATE_KEY }}
+1 -1
View File
@@ -23,7 +23,7 @@ jobs:
egress-policy: audit
- name: PR sync
uses: backstage/actions/pr-sync@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/pr-sync@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
github-token: ${{ secrets.GH_SERVICE_ACCOUNT_TOKEN }}
app-id: ${{ secrets.BACKSTAGE_GOALIE_APPLICATION_ID }}
+1 -1
View File
@@ -67,6 +67,6 @@ jobs:
# Upload the results to GitHub's code scanning dashboard.
- name: 'Upload to code-scanning'
uses: github/codeql-action/upload-sarif@d39d31e687223d841ef683f52467bd88e9b21c14 # v3.25.3
uses: github/codeql-action/upload-sarif@2e230e8fe0ad3a14a340ad0815ddb96d599d2aff # v3.25.8
with:
sarif_file: results.sarif
+1 -1
View File
@@ -25,7 +25,7 @@ jobs:
node-version: ${{ matrix.node-version }}
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
@@ -24,7 +24,7 @@ jobs:
node-version: 18.x
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v18.x
+1 -1
View File
@@ -58,6 +58,6 @@ jobs:
SNYK_TOKEN: ${{ secrets.SNYK_TOKEN }}
NODE_OPTIONS: --max-old-space-size=7168
- name: Upload Snyk report
uses: github/codeql-action/upload-sarif@d39d31e687223d841ef683f52467bd88e9b21c14 # v3.25.3
uses: github/codeql-action/upload-sarif@2e230e8fe0ad3a14a340ad0815ddb96d599d2aff # v3.25.8
with:
sarif_file: snyk.sarif
+1 -1
View File
@@ -30,7 +30,7 @@ jobs:
with:
node-version: 18.x
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v18.x
- name: run Lighthouse CI
+3 -3
View File
@@ -55,7 +55,7 @@ jobs:
# Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL
uses: github/codeql-action/init@d39d31e687223d841ef683f52467bd88e9b21c14 # v3.25.3
uses: github/codeql-action/init@2e230e8fe0ad3a14a340ad0815ddb96d599d2aff # v3.25.8
with:
languages: ${{ matrix.language }}
# If you wish to specify custom queries, you can do so here or in a config file.
@@ -66,7 +66,7 @@ jobs:
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
# If this step fails, then you should remove it and run the build manually (see below)
- name: Autobuild
uses: github/codeql-action/autobuild@d39d31e687223d841ef683f52467bd88e9b21c14 # v3.25.3
uses: github/codeql-action/autobuild@2e230e8fe0ad3a14a340ad0815ddb96d599d2aff # v3.25.8
# ️ Command-line programs to run using the OS shell.
# 📚 https://git.io/JvXDl
@@ -80,4 +80,4 @@ jobs:
# make release
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@d39d31e687223d841ef683f52467bd88e9b21c14 # v3.25.3
uses: github/codeql-action/analyze@2e230e8fe0ad3a14a340ad0815ddb96d599d2aff # v3.25.8
+1 -1
View File
@@ -35,7 +35,7 @@ jobs:
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+1 -1
View File
@@ -58,7 +58,7 @@ jobs:
node-version: ${{ matrix.node-version }}
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+1 -1
View File
@@ -78,7 +78,7 @@ jobs:
uses: browser-actions/setup-chrome@803ef6dfb4fdf22089c9563225d95e4a515820a0 # latest
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
+2 -2
View File
@@ -42,7 +42,7 @@ jobs:
node-version: ${{ matrix.node-version }}
registry-url: https://registry.npmjs.org/ # Needed for auth
- name: yarn install
uses: backstage/actions/yarn-install@af61233abb88019335b07ab855873d991f43d25a # v0.6.7
uses: backstage/actions/yarn-install@772cef06641090d0095188e15c85647acdf0c250 # v0.6.11
with:
cache-prefix: ${{ runner.os }}-v${{ matrix.node-version }}
- name: storybook yarn install
@@ -51,7 +51,7 @@ jobs:
- run: yarn build-storybook
- uses: chromaui/action@3dcb6636a4f8eed347ef6214f5d74d2b5fee45e4 # v11
- uses: chromaui/action@fa68b990eaee8aa67857557651a1953a8eb6d70b # v11
with:
token: ${{ secrets.GITHUB_TOKEN }}
# projectToken intentionally shared to allow collaborators to run Chromatic on forks
+2 -3
View File
@@ -114,10 +114,9 @@ Scope: Tooling and Community Repo Maintainers for the Backstage [Community Plugi
| Name | Organization | GitHub | Discord |
| -------------------- | ------------ | ------------------------------------------- | ------------ |
| Bethany Griggs | Red Hat | [BethGriggs](https://github.com/BethGriggs) | `bethgriggs` |
| Tomas Kral | Red Hat | [kadel](https://github.com/kadel) | `tomkral` |
| André Wanlin | Spotify | [awanlin](https://github.com/awanlin) | `ahhhndre` |
| Philipp Hugenroth | Spotify | [tudi2d](https://github.com/tudi2d) | `tudi2d` |
| Bethany Griggs | Red Hat | [BethGriggs](https://github.com/BethGriggs) | `bethgriggs` |
| Nick Boldt | Red Hat | [nickboldt](https://github.com/nickboldt) | `nboldt` |
| Vincenzo Scamporlino | Spotify | [vinzscam](https://github.com/vinzscam) | `vinzscam` |
### Events
+3 -1
View File
@@ -1,6 +1,6 @@
---
title: Plugin Metadata
status: provisional
status: implementable
authors:
- '@Rugvip'
owners:
@@ -155,6 +155,8 @@ The following resources have been used to inform this proposal:
The new metadata fields and any generation and validation of fields will initially be rolled out as part of the `repo fix` command in the Backstage CLI. In addition we will also add validation to the `yarn prepack` command in such a way that it does not interfere with backend package bundling, but does apply when packing packages for publishing. These changes will all be rolled out in a single release of the Backstage CLI, meaning that anyone publishing Backstage packages using the Backstage CLI will be required to provide the new metadata.
We will roll out these changes early on but be prepared to change the metadata structure if needed. Initially there will be very few consumers of this information, and it will be up to these consumers to handle the potentially varying versions of this metadata. We will aim to reach a stable state for the metadata as soon as possible, but we believe we need real world usage and feedback to get there.
## Dependencies
None
+1 -1
View File
@@ -123,7 +123,7 @@ backend:
# all interfaces, the most permissive setting. The right value depends on your specific deployment.
listen: ':7007'
# config options: https://node-postgres.com/api/client
# config options: https://node-postgres.com/apis/client
database:
client: pg
pluginDivisionMode: 'schema'
+48 -4
View File
@@ -20,7 +20,34 @@ To use this integration, add configuration to your `app-config.yaml`:
```yaml
integrations:
awsCodeCommit:
- accessKeyId: ${AWS_ACCESS_KEY_ID}
- region: eu-west-1
```
This most basic example can only be used if you are running Backstage on an instance that has an IAM identity with the following policies:
```
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"codecommit:GetFile",
"codecommit:GetFolder"
],
"Resource": "*",
"Effect": "Allow"
}
]
}
```
If you are running Backstage outside AWS and want to use Access key authentication, you can use the following configuration:
```yaml
integrations:
awsCodeCommit:
- region: eu-west-1
accessKeyId: ${AWS_ACCESS_KEY_ID}
secretAccessKey: ${AWS_SECRET_ACCESS_KEY}
```
@@ -34,10 +61,27 @@ instruct the AWS CodeCommit reader to assume a role before accessing CodeCommit:
```yaml
integrations:
awsCodeCommit:
- accessKeyId: ${AWS_ACCESS_KEY_ID}
secretAccessKey: ${AWS_SECRET_ACCESS_KEY}
- region: eu-west-1
roleArn: 'arn:aws:iam::xxxxxxxxxxxx:role/example-role'
externalId: 'some-id' # optional
```
When no entries are added, the AWS CodeCommit reader will add a default entry that uses the [standard credentials provider chain](https://docs.aws.amazon.com/AWSJavaSDK/latest/javadoc/com/amazonaws/auth/DefaultAWSCredentialsProviderChain.html).
Each entry is a structure with the following **required** elements:
- `region`: The AWS region to connect to, to communicate with the CodeCommit services
The configuration can also provide a `host` property like the other integrations. If it is not provided, it will be determined from the provided region.
i.e. When you provide `eu-west-1` as the region, Backstage will use the host `eu-west-1.console.aws.amazon.com` to check whether a provided url matches the integration.
## Register an entity on AWS CodeCommit
To register an entity that is stored in an AWS CodeCommit repository, you need to fetch the URL from the AWS Console:
- Navigate to the Code Commit service in the AWS Console ([https://console.aws.amazon.com/codecommit/home](https://console.aws.amazon.com/codecommit/home))
- _Optional: Make sure you select the correct region if you don't use the default one (us-east-1)_
- Select the repository where the entity file is stored
- Inside the repository navigate to the backstage entity file (`catalog-info.yaml`) and open the file
- Now you can copy-paste the URL from your browser inside Backstage
The format would be something like:
`https://{region}.console.aws.amazon.com/codesuite/codecommit/repositories/{reponame}/browse/refs/heads/{branch}/--/catalog-info.yaml`
+2 -6
View File
@@ -19,9 +19,9 @@ To use this integration, add at least one Gerrit configuration to your root `app
integrations:
gerrit:
- host: gerrit.company.com
gitilesBaseUrl: https://gerrit.company.com/gitiles
baseUrl: https://gerrit.company.com/gerrit
cloneUrl: https://gerrit.company.com/clone
gitilesBaseUrl: https://gerrit.company.com/gitiles
username: ${GERRIT_USERNAME}
password: ${GERRIT_PASSWORD}
```
@@ -31,16 +31,12 @@ you can list the Gerrit instances you want to fetch data from. Each entry is
a structure with up to six elements:
- `host`: The host of the Gerrit instance, e.g. `gerrit.company.com`.
- `gitilesBaseUrl`: The base url of the Gitiles instance.
- `baseUrl` (optional): Needed if the Gerrit instance is not reachable at
the base of the `host` option (e.g. `https://gerrit.company.com`) set the
address here. This is the address that you would open in a browser.
- `cloneUrl` (optional): The base URL for HTTP clones. Will default to `baseUrl` if
not set. The address used to clone a repo is the `cloneUrl` plus the repo name.
- `gitilesBaseUrl` (optional): This is needed for creating a valid user-friendly URL
that can be used for browsing the content of the provider. If not set a default
value will be created in the same way as the `baseUrl` option. There is no
requirement to have Gitiles for the Backstage Gerrit integration but without it
some links in the Backstage UI will be broken.
- `username` (optional): The Gerrit username to use in API requests. If
neither a username nor password are supplied, anonymous access will be used.
- `password` (optional): The password or http token for the Gerrit user.
+3 -4
View File
@@ -19,7 +19,7 @@ files before generating a documentation site.
Since, the requirement for reading files is so essential for Backstage plugins,
the
[`@backstage/backend-common`](https://github.com/backstage/backstage/tree/master/packages/backend-common)
[`coreServices.urlReader`](../reference/backend-plugin-api.coreservices.urlreader.md)
package provides a dedicated API for reading from such URL based remote
locations like GitHub, GitLab, Bitbucket, Google Cloud Storage, etc. This is
commonly referred to as "URL Reader". It takes care of making authenticated
@@ -49,9 +49,8 @@ function makeCreateEnv(config: Config) {
}
```
This instance contains all
[the default URL Reader providers](https://github.com/backstage/backstage/blob/master/packages/backend-common/src/reading/UrlReaders.ts)
in the backend-common package including GitHub, GitLab, Bitbucket, Azure, Google
This instance contains all the default URL Reader providers
in the backend-defaults package including GitHub, GitLab, Bitbucket, Azure, Google
GCS. As the need arises, more URL Readers are being written to support different
providers.
File diff suppressed because it is too large Load Diff
+11 -11
View File
@@ -3996,11 +3996,11 @@ __metadata:
linkType: hard
"braces@npm:^3.0.2, braces@npm:~3.0.2":
version: 3.0.2
resolution: "braces@npm:3.0.2"
version: 3.0.3
resolution: "braces@npm:3.0.3"
dependencies:
fill-range: ^7.0.1
checksum: e2a8e769a863f3d4ee887b5fe21f63193a891c68b612ddb4b68d82d1b5f3ff9073af066c343e9867a393fe4c2555dcb33e89b937195feb9c1613d259edfcd459
fill-range: ^7.1.1
checksum: b95aa0b3bd909f6cd1720ffcf031aeaf46154dd88b4da01f9a1d3f7ea866a79eba76a6d01cbc3c422b2ee5cdc39a4f02491058d5df0d7bf6e6a162a832df1f69
languageName: node
linkType: hard
@@ -5111,11 +5111,11 @@ __metadata:
linkType: hard
"docusaurus-pushfeedback@npm:^1.0.0":
version: 1.0.0
resolution: "docusaurus-pushfeedback@npm:1.0.0"
version: 1.0.1
resolution: "docusaurus-pushfeedback@npm:1.0.1"
peerDependencies:
"@docusaurus/core": 3.x
checksum: 5f119fac4b18198ecab7ca3892b8d19ea21c1f4147b7500de0f2a341651630ff090e38ac4984e33d87729f1b00d621ae8945efe2a2ea37b9a74b76c7f468f21e
checksum: 45319080911438f828d9b550481511065de225b03511347324f9ecba133ce2693fa19fd394cd0a0e43b1723e15c2c988a11838a5cab1e3702295123be4b875a8
languageName: node
linkType: hard
@@ -5710,12 +5710,12 @@ __metadata:
languageName: node
linkType: hard
"fill-range@npm:^7.0.1":
version: 7.0.1
resolution: "fill-range@npm:7.0.1"
"fill-range@npm:^7.1.1":
version: 7.1.1
resolution: "fill-range@npm:7.1.1"
dependencies:
to-regex-range: ^5.0.1
checksum: cc283f4e65b504259e64fd969bcf4def4eb08d85565e906b7d36516e87819db52029a76b6363d0f02d0d532f0033c9603b9e2d943d56ee3b0d4f7ad3328ff917
checksum: b4abfbca3839a3d55e4ae5ec62e131e2e356bf4859ce8480c64c4876100f4df292a63e5bb1618e1d7460282ca2b305653064f01654474aa35c68000980f17798
languageName: node
linkType: hard
+3 -3
View File
@@ -1,6 +1,6 @@
{
"name": "root",
"version": "1.28.0-next.2",
"version": "1.28.0-next.3",
"private": true,
"repository": {
"type": "git",
@@ -17,7 +17,7 @@
"build:all": "backstage-cli repo build --all",
"build:api-docs": "LANG=en_EN yarn build:api-reports --docs --exclude 'plugins/@(adr|adr-backend|adr-common|airbrake|airbrake-backend|allure|analytics-module-ga|analytics-module-ga4|analytics-module-newrelic-browser|apache-airflow|api-docs|api-docs-module-protoc-gen-doc|apollo-explorer|app-visualizer|azure-devops|azure-devops-backend|azure-devops-common|azure-sites|azure-sites-backend|azure-sites-common|badges|badges-backend|bazaar|bazaar-backend|bitbucket-cloud-common|bitrise|catalog-graph|catalog-graphql|catalog-import|catalog-unprocessed-entities|cicd-statistics|cicd-statistics-module-gitlab|circleci|cloudbuild|code-climate|code-coverage|code-coverage-backend|codescene|config-schema|cost-insights|cost-insights-common|dynatrace|entity-feedback|entity-feedback-backend|entity-feedback-common|entity-validation|example-todo-list|example-todo-list-backend|example-todo-list-common|firehydrant|fossa|gcalendar|gcp-projects|git-release-manager|github-actions|github-deployments|github-issues|github-pull-requests-board|gitops-profiles|gocd|graphiql|graphql-backend|graphql-voyager|ilert|jenkins|jenkins-backend|jenkins-common|kafka|kafka-backend|lighthouse|lighthouse-backend|lighthouse-common|linguist|linguist-backend|linguist-common|microsoft-calendar|newrelic|newrelic-dashboard|nomad|nomad-backend|octopus-deploy|opencost|pagerduty|periskop|periskop-backend|playlist|playlist-backend|playlist-common|proxy-backend|puppetdb|rollbar|rollbar-backend|sentry|shortcuts|splunk-on-call|stack-overflow|stack-overflow-backend|stackstorm|tech-radar|tech-radar-2|todo|todo-backend|xcmetrics)'",
"build:api-reports": "yarn build:api-reports:only --tsc",
"build:api-reports:only": "NODE_OPTIONS=--max-old-space-size=8192 backstage-repo-tools api-reports --allow-warnings 'packages/core-components,plugins/+(catalog|catalog-import|git-release-manager|jenkins|kubernetes)' -o ae-wrong-input-file-type --validate-release-tags",
"build:api-reports:only": "NODE_OPTIONS=--max-old-space-size=8192 backstage-repo-tools api-reports --allow-warnings 'packages/backend-common,packages/core-components,plugins/+(catalog|catalog-import|git-release-manager|jenkins|kubernetes)' -o ae-wrong-input-file-type --validate-release-tags",
"build:backend": "yarn workspace example-backend build",
"build:knip-reports": "backstage-repo-tools knip-reports",
"build:plugins-report": "node ./scripts/build-plugins-report",
@@ -26,7 +26,7 @@
"dev": "yarn workspaces foreach -A --include example-backend --include example-app --parallel -v -i run start",
"dev:next": "yarn workspaces foreach -A --include example-backend --include example-app-next --parallel -v -i run start",
"docker-build": "yarn tsc && yarn workspace example-backend build && yarn workspace example-backend build-image",
"fix": "backstage-cli repo fix",
"fix": "backstage-cli repo fix --publish",
"postinstall": "husky || true",
"lint": "backstage-cli repo lint --since origin/master",
"lint:all": "backstage-cli repo lint",
+11
View File
@@ -1,5 +1,16 @@
# @backstage/app-defaults
## 1.5.6-next.2
### Patch Changes
- Updated dependencies
- @backstage/core-components@0.14.8-next.2
- @backstage/plugin-permission-react@0.4.23-next.1
- @backstage/core-app-api@1.12.6-next.0
- @backstage/core-plugin-api@1.9.3-next.0
- @backstage/theme@0.5.6-next.0
## 1.5.6-next.1
### Patch Changes
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@backstage/app-defaults",
"version": "1.5.6-next.1",
"version": "1.5.6-next.2",
"description": "Provides the default wiring of a Backstage App",
"backstage": {
"role": "web-library"
@@ -1,5 +1,13 @@
# app-next-example-plugin
## 0.0.12-next.2
### Patch Changes
- Updated dependencies
- @backstage/core-components@0.14.8-next.2
- @backstage/frontend-plugin-api@0.6.6-next.2
## 0.0.12-next.1
### Patch Changes
@@ -1,9 +1,13 @@
{
"name": "app-next-example-plugin",
"version": "0.0.12-next.1",
"version": "0.0.12-next.2",
"description": "Backstage internal example plugin",
"backstage": {
"role": "frontend-plugin"
"role": "frontend-plugin",
"pluginId": "example",
"pluginPackages": [
"app-next-example-plugin"
]
},
"publishConfig": {
"access": "public",
+43
View File
@@ -1,5 +1,48 @@
# example-app-next
## 0.0.12-next.3
### Patch Changes
- Updated dependencies
- @backstage/plugin-catalog-graph@0.4.6-next.2
- @backstage/core-components@0.14.8-next.2
- @backstage/plugin-techdocs-module-addons-contrib@1.1.11-next.2
- @backstage/plugin-catalog-unprocessed-entities@0.2.5-next.2
- @backstage/plugin-kubernetes-cluster@0.0.12-next.3
- @backstage/plugin-permission-react@0.4.23-next.1
- @backstage/plugin-scaffolder-react@1.8.7-next.3
- @backstage/plugin-app-visualizer@0.1.7-next.2
- @backstage/plugin-catalog-common@1.0.24-next.0
- @backstage/plugin-catalog-import@0.12.0-next.3
- @backstage/plugin-techdocs-react@1.2.5-next.2
- @backstage/plugin-catalog-react@1.12.1-next.2
- @backstage/plugin-notifications@0.2.2-next.3
- @backstage/plugin-search-common@1.2.12-next.0
- @backstage/plugin-user-settings@0.8.7-next.2
- @backstage/plugin-search-react@1.7.12-next.2
- @backstage/plugin-auth-react@0.1.3-next.2
- @backstage/plugin-kubernetes@0.11.11-next.3
- @backstage/plugin-scaffolder@1.21.0-next.3
- @backstage/plugin-api-docs@0.11.6-next.2
- @backstage/plugin-techdocs@1.10.6-next.2
- @backstage/plugin-catalog@1.21.0-next.3
- @backstage/plugin-signals@0.0.7-next.2
- @backstage/plugin-search@1.4.12-next.3
- @backstage/plugin-home@0.7.5-next.2
- @backstage/plugin-org@0.6.26-next.2
- @backstage/integration-react@1.1.28-next.1
- @backstage/cli@0.26.7-next.3
- @backstage/app-defaults@1.5.6-next.2
- @backstage/frontend-app-api@0.7.1-next.2
- @backstage/frontend-plugin-api@0.6.6-next.2
- @backstage/core-compat-api@0.2.6-next.2
- @backstage/catalog-model@1.5.0
- @backstage/config@1.2.0
- @backstage/core-app-api@1.12.6-next.0
- @backstage/core-plugin-api@1.9.3-next.0
- @backstage/theme@0.5.6-next.0
## 0.0.12-next.2
### Patch Changes
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "example-app-next",
"version": "0.0.12-next.2",
"version": "0.0.12-next.3",
"private": true,
"repository": {
"type": "git",
+41
View File
@@ -1,5 +1,46 @@
# example-app
## 0.2.98-next.3
### Patch Changes
- Updated dependencies
- @backstage/plugin-catalog-graph@0.4.6-next.2
- @backstage/core-components@0.14.8-next.2
- @backstage/plugin-techdocs-module-addons-contrib@1.1.11-next.2
- @backstage/plugin-catalog-unprocessed-entities@0.2.5-next.2
- @backstage/plugin-kubernetes-cluster@0.0.12-next.3
- @backstage/plugin-permission-react@0.4.23-next.1
- @backstage/plugin-scaffolder-react@1.8.7-next.3
- @backstage/plugin-catalog-common@1.0.24-next.0
- @backstage/plugin-catalog-import@0.12.0-next.3
- @backstage/plugin-techdocs-react@1.2.5-next.2
- @backstage/plugin-catalog-react@1.12.1-next.2
- @backstage/plugin-notifications@0.2.2-next.3
- @backstage/plugin-search-common@1.2.12-next.0
- @backstage/plugin-user-settings@0.8.7-next.2
- @backstage/plugin-search-react@1.7.12-next.2
- @backstage/plugin-auth-react@0.1.3-next.2
- @backstage/plugin-kubernetes@0.11.11-next.3
- @backstage/plugin-scaffolder@1.21.0-next.3
- @backstage/plugin-api-docs@0.11.6-next.2
- @backstage/plugin-devtools@0.1.15-next.2
- @backstage/plugin-techdocs@1.10.6-next.2
- @backstage/plugin-catalog@1.21.0-next.3
- @backstage/plugin-signals@0.0.7-next.2
- @backstage/plugin-search@1.4.12-next.3
- @backstage/plugin-home@0.7.5-next.2
- @backstage/plugin-org@0.6.26-next.2
- @backstage/integration-react@1.1.28-next.1
- @backstage/cli@0.26.7-next.3
- @backstage/app-defaults@1.5.6-next.2
- @backstage/frontend-app-api@0.7.1-next.2
- @backstage/catalog-model@1.5.0
- @backstage/config@1.2.0
- @backstage/core-app-api@1.12.6-next.0
- @backstage/core-plugin-api@1.9.3-next.0
- @backstage/theme@0.5.6-next.0
## 0.2.98-next.2
### Patch Changes
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "example-app",
"version": "0.2.98-next.2",
"version": "0.2.98-next.3",
"backstage": {
"role": "frontend"
},
+17
View File
@@ -1,5 +1,22 @@
# @backstage/backend-app-api
## 0.7.6-next.3
### Patch Changes
- Updated dependencies
- @backstage/cli-node@0.2.6-next.2
- @backstage/backend-plugin-api@0.6.19-next.3
- @backstage/plugin-auth-node@0.4.14-next.3
- @backstage/plugin-permission-node@0.7.30-next.3
- @backstage/cli-common@0.1.14-next.0
- @backstage/backend-tasks@0.5.24-next.3
- @backstage/backend-common@0.23.0-next.3
- @backstage/config-loader@1.8.1-next.0
- @backstage/config@1.2.0
- @backstage/errors@1.2.4
- @backstage/types@1.1.1
## 0.7.6-next.2
### Patch Changes
+5 -2
View File
@@ -42,7 +42,7 @@ import { ServiceFactory } from '@backstage/backend-plugin-api';
import { ServiceFactoryOrFunction } from '@backstage/backend-plugin-api';
import { TokenManagerService } from '@backstage/backend-plugin-api';
import { transport } from 'winston';
import { UrlReader } from '@backstage/backend-common';
import { UrlReaderService } from '@backstage/backend-plugin-api';
import { UserInfoService } from '@backstage/backend-plugin-api';
// @public (undocumented)
@@ -339,7 +339,10 @@ export const tokenManagerServiceFactory: () => ServiceFactory<
>;
// @public @deprecated (undocumented)
export const urlReaderServiceFactory: () => ServiceFactory<UrlReader, 'plugin'>;
export const urlReaderServiceFactory: () => ServiceFactory<
UrlReaderService,
'plugin'
>;
// @public (undocumented)
export const userInfoServiceFactory: () => ServiceFactory<
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@backstage/backend-app-api",
"version": "0.7.6-next.2",
"version": "0.7.6-next.3",
"description": "Core API used by Backstage backend apps",
"backstage": {
"role": "node-library"
+19
View File
@@ -1,5 +1,24 @@
# @backstage/backend-common
## 0.23.0-next.3
### Patch Changes
- b2ee7f3: Moved over all URL reader functionality from `@backstage/backend-common` to `@backstage/backend-defaults/urlReader`. Please update your imports.
- 23ee9ab: Fix AWS CodeCommit integration by allowing to change the host
- Updated dependencies
- @backstage/backend-plugin-api@0.6.19-next.3
- @backstage/plugin-auth-node@0.4.14-next.3
- @backstage/integration@1.12.0-next.1
- @backstage/cli-common@0.1.14-next.0
- @backstage/backend-app-api@0.7.6-next.3
- @backstage/config-loader@1.8.1-next.0
- @backstage/backend-dev-utils@0.1.4
- @backstage/config@1.2.0
- @backstage/errors@1.2.4
- @backstage/integration-aws-node@0.1.12
- @backstage/types@1.1.1
## 0.23.0-next.2
### Minor Changes
+118 -323
View File
@@ -49,26 +49,32 @@ import { PluginMetadataService } from '@backstage/backend-plugin-api';
import { PushResult } from 'isomorphic-git';
import { Readable } from 'stream';
import { ReadCommitResult } from 'isomorphic-git';
import { ReadTreeOptions } from '@backstage/backend-plugin-api';
import { ReadTreeResponse } from '@backstage/backend-plugin-api';
import { ReadTreeResponseDirOptions } from '@backstage/backend-plugin-api';
import { ReadTreeResponseFile } from '@backstage/backend-plugin-api';
import { ReadUrlOptions } from '@backstage/backend-plugin-api';
import { ReadUrlResponse } from '@backstage/backend-plugin-api';
import type { ReadTreeOptions as ReadTreeOptions_2 } from '@backstage/backend-plugin-api';
import type { ReadTreeResponse as ReadTreeResponse_2 } from '@backstage/backend-plugin-api';
import type { ReadTreeResponseDirOptions as ReadTreeResponseDirOptions_2 } from '@backstage/backend-plugin-api';
import type { ReadTreeResponseFile as ReadTreeResponseFile_2 } from '@backstage/backend-plugin-api';
import type { ReadUrlOptions as ReadUrlOptions_2 } from '@backstage/backend-plugin-api';
import type { ReadUrlResponse as ReadUrlResponse_2 } from '@backstage/backend-plugin-api';
import { RequestHandler } from 'express';
import { resolvePackagePath as resolvePackagePath_2 } from '@backstage/backend-plugin-api';
import { resolveSafeChildPath as resolveSafeChildPath_2 } from '@backstage/backend-plugin-api';
import { RootConfigService } from '@backstage/backend-plugin-api';
import { Router } from 'express';
import { SchedulerService } from '@backstage/backend-plugin-api';
import { SearchOptions } from '@backstage/backend-plugin-api';
import { SearchResponse } from '@backstage/backend-plugin-api';
import { SearchResponseFile } from '@backstage/backend-plugin-api';
import type { SearchOptions as SearchOptions_2 } from '@backstage/backend-plugin-api';
import type { SearchResponse as SearchResponse_2 } from '@backstage/backend-plugin-api';
import type { SearchResponseFile as SearchResponseFile_2 } from '@backstage/backend-plugin-api';
import { Server } from 'http';
import { ServiceRef } from '@backstage/backend-plugin-api';
import { TokenManagerService as TokenManager } from '@backstage/backend-plugin-api';
import { TransportStreamOptions } from 'winston-transport';
import { UrlReaderService as UrlReader } from '@backstage/backend-plugin-api';
import { UrlReaderReadTreeOptions } from '@backstage/backend-plugin-api';
import { UrlReaderReadTreeResponse } from '@backstage/backend-plugin-api';
import { UrlReaderReadUrlOptions } from '@backstage/backend-plugin-api';
import { UrlReaderReadUrlResponse } from '@backstage/backend-plugin-api';
import { UrlReaderSearchOptions } from '@backstage/backend-plugin-api';
import { UrlReaderSearchResponse } from '@backstage/backend-plugin-api';
import { UrlReaderService } from '@backstage/backend-plugin-api';
import { UserInfoService } from '@backstage/backend-plugin-api';
import { V1PodTemplateSpec } from '@kubernetes/client-node';
import * as winston from 'winston';
@@ -80,118 +86,30 @@ export type AuthCallbackOptions = {
logger?: LoggerService;
};
// @public
export class AwsS3UrlReader implements UrlReader {
constructor(
credsManager: AwsCredentialsManager,
integration: AwsS3Integration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "AwsS3UrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const AwsS3UrlReader: typeof AwsS3UrlReader_2;
// @public
export class AzureUrlReader implements UrlReader {
constructor(
integration: AzureIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
credentialsProvider: AzureDevOpsCredentialsProvider;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "AzureUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const AzureUrlReader: typeof AzureUrlReader_2;
// @public
export class BitbucketCloudUrlReader implements UrlReader {
constructor(
integration: BitbucketCloudIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "BitbucketCloudUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const BitbucketCloudUrlReader: typeof BitbucketCloudUrlReader_2;
// @public
export class BitbucketServerUrlReader implements UrlReader {
constructor(
integration: BitbucketServerIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "BitbucketServerUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const BitbucketServerUrlReader: typeof BitbucketServerUrlReader_2;
// @public @deprecated
export class BitbucketUrlReader implements UrlReader {
constructor(
integration: BitbucketIntegration,
logger: LoggerService,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "BitbucketUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const BitbucketUrlReader: typeof BitbucketUrlReader_2;
// @public @deprecated (undocumented)
export type CacheClient = CacheService;
@@ -330,50 +248,20 @@ export type ErrorHandlerOptions = {
logClientErrors?: boolean;
};
// @public
export class FetchUrlReader implements UrlReader {
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "FetchUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const FetchUrlReader: typeof FetchUrlReader_2;
// @public
export type FromReadableArrayOptions = Array<{
data: Readable;
path: string;
lastModifiedAt?: Date;
}>;
// Warning: (ae-forgotten-export) The symbol "FromReadableArrayOptions_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type FromReadableArrayOptions = FromReadableArrayOptions_2;
// @public
export class GerritUrlReader implements UrlReader {
constructor(
integration: GerritIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
workDir: string,
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "GerritUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const GerritUrlReader: typeof GerritUrlReader_2;
// @public @deprecated
export function getRootLogger(): winston.Logger;
@@ -457,94 +345,25 @@ export class Git {
resolveRef(options: { dir: string; ref: string }): Promise<string>;
}
// @public
export class GiteaUrlReader implements UrlReader {
constructor(
integration: GiteaIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "GiteaUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const GiteaUrlReader: typeof GiteaUrlReader_2;
// @public
export class GithubUrlReader implements UrlReader {
constructor(
integration: GithubIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
credentialsProvider: GithubCredentialsProvider;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "GithubUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const GithubUrlReader: typeof GithubUrlReader_2;
// @public
export class GitlabUrlReader implements UrlReader {
constructor(
integration: GitLabIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(url: string, options?: SearchOptions): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "GitlabUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const GitlabUrlReader: typeof GitlabUrlReader_2;
// @public
export class HarnessUrlReader implements UrlReader {
constructor(
integration: HarnessIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(url: string, options?: ReadTreeOptions): Promise<ReadTreeResponse>;
// (undocumented)
readUrl(url: string, options?: ReadUrlOptions): Promise<ReadUrlResponse>;
// (undocumented)
search(): Promise<SearchResponse>;
// (undocumented)
toString(): string;
}
// Warning: (ae-forgotten-export) The symbol "HarnessUrlReader_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const HarnessUrlReader: typeof HarnessUrlReader_2;
// @public @deprecated
export const HostDiscovery: typeof HostDiscovery_2;
@@ -596,7 +415,7 @@ export const legacyPlugin: (
permissions: PermissionsService;
scheduler: SchedulerService;
tokenManager: TokenManager;
reader: UrlReader;
reader: UrlReaderService;
identity: IdentityService;
},
{
@@ -677,73 +496,49 @@ export interface PullOptions {
};
}
// @public
export type ReaderFactory = (options: {
config: Config;
logger: LoggerService;
treeResponseFactory: ReadTreeResponseFactory;
}) => UrlReaderPredicateTuple[];
// Warning: (ae-forgotten-export) The symbol "ReaderFactory_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type ReaderFactory = ReaderFactory_2;
export { ReadTreeOptions };
// @public @deprecated (undocumented)
export type ReadTreeOptions = ReadTreeOptions_2;
export { ReadTreeResponse };
// @public @deprecated (undocumented)
export type ReadTreeResponse = ReadTreeResponse_2;
export { ReadTreeResponseDirOptions };
// @public @deprecated (undocumented)
export type ReadTreeResponseDirOptions = ReadTreeResponseDirOptions_2;
// @public
export interface ReadTreeResponseFactory {
// (undocumented)
fromReadableArray(
options: FromReadableArrayOptions,
): Promise<ReadTreeResponse>;
// (undocumented)
fromTarArchive(
options: ReadTreeResponseFactoryOptions & {
stripFirstDirectory?: boolean;
},
): Promise<ReadTreeResponse>;
// (undocumented)
fromZipArchive(
options: ReadTreeResponseFactoryOptions,
): Promise<ReadTreeResponse>;
}
// Warning: (ae-forgotten-export) The symbol "ReadTreeResponseFactory_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type ReadTreeResponseFactory = ReadTreeResponseFactory_2;
// @public
export type ReadTreeResponseFactoryOptions = {
stream: Readable;
subpath?: string;
etag: string;
filter?: (
path: string,
info?: {
size: number;
},
) => boolean;
};
// Warning: (ae-forgotten-export) The symbol "ReadTreeResponseFactoryOptions_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type ReadTreeResponseFactoryOptions = ReadTreeResponseFactoryOptions_2;
export { ReadTreeResponseFile };
// @public @deprecated (undocumented)
export type ReadTreeResponseFile = ReadTreeResponseFile_2;
export { ReadUrlOptions };
// @public @deprecated (undocumented)
export type ReadUrlOptions = ReadUrlOptions_2;
export { ReadUrlResponse };
// @public @deprecated (undocumented)
export type ReadUrlResponse = ReadUrlResponse_2;
// @public
export class ReadUrlResponseFactory {
static fromNodeJSReadable(
oldStyleStream: NodeJS.ReadableStream,
options?: ReadUrlResponseFactoryFromStreamOptions,
): Promise<ReadUrlResponse>;
static fromReadable(
stream: Readable,
options?: ReadUrlResponseFactoryFromStreamOptions,
): Promise<ReadUrlResponse>;
}
// Warning: (ae-forgotten-export) The symbol "ReadUrlResponseFactory_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const ReadUrlResponseFactory: typeof ReadUrlResponseFactory_2;
// @public
export type ReadUrlResponseFactoryFromStreamOptions = {
etag?: string;
lastModifiedAt?: Date;
};
// Warning: (ae-forgotten-export) The symbol "ReadUrlResponseFactoryFromStreamOptions_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type ReadUrlResponseFactoryFromStreamOptions =
ReadUrlResponseFactoryFromStreamOptions_2;
// @public
export function redactWinstonLogLine(
@@ -778,11 +573,14 @@ export type RunContainerOptions = {
pullOptions?: PullOptions;
};
export { SearchOptions };
// @public @deprecated (undocumented)
export type SearchOptions = SearchOptions_2;
export { SearchResponse };
// @public @deprecated (undocumented)
export type SearchResponse = SearchResponse_2;
export { SearchResponseFile };
// @public @deprecated (undocumented)
export type SearchResponseFile = SearchResponseFile_2;
// @public
export class ServerTokenManager implements TokenManager {
@@ -861,26 +659,23 @@ export interface StatusCheckHandlerOptions {
export { TokenManager };
export { UrlReader };
// @public @deprecated (undocumented)
export type UrlReader = UrlReaderService;
// @public
export type UrlReaderPredicateTuple = {
predicate: (url: URL) => boolean;
reader: UrlReader;
};
// Warning: (ae-forgotten-export) The symbol "UrlReaderPredicateTuple_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type UrlReaderPredicateTuple = UrlReaderPredicateTuple_2;
// @public
export class UrlReaders {
static create(options: UrlReadersOptions): UrlReader;
static default(options: UrlReadersOptions): UrlReader;
}
// Warning: (ae-forgotten-export) The symbol "UrlReaders_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export const UrlReaders: typeof UrlReaders_2;
// @public
export type UrlReadersOptions = {
config: Config;
logger: LoggerService;
factories?: ReaderFactory[];
};
// Warning: (ae-forgotten-export) The symbol "UrlReadersOptions_2" needs to be exported by the entry point index.d.ts
//
// @public @deprecated (undocumented)
export type UrlReadersOptions = UrlReadersOptions_2;
// @public @deprecated
export function useHotCleanup(
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@backstage/backend-common",
"version": "0.23.0-next.2",
"version": "0.23.0-next.3",
"description": "Common functionality library for Backstage backends",
"backstage": {
"role": "node-library"
+204 -32
View File
@@ -14,35 +14,207 @@
* limitations under the License.
*/
export { AzureUrlReader } from './AzureUrlReader';
export { BitbucketCloudUrlReader } from './BitbucketCloudUrlReader';
export { BitbucketUrlReader } from './BitbucketUrlReader';
export { BitbucketServerUrlReader } from './BitbucketServerUrlReader';
export { GerritUrlReader } from './GerritUrlReader';
export { GithubUrlReader } from './GithubUrlReader';
export { GitlabUrlReader } from './GitlabUrlReader';
export { GiteaUrlReader } from './GiteaUrlReader';
export { HarnessUrlReader } from './HarnessUrlReader';
export { AwsS3UrlReader } from './AwsS3UrlReader';
export { FetchUrlReader } from './FetchUrlReader';
export { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
export type {
FromReadableArrayOptions,
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadTreeResponseFile,
ReadTreeResponseDirOptions,
ReadTreeResponseFactoryOptions,
ReadUrlOptions,
ReadUrlResponse,
ReadUrlResponseFactoryFromStreamOptions,
SearchOptions,
SearchResponse,
SearchResponseFile,
UrlReader,
UrlReaderPredicateTuple,
} from './types';
export { UrlReaders } from './UrlReaders';
export type { UrlReadersOptions } from './UrlReaders';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { AzureUrlReader as _AzureUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/AzureUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { BitbucketCloudUrlReader as _BitbucketCloudUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/BitbucketCloudUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { BitbucketUrlReader as _BitbucketUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/BitbucketUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { BitbucketServerUrlReader as _BitbucketServerUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/BitbucketServerUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { GerritUrlReader as _GerritUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/GerritUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { GithubUrlReader as _GithubUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/GithubUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { GitlabUrlReader as _GitlabUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/GitlabUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { GiteaUrlReader as _GiteaUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/GiteaUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { HarnessUrlReader as _HarnessUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/HarnessUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { AwsS3UrlReader as _AwsS3UrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/AwsS3UrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { FetchUrlReader as _FetchUrlReader } from '../../../backend-defaults/src/entrypoints/urlReader/lib/FetchUrlReader';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { UrlReaders as _UrlReaders } from '../../../backend-defaults/src/entrypoints/urlReader/lib/UrlReaders';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import { ReadUrlResponseFactory as _ReadUrlResponseFactory } from '../../../backend-defaults/src/entrypoints/urlReader/lib/ReadUrlResponseFactory';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import type { UrlReadersOptions as _UrlReadersOptions } from '../../../backend-defaults/src/entrypoints/urlReader/lib/UrlReaders';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import type { FromReadableArrayOptions as _FromReadableArrayOptions } from '../../../backend-defaults/src/entrypoints/urlReader/lib/types';
// eslint-disable-next-line @backstage/no-relative-monorepo-imports
import type {
ReaderFactory as _ReaderFactory,
ReadTreeResponseFactory as _ReadTreeResponseFactory,
ReadTreeResponseFactoryOptions as _ReadTreeResponseFactoryOptions,
ReadUrlResponseFactoryFromStreamOptions as _ReadUrlResponseFactoryFromStreamOptions,
UrlReaderPredicateTuple as _UrlReaderPredicateTuple,
} from '../../../backend-defaults/src/entrypoints/urlReader/lib/types';
import type {
ReadTreeOptions as _ReadTreeOptions,
ReadTreeResponse as _ReadTreeResponse,
ReadTreeResponseFile as _ReadTreeResponseFile,
ReadTreeResponseDirOptions as _ReadTreeResponseDirOptions,
ReadUrlOptions as _ReadUrlOptions,
ReadUrlResponse as _ReadUrlResponse,
SearchOptions as _SearchOptions,
SearchResponse as _SearchResponse,
SearchResponseFile as _SearchResponseFile,
UrlReaderService as _UrlReaderService,
} from '@backstage/backend-plugin-api';
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const AzureUrlReader = _AzureUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const BitbucketCloudUrlReader = _BitbucketCloudUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const BitbucketUrlReader = _BitbucketUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const BitbucketServerUrlReader = _BitbucketServerUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const GerritUrlReader = _GerritUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const GithubUrlReader = _GithubUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const GitlabUrlReader = _GitlabUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const GiteaUrlReader = _GiteaUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const HarnessUrlReader = _HarnessUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const AwsS3UrlReader = _AwsS3UrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const FetchUrlReader = _FetchUrlReader;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const UrlReaders = _UrlReaders;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export const ReadUrlResponseFactory = _ReadUrlResponseFactory;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type UrlReadersOptions = _UrlReadersOptions;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type FromReadableArrayOptions = _FromReadableArrayOptions;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type ReaderFactory = _ReaderFactory;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type ReadTreeResponseFactory = _ReadTreeResponseFactory;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type ReadTreeResponseFactoryOptions = _ReadTreeResponseFactoryOptions;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type ReadUrlResponseFactoryFromStreamOptions =
_ReadUrlResponseFactoryFromStreamOptions;
/**
* @public
* @deprecated Import from `@backstage/backend-defaults/urlReader` instead
*/
export type UrlReaderPredicateTuple = _UrlReaderPredicateTuple;
/**
* @public
* @deprecated Use `ÙrlReaderReadTreeOptions` from `@backstage/backend-plugin-api` instead
*/
export type ReadTreeOptions = _ReadTreeOptions;
/**
* @public
* @deprecated Use `ÙrlReaderReadTreeResponse` from `@backstage/backend-plugin-api` instead
*/
export type ReadTreeResponse = _ReadTreeResponse;
/**
* @public
* @deprecated Use `ÙrlReaderReadTreeResponseFile` from `@backstage/backend-plugin-api` instead
*/
export type ReadTreeResponseFile = _ReadTreeResponseFile;
/**
* @public
* @deprecated Use `ÙrlReaderReadTreeResponseDirOptions` from `@backstage/backend-plugin-api` instead
*/
export type ReadTreeResponseDirOptions = _ReadTreeResponseDirOptions;
/**
* @public
* @deprecated Use `ÙrlReaderReadUrlOptions` from `@backstage/backend-plugin-api` instead
*/
export type ReadUrlOptions = _ReadUrlOptions;
/**
* @public
* @deprecated Use `ÙrlReaderReadUrlResponse` from `@backstage/backend-plugin-api` instead
*/
export type ReadUrlResponse = _ReadUrlResponse;
/**
* @public
* @deprecated Use `ÙrlReaderSearchOptions` from `@backstage/backend-plugin-api` instead
*/
export type SearchOptions = _SearchOptions;
/**
* @public
* @deprecated Use `ÙrlReaderSearchResponse` from `@backstage/backend-plugin-api` instead
*/
export type SearchResponse = _SearchResponse;
/**
* @public
* @deprecated Use `ÙrlReaderSearchResponseFile` from `@backstage/backend-plugin-api` instead
*/
export type SearchResponseFile = _SearchResponseFile;
/**
* @public
* @deprecated Use `ÙrlReaderService` from `@backstage/backend-plugin-api` instead
*/
export type UrlReader = _UrlReaderService;
+21
View File
@@ -1,5 +1,26 @@
# @backstage/backend-defaults
## 0.3.0-next.3
### Patch Changes
- 1897169: Exposed `DefaultSchedulerService`
- 8aab451: Internal minor refactors of the database connectors
- b2ee7f3: Moved over all URL reader functionality from `@backstage/backend-common` to `@backstage/backend-defaults/urlReader`. Please update your imports.
- Updated dependencies
- @backstage/backend-plugin-api@0.6.19-next.3
- @backstage/integration@1.12.0-next.1
- @backstage/plugin-permission-node@0.7.30-next.3
- @backstage/plugin-events-node@0.3.5-next.2
- @backstage/backend-common@0.23.0-next.3
- @backstage/backend-app-api@0.7.6-next.3
- @backstage/config-loader@1.8.1-next.0
- @backstage/backend-dev-utils@0.1.4
- @backstage/config@1.2.0
- @backstage/errors@1.2.4
- @backstage/integration-aws-node@0.1.12
- @backstage/types@1.1.1
## 0.3.0-next.2
### Patch Changes
@@ -3,11 +3,440 @@
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
```ts
/// <reference types="node" />
import { AwsCredentialsManager } from '@backstage/integration-aws-node';
import { AwsS3Integration } from '@backstage/integration';
import { AzureDevOpsCredentialsProvider } from '@backstage/integration';
import { AzureIntegration } from '@backstage/integration';
import { BitbucketCloudIntegration } from '@backstage/integration';
import { BitbucketIntegration } from '@backstage/integration';
import { BitbucketServerIntegration } from '@backstage/integration';
import { Config } from '@backstage/config';
import { GerritIntegration } from '@backstage/integration';
import { GiteaIntegration } from '@backstage/integration';
import { GithubCredentialsProvider } from '@backstage/integration';
import { GithubIntegration } from '@backstage/integration';
import { GitLabIntegration } from '@backstage/integration';
import { HarnessIntegration } from '@backstage/integration';
import { LoggerService } from '@backstage/backend-plugin-api';
import { Readable } from 'stream';
import { ServiceFactory } from '@backstage/backend-plugin-api';
import { UrlReader } from '@backstage/backend-common';
import { UrlReaderReadTreeOptions } from '@backstage/backend-plugin-api';
import { UrlReaderReadTreeResponse } from '@backstage/backend-plugin-api';
import { UrlReaderReadUrlOptions } from '@backstage/backend-plugin-api';
import { UrlReaderReadUrlResponse } from '@backstage/backend-plugin-api';
import { UrlReaderSearchOptions } from '@backstage/backend-plugin-api';
import { UrlReaderSearchResponse } from '@backstage/backend-plugin-api';
import { UrlReaderService } from '@backstage/backend-plugin-api';
// @public
export class AwsS3UrlReader implements UrlReaderService {
constructor(
credsManager: AwsCredentialsManager,
integration: AwsS3Integration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class AzureUrlReader implements UrlReaderService {
constructor(
integration: AzureIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
credentialsProvider: AzureDevOpsCredentialsProvider;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class BitbucketCloudUrlReader implements UrlReaderService {
constructor(
integration: BitbucketCloudIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class BitbucketServerUrlReader implements UrlReaderService {
constructor(
integration: BitbucketServerIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public @deprecated
export class BitbucketUrlReader implements UrlReaderService {
constructor(
integration: BitbucketIntegration,
logger: LoggerService,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class FetchUrlReader implements UrlReaderService {
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export type FromReadableArrayOptions = Array<{
data: Readable;
path: string;
lastModifiedAt?: Date;
}>;
// @public
export class GerritUrlReader implements UrlReaderService {
constructor(
integration: GerritIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class GiteaUrlReader implements UrlReaderService {
constructor(
integration: GiteaIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class GithubUrlReader implements UrlReaderService {
constructor(
integration: GithubIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
credentialsProvider: GithubCredentialsProvider;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class GitlabUrlReader implements UrlReaderService {
constructor(
integration: GitLabIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export class HarnessUrlReader implements UrlReaderService {
constructor(
integration: HarnessIntegration,
deps: {
treeResponseFactory: ReadTreeResponseFactory;
},
);
// (undocumented)
static factory: ReaderFactory;
// (undocumented)
read(url: string): Promise<Buffer>;
// (undocumented)
readTree(
url: string,
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
readUrl(
url: string,
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse>;
// (undocumented)
search(): Promise<UrlReaderSearchResponse>;
// (undocumented)
toString(): string;
}
// @public
export type ReaderFactory = (options: {
config: Config;
logger: LoggerService;
treeResponseFactory: ReadTreeResponseFactory;
}) => UrlReaderPredicateTuple[];
// @public
export interface ReadTreeResponseFactory {
// (undocumented)
fromReadableArray(
options: FromReadableArrayOptions,
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
fromTarArchive(
options: ReadTreeResponseFactoryOptions & {
stripFirstDirectory?: boolean;
},
): Promise<UrlReaderReadTreeResponse>;
// (undocumented)
fromZipArchive(
options: ReadTreeResponseFactoryOptions,
): Promise<UrlReaderReadTreeResponse>;
}
// @public
export type ReadTreeResponseFactoryOptions = {
stream: Readable;
subpath?: string;
etag: string;
filter?: (
path: string,
info?: {
size: number;
},
) => boolean;
};
// @public
export class ReadUrlResponseFactory {
static fromNodeJSReadable(
oldStyleStream: NodeJS.ReadableStream,
options?: ReadUrlResponseFactoryFromStreamOptions,
): Promise<UrlReaderReadUrlResponse>;
static fromReadable(
stream: Readable,
options?: ReadUrlResponseFactoryFromStreamOptions,
): Promise<UrlReaderReadUrlResponse>;
}
// @public
export type ReadUrlResponseFactoryFromStreamOptions = {
etag?: string;
lastModifiedAt?: Date;
};
// @public
export type UrlReaderPredicateTuple = {
predicate: (url: URL) => boolean;
reader: UrlReaderService;
};
// @public
export class UrlReaders {
static create(options: UrlReadersOptions): UrlReaderService;
static default(options: UrlReadersOptions): UrlReaderService;
}
// @public (undocumented)
export const urlReaderServiceFactory: () => ServiceFactory<UrlReader, 'plugin'>;
export const urlReaderServiceFactory: () => ServiceFactory<
UrlReaderService,
'plugin'
>;
// @public
export type UrlReadersOptions = {
config: Config;
logger: LoggerService;
factories?: ReaderFactory[];
};
// (No @packageDocumentation comment for this package)
```
+23 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@backstage/backend-defaults",
"version": "0.3.0-next.2",
"version": "0.3.0-next.3",
"description": "Backend defaults used by Backstage backend apps",
"backstage": {
"role": "node-library"
@@ -82,6 +82,11 @@
"test": "backstage-cli package test"
},
"dependencies": {
"@aws-sdk/abort-controller": "^3.347.0",
"@aws-sdk/client-codecommit": "^3.350.0",
"@aws-sdk/client-s3": "^3.350.0",
"@aws-sdk/credential-providers": "^3.350.0",
"@aws-sdk/types": "^3.347.0",
"@backstage/backend-app-api": "workspace:^",
"@backstage/backend-common": "workspace:^",
"@backstage/backend-dev-utils": "workspace:^",
@@ -89,31 +94,48 @@
"@backstage/config": "workspace:^",
"@backstage/config-loader": "workspace:^",
"@backstage/errors": "workspace:^",
"@backstage/integration": "workspace:^",
"@backstage/integration-aws-node": "workspace:^",
"@backstage/plugin-events-node": "workspace:^",
"@backstage/plugin-permission-node": "workspace:^",
"@backstage/types": "workspace:^",
"@google-cloud/storage": "^7.0.0",
"@keyv/memcache": "^1.3.5",
"@keyv/redis": "^2.5.3",
"@octokit/rest": "^19.0.3",
"@opentelemetry/api": "^1.3.0",
"archiver": "^6.0.0",
"base64-stream": "^1.0.0",
"better-sqlite3": "^9.0.0",
"concat-stream": "^2.0.0",
"cron": "^3.0.0",
"fs-extra": "^11.2.0",
"git-url-parse": "^14.0.0",
"isomorphic-git": "^1.23.0",
"keyv": "^4.5.2",
"knex": "^3.0.0",
"lodash": "^4.17.21",
"luxon": "^3.0.0",
"minimatch": "^9.0.0",
"mysql2": "^3.0.0",
"node-fetch": "^2.6.7",
"p-limit": "^3.1.0",
"pg": "^8.11.3",
"pg-connection-string": "^2.3.0",
"raw-body": "^2.4.1",
"tar": "^6.1.12",
"uuid": "^9.0.0",
"yauzl": "^3.0.0",
"yn": "^4.0.0",
"zod": "^3.22.4"
},
"devDependencies": {
"@aws-sdk/util-stream-node": "^3.350.0",
"@backstage/backend-plugin-api": "workspace:^",
"@backstage/backend-test-utils": "workspace:^",
"@backstage/cli": "workspace:^",
"aws-sdk-client-mock": "^4.0.0",
"msw": "^1.0.0",
"wait-for-expect": "^3.0.2"
},
"configSchema": "config.d.ts"
@@ -192,7 +192,7 @@ export class Sqlite3Connector implements Connector {
const pluginDivisionMode = this.getPluginDivisionModeConfig();
if (pluginDivisionMode !== 'database') {
throw new Error(
`The SQLite driver does not suppoert plugin division mode '${pluginDivisionMode}'`,
`The SQLite driver does not support plugin division mode '${pluginDivisionMode}'`,
);
}
@@ -14,4 +14,5 @@
* limitations under the License.
*/
export * from './lib';
export { urlReaderServiceFactory } from './urlReaderServiceFactory';
@@ -212,7 +212,7 @@ describe('AwsCodeCommitUrlReader', () => {
integrations: {},
});
expect(entries).toHaveLength(1);
expect(entries).toHaveLength(0);
});
it('creates a reader with credentials correctly configured', () => {
@@ -221,6 +221,7 @@ describe('AwsCodeCommitUrlReader', () => {
host: AMAZON_AWS_CODECOMMIT_HOST,
accessKeyId: 'fakekey',
secretAccessKey: 'fakekey',
region: 'fakeregion',
});
const entries = createReader({
@@ -236,6 +237,7 @@ describe('AwsCodeCommitUrlReader', () => {
const awsCodeCommitIntegrations = [];
awsCodeCommitIntegrations.push({
host: AMAZON_AWS_CODECOMMIT_HOST,
region: 'fakeregion',
});
const entries = createReader({
@@ -247,10 +249,32 @@ describe('AwsCodeCommitUrlReader', () => {
expect(entries).toHaveLength(1);
});
it('creates a reader without a region', () => {
const awsCodeCommitIntegrations: any[] = [];
awsCodeCommitIntegrations.push({
accessKeyId: 'fakekey',
secretAccessKey: 'fakekey',
});
expect(() => {
createReader({
integrations: {
awsCodeCommit: awsCodeCommitIntegrations,
},
});
}).toThrow(
"Missing required config value at 'integrations.awsCodeCommit[0].region' in 'mock-config'",
);
});
describe('predicates', () => {
const readers = createReader({
integrations: {
awsCodeCommit: [{}],
awsCodeCommit: [
{
region: 'fakeregion',
},
],
},
});
const predicate = readers[0].predicate;
@@ -259,7 +283,7 @@ describe('AwsCodeCommitUrlReader', () => {
expect(
predicate(
new URL(
'https://eu-west-1.console.aws.amazon.com/codesuite/codecommit/repositories/my-repo',
'https://fakeregion.console.aws.amazon.com/codesuite/codecommit/repositories/my-repo',
),
),
).toBe(true);
@@ -269,12 +293,54 @@ describe('AwsCodeCommitUrlReader', () => {
expect(
predicate(
new URL(
'https://eu-west-1.console.aws.amazon.com/codesuite/codecommit/repositories/my-repo/browse/--/catalog-info.yaml?region=eu-west-1',
'https://fakeregion.console.aws.amazon.com/codesuite/codecommit/repositories/my-repo/browse/--/catalog-info.yaml?region=eu-west-1',
),
),
).toBe(true);
});
it('returns true for a url with the full path and the correct host when the host overrules the region', () => {
const predicateWithHost = createReader({
integrations: {
awsCodeCommit: [
{
host: 'fakehost',
region: 'fakeregion',
},
],
},
})[0].predicate;
expect(
predicateWithHost(
new URL(
'https://fakehost/codesuite/codecommit/repositories/my-repo/browse/--/catalog-info.yaml?region=eu-west-1',
),
),
).toBe(true);
});
it('returns false for a url with the full path and the wrong host when the host overrules the region', () => {
const predicateWithHost = createReader({
integrations: {
awsCodeCommit: [
{
host: 'fakehost',
region: 'fakeregion',
},
],
},
})[0].predicate;
expect(
predicateWithHost(
new URL(
'https://fakeregion.console.aws.amazon.com/codesuite/codecommit/repositories/my-repo/browse/--/catalog-info.yaml?region=eu-west-1',
),
),
).toBe(false);
});
it('returns false for an incorrect host', () => {
expect(predicate(new URL('https://amazon.com'))).toBe(false);
});
@@ -304,6 +370,7 @@ describe('AwsCodeCommitUrlReader', () => {
host: 'amazonaws.com',
accessKeyId: 'fake-access-key',
secretAccessKey: 'fake-secret-key',
region: 'fakeregion',
},
],
},
@@ -348,6 +415,7 @@ describe('AwsCodeCommitUrlReader', () => {
host: AMAZON_AWS_CODECOMMIT_HOST,
accessKeyId: 'fake-access-key',
secretAccessKey: 'fake-secret-key',
region: 'fakeregion',
},
],
},
@@ -403,6 +471,7 @@ describe('AwsCodeCommitUrlReader', () => {
host: AMAZON_AWS_CODECOMMIT_HOST,
accessKeyId: 'fake-access-key',
secretAccessKey: 'fake-secret-key',
region: 'fakeregion',
},
],
},
@@ -509,9 +578,9 @@ describe('AwsCodeCommitUrlReader', () => {
});
const config = new ConfigReader({
host: AMAZON_AWS_CODECOMMIT_HOST,
accessKeyId: 'fake-access-key',
secretAccessKey: 'fake-secret-key',
region: 'fakeregion',
});
const credsManager = DefaultAwsCredentialsManager.fromConfig(config);
@@ -527,7 +596,7 @@ describe('AwsCodeCommitUrlReader', () => {
it('returns contents of a file in a repository', async () => {
const response = await awsCodeCommitUrlReader.readTree(
'https://eu-west-1.console.aws.amazon.com/codesuite/codecommit/repositories/my-test-techdocs',
'https://fakeregion.console.aws.amazon.com/codesuite/codecommit/repositories/my-test-techdocs',
);
const files = await response.files();
@@ -14,16 +14,15 @@
* limitations under the License.
*/
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchResponse,
UrlReader,
} from './types';
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import {
AwsCredentialsManager,
DefaultAwsCredentialsManager,
@@ -118,7 +117,7 @@ export function parseUrl(
*
* @public
*/
export class AwsCodeCommitUrlReader implements UrlReader {
export class AwsCodeCommitUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
const credsManager = DefaultAwsCredentialsManager.fromConfig(config);
@@ -222,8 +221,8 @@ export class AwsCodeCommitUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
// etag and lastModifiedAfter are not supported by the CodeCommit API
try {
const { path, repositoryName, region, commitSpecifier } = parseUrl(
@@ -326,8 +325,8 @@ export class AwsCodeCommitUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
// url: https://eu-west-1.console.aws.amazon.com/codesuite/codecommit/repositories/test-stijn-delete-techdocs/browse?region=eu-west-1
try {
const { path, repositoryName, region, commitSpecifier } = parseUrl(url);
@@ -380,7 +379,7 @@ export class AwsCodeCommitUrlReader implements UrlReader {
}
}
async search(): Promise<SearchResponse> {
async search(): Promise<UrlReaderSearchResponse> {
throw new Error('AwsCodeCommitReader does not implement search');
}
@@ -15,15 +15,14 @@
*/
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchResponse,
UrlReader,
} from './types';
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import {
AwsCredentialsManager,
DefaultAwsCredentialsManager,
@@ -132,7 +131,7 @@ export function parseUrl(
*
* @public
*/
export class AwsS3UrlReader implements UrlReader {
export class AwsS3UrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
const credsManager = DefaultAwsCredentialsManager.fromConfig(config);
@@ -253,8 +252,8 @@ export class AwsS3UrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const { etag, lastModifiedAfter } = options ?? {};
try {
@@ -300,8 +299,8 @@ export class AwsS3UrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
try {
const { path, bucket, region } = parseUrl(url, this.integration.config);
const s3Client = await this.buildS3Client(
@@ -357,7 +356,7 @@ export class AwsS3UrlReader implements UrlReader {
}
}
async search(): Promise<SearchResponse> {
async search(): Promise<UrlReaderSearchResponse> {
throw new Error('AwsS3Reader does not implement search');
}
@@ -14,6 +14,15 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import {
getAzureCommitsUrl,
getAzureDownloadUrl,
@@ -27,17 +36,7 @@ import fetch, { Response } from 'node-fetch';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
ReadTreeResponseFactory,
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
SearchOptions,
SearchResponse,
UrlReader,
ReadUrlOptions,
ReadUrlResponse,
} from './types';
import { ReadTreeResponseFactory, ReaderFactory } from './types';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
/**
@@ -45,7 +44,7 @@ import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
*
* @public
*/
export class AzureUrlReader implements UrlReader {
export class AzureUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
const credentialProvider =
@@ -75,8 +74,8 @@ export class AzureUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
// TODO: etag is not implemented yet.
const { signal } = options ?? {};
@@ -114,8 +113,8 @@ export class AzureUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const { etag, filter, signal } = options ?? {};
// TODO: Support filepath based reading tree feature like other providers
@@ -180,7 +179,10 @@ export class AzureUrlReader implements UrlReader {
});
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const treeUrl = new URL(url);
const path = treeUrl.searchParams.get('path');
@@ -14,6 +14,15 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
BitbucketCloudIntegration,
@@ -28,17 +37,7 @@ import parseGitUrl from 'git-url-parse';
import { trimEnd } from 'lodash';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchOptions,
SearchResponse,
UrlReader,
} from './types';
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -47,7 +46,7 @@ import { parseLastModified } from './util';
*
* @public
*/
export class BitbucketCloudUrlReader implements UrlReader {
export class BitbucketCloudUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
return integrations.bitbucketCloud.list().map(integration => {
@@ -79,8 +78,8 @@ export class BitbucketCloudUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const { etag, lastModifiedAfter, signal } = options ?? {};
const bitbucketUrl = getBitbucketCloudFileFetchUrl(
url,
@@ -134,8 +133,8 @@ export class BitbucketCloudUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const { filepath } = parseGitUrl(url);
const lastCommitShortHash = await this.getLastCommitShortHash(url);
@@ -167,7 +166,10 @@ export class BitbucketCloudUrlReader implements UrlReader {
});
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const { filepath } = parseGitUrl(url);
const matcher = new Minimatch(filepath);
@@ -14,6 +14,15 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
BitbucketServerIntegration,
@@ -27,17 +36,7 @@ import parseGitUrl from 'git-url-parse';
import { trimEnd } from 'lodash';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchOptions,
SearchResponse,
UrlReader,
} from './types';
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -46,7 +45,7 @@ import { parseLastModified } from './util';
*
* @public
*/
export class BitbucketServerUrlReader implements UrlReader {
export class BitbucketServerUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
return integrations.bitbucketServer.list().map(integration => {
@@ -70,8 +69,8 @@ export class BitbucketServerUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const { etag, lastModifiedAfter, signal } = options ?? {};
const bitbucketUrl = getBitbucketServerFileFetchUrl(
url,
@@ -125,8 +124,8 @@ export class BitbucketServerUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const { filepath } = parseGitUrl(url);
const lastCommitShortHash = await this.getLastCommitShortHash(url);
@@ -158,7 +157,10 @@ export class BitbucketServerUrlReader implements UrlReader {
});
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const { filepath } = parseGitUrl(url);
const matcher = new Minimatch(filepath);
@@ -14,6 +14,15 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
BitbucketIntegration,
@@ -29,17 +38,7 @@ import { trimEnd } from 'lodash';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import { LoggerService } from '@backstage/backend-plugin-api';
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchOptions,
SearchResponse,
UrlReader,
} from './types';
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -50,7 +49,7 @@ import { parseLastModified } from './util';
* @public
* @deprecated in favor of BitbucketCloudUrlReader and BitbucketServerUrlReader
*/
export class BitbucketUrlReader implements UrlReader {
export class BitbucketUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, logger, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
return integrations.bitbucket
@@ -95,8 +94,8 @@ export class BitbucketUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const { etag, lastModifiedAfter, signal } = options ?? {};
const bitbucketUrl = getBitbucketFileFetchUrl(url, this.integration.config);
const requestOptions = getBitbucketRequestOptions(this.integration.config);
@@ -145,8 +144,8 @@ export class BitbucketUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const { filepath } = parseGitUrl(url);
const lastCommitShortHash = await this.getLastCommitShortHash(url);
@@ -178,7 +177,10 @@ export class BitbucketUrlReader implements UrlReader {
});
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const { filepath } = parseGitUrl(url);
const matcher = new Minimatch(filepath);
@@ -14,16 +14,16 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import fetch, { Response } from 'node-fetch';
import {
ReaderFactory,
ReadTreeResponse,
ReadUrlOptions,
ReadUrlResponse,
SearchResponse,
UrlReader,
} from './types';
import { ReaderFactory } from './types';
import path from 'path';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -68,7 +68,7 @@ const parsePortPredicate = (port: string | undefined) => {
*
* @public
*/
export class FetchUrlReader implements UrlReader {
export class FetchUrlReader implements UrlReaderService {
/**
* The factory creates a single reader that will be used for reading any URL that's listed
* in configuration at `backend.reading.allow`. The allow list contains a list of objects describing
@@ -121,8 +121,8 @@ export class FetchUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
let response: Response;
try {
response = await fetch(url, {
@@ -165,11 +165,11 @@ export class FetchUrlReader implements UrlReader {
throw new Error(message);
}
async readTree(): Promise<ReadTreeResponse> {
async readTree(): Promise<UrlReaderReadTreeResponse> {
throw new Error('FetchUrlReader does not implement readTree');
}
async search(): Promise<SearchResponse> {
async search(): Promise<UrlReaderSearchResponse> {
throw new Error('FetchUrlReader does not implement search');
}
@@ -32,10 +32,7 @@ import fs from 'fs-extra';
import path from 'path';
import { UrlReaderPredicateTuple } from './types';
import { DefaultReadTreeResponseFactory } from './tree';
import {
GITILES_BASE_URL_DEPRECATION_MESSSAGE,
GerritUrlReader,
} from './GerritUrlReader';
import { GerritUrlReader } from './GerritUrlReader';
import getRawBody from 'raw-body';
const mockDir = createMockDirectory({ mockOsTmpDir: true });
@@ -61,11 +58,11 @@ const gerritProcessor = new GerritUrlReader(
readGerritIntegrationConfig(
new ConfigReader({
host: 'gerrit.com',
gitilesBaseUrl: 'https://gerrit.com/gitiles',
}),
),
),
{ treeResponseFactory },
'/tmp',
);
// Gerrit processor with a gitilesBaseUrl configured.
@@ -80,7 +77,6 @@ const gerritProcessorWithGitiles = new GerritUrlReader(
),
),
{ treeResponseFactory },
'/tmp',
);
const createReader = (config: JsonObject): UrlReaderPredicateTuple[] => {
@@ -112,7 +108,12 @@ describe.skip('GerritUrlReader', () => {
it('creates a reader.', () => {
const readers = createReader({
integrations: {
gerrit: [{ host: 'gerrit.com' }],
gerrit: [
{
host: 'gerrit.com',
gitilesBaseUrl: 'https://gerrit.com/gitiles',
},
],
},
});
expect(readers).toHaveLength(1);
@@ -126,33 +127,12 @@ describe.skip('GerritUrlReader', () => {
});
});
describe('handle optional gitilesBaseUrl deprecation', () => {
it('should throw if gitilesBaseUrl is not set.', () => {
process.env = env;
expect(() =>
createReader({
integrations: {
gerrit: [{ host: 'gerrit.com' }],
},
}),
).toThrow(GITILES_BASE_URL_DEPRECATION_MESSSAGE);
});
it('should not throw if gitilesBaseUrl requirement is overridden.', () => {
process.env = { ...env, DISABLE_GERRIT_GITILES_REQUIREMENT: '1' };
expect(() =>
createReader({
integrations: {
gerrit: [{ host: 'gerrit.com' }],
},
}),
).not.toThrow();
});
});
describe('predicates without Gitiles', () => {
const readers = createReader({
integrations: {
gerrit: [{ host: 'gerrit.com' }],
gerrit: [
{ host: 'gerrit.com', gitilesBaseUrl: 'https://gerrit.com/gitiles' },
],
},
});
const predicate = readers[0].predicate;
@@ -354,29 +334,6 @@ describe.skip('GerritUrlReader', () => {
expect(cloneMock).not.toHaveBeenCalled();
});
it('reads the wanted files correctly using git clone.', async () => {
worker.use(
rest.get(branchAPIUrl, (_, res, ctx) => {
return res(ctx.status(200), ctx.body(branchAPIresponse));
}),
);
const response = await gerritProcessor.readTree(treeUrl);
expect(response.etag).toBe(etag);
const files = await response.files();
expect(files.length).toBe(2);
const docsYaml = await files[0].content();
expect(docsYaml.toString()).toBe(mkdocsContent);
const mdFile = await files[1].content();
expect(mdFile.toString()).toBe(mdContent);
expect(cloneMock).toHaveBeenCalled();
});
it('throws NotModifiedError for matching etags.', async () => {
worker.use(
rest.get(branchAPIUrl, (_, res, ctx) => {
@@ -432,25 +389,5 @@ describe.skip('GerritUrlReader', () => {
expect(cloneMock).not.toHaveBeenCalled();
});
it('should returns wanted files with a subpath using git clone', async () => {
worker.use(
rest.get(branchAPIUrl, (_, res, ctx) => {
return res(ctx.status(200), ctx.body(branchAPIresponse));
}),
);
const response = await gerritProcessor.readTree(`${treeUrl}/docs`);
expect(response.etag).toBe(etag);
const files = await response.files();
expect(files.length).toBe(1);
const mdFile = await files[0].content();
expect(mdFile.toString()).toBe(mdContent);
expect(cloneMock).toHaveBeenCalled();
});
});
});
@@ -14,49 +14,29 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { Base64Decode } from 'base64-stream';
import concatStream from 'concat-stream';
import fs from 'fs-extra';
import fetch, { Response } from 'node-fetch';
import os from 'os';
import { join as joinPath } from 'path';
import { Readable, pipeline as pipelineCb } from 'stream';
import tar from 'tar';
import { promisify } from 'util';
import { Readable } from 'stream';
import {
GerritIntegration,
ScmIntegrations,
buildGerritGitilesArchiveUrl,
getGerritBranchApiUrl,
getGerritCloneRepoUrl,
getGerritFileContentsApiUrl,
getGerritRequestOptions,
parseGerritGitilesUrl,
parseGerritJsonResponse,
} from '@backstage/integration';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
ReaderFactory,
SearchResponse,
UrlReader,
} from './types';
import { Git } from './git';
const pipeline = promisify(pipelineCb);
export const GITILES_BASE_URL_DEPRECATION_MESSSAGE = `A gitilesBaseUrl must be provided \
for the gerrit integration to work. You can disable this check by setting \
DISABLE_GERRIT_GITILES_REQUIREMENT=1 but this will be removed in a future release. If you \
are not able to use the gitiles gerrit plugin, please open an issue towards \
https://github.com/backstage/backstage`;
const createTemporaryDirectory = async (workDir: string): Promise<string> =>
await fs.mkdtemp(joinPath(workDir, '/gerrit-clone-'));
import { ReadTreeResponseFactory, ReaderFactory } from './types';
/**
* Implements a {@link @backstage/backend-plugin-api#UrlReaderService} for files in Gerrit.
@@ -78,26 +58,14 @@ const createTemporaryDirectory = async (workDir: string): Promise<string> =>
*
* @public
*/
export class GerritUrlReader implements UrlReader {
export class GerritUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
if (!integrations.gerrit) {
return [];
}
const workDir =
config.getOptionalString('backend.workingDirectory') ?? os.tmpdir();
return integrations.gerrit.list().map(integration => {
if (
integration.config.gitilesBaseUrl === integration.config.baseUrl &&
process.env.DISABLE_GERRIT_GITILES_REQUIREMENT === undefined
) {
throw new Error(GITILES_BASE_URL_DEPRECATION_MESSSAGE);
}
const reader = new GerritUrlReader(
integration,
{ treeResponseFactory },
workDir,
);
const reader = new GerritUrlReader(integration, { treeResponseFactory });
const predicate = (url: URL) => {
const gitilesUrl = new URL(integration.config.gitilesBaseUrl!);
// If gitilesUrl is not specified it will default to
@@ -111,7 +79,6 @@ export class GerritUrlReader implements UrlReader {
constructor(
private readonly integration: GerritIntegration,
private readonly deps: { treeResponseFactory: ReadTreeResponseFactory },
private readonly workDir: string,
) {}
async read(url: string): Promise<Buffer> {
@@ -121,8 +88,8 @@ export class GerritUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const apiUrl = getGerritFileContentsApiUrl(this.integration.config, url);
let response: Response;
try {
@@ -166,8 +133,8 @@ export class GerritUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const apiUrl = getGerritBranchApiUrl(this.integration.config, url);
let response: Response;
try {
@@ -195,15 +162,10 @@ export class GerritUrlReader implements UrlReader {
throw new NotModifiedError();
}
if (
this.integration.config.gitilesBaseUrl !== this.integration.config.baseUrl
) {
return this.readTreeFromGitiles(url, branchInfo.revision, options);
}
return this.readTreeFromGitClone(url, branchInfo.revision, options);
return this.readTreeFromGitiles(url, branchInfo.revision, options);
}
async search(): Promise<SearchResponse> {
async search(): Promise<UrlReaderSearchResponse> {
throw new Error('GerritReader does not implement search');
}
@@ -212,53 +174,10 @@ export class GerritUrlReader implements UrlReader {
return `gerrit{host=${host},authed=${Boolean(password)}}`;
}
private async readTreeFromGitClone(
url: string,
revision: string,
options?: ReadTreeOptions,
) {
const { filePath } = parseGerritGitilesUrl(this.integration.config, url);
const git = Git.fromAuth({
username: this.integration.config.username,
password: this.integration.config.password,
});
const tempDir = await createTemporaryDirectory(this.workDir);
const cloneUrl = getGerritCloneRepoUrl(this.integration.config, url);
try {
// The "fromTarArchive" function will strip the top level directory so
// an additional directory level is created when we clone.
await git.clone({
url: cloneUrl,
dir: joinPath(tempDir, 'repo'),
ref: revision,
depth: 1,
});
const data = await new Promise<Buffer>(async resolve => {
await pipeline(
tar.create({ cwd: tempDir }, ['']),
concatStream(resolve),
);
});
const tarArchive = Readable.from(data);
return await this.deps.treeResponseFactory.fromTarArchive({
stream: tarArchive,
subpath: filePath === '/' ? undefined : filePath,
etag: revision,
filter: options?.filter,
});
} catch (error) {
throw new Error(`Could not clone ${cloneUrl}: ${error}`);
} finally {
await fs.rm(tempDir, { recursive: true, force: true });
}
}
private async readTreeFromGitiles(
url: string,
revision: string,
options?: ReadTreeOptions,
options?: UrlReaderReadTreeOptions,
) {
const { branch, filePath, project } = parseGerritGitilesUrl(
this.integration.config,
@@ -13,6 +13,15 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import {
getGiteaFileContentsUrl,
getGiteaArchiveUrl,
@@ -22,16 +31,7 @@ import {
GiteaIntegration,
ScmIntegrations,
} from '@backstage/integration';
import {
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
ReadTreeResponseFactory,
ReadUrlOptions,
ReadUrlResponse,
SearchResponse,
UrlReader,
} from './types';
import { ReaderFactory, ReadTreeResponseFactory } from './types';
import fetch, { Response } from 'node-fetch';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import {
@@ -47,7 +47,7 @@ import { parseLastModified } from './util';
*
* @public
*/
export class GiteaUrlReader implements UrlReader {
export class GiteaUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
return ScmIntegrations.fromConfig(config)
.gitea.list()
@@ -74,8 +74,8 @@ export class GiteaUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
let response: Response;
const blobUrl = getGiteaFileContentsUrl(this.integration.config, url);
@@ -126,8 +126,8 @@ export class GiteaUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const lastCommitHash = await this.getLastCommitHash(url);
if (options?.etag && options.etag === lastCommitHash) {
throw new NotModifiedError();
@@ -156,7 +156,7 @@ export class GiteaUrlReader implements UrlReader {
});
}
search(): Promise<SearchResponse> {
search(): Promise<UrlReaderSearchResponse> {
throw new Error('GiteaUrlReader search not implemented.');
}
@@ -14,6 +14,16 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
UrlReaderSearchResponseFile,
} from '@backstage/backend-plugin-api';
import {
getGithubFileFetchUrl,
DefaultGithubCredentialsProvider,
@@ -28,18 +38,7 @@ import parseGitUrl from 'git-url-parse';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
ReadTreeResponseFactory,
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
SearchOptions,
SearchResponse,
SearchResponseFile,
UrlReader,
ReadUrlOptions,
ReadUrlResponse,
} from './types';
import { ReadTreeResponseFactory, ReaderFactory } from './types';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -58,7 +57,7 @@ export type GhBlobResponse =
*
* @public
*/
export class GithubUrlReader implements UrlReader {
export class GithubUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
const credentialsProvider =
@@ -113,8 +112,8 @@ export class GithubUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const credentials = await this.getCredentials(url, options);
const ghUrl = getGithubFileFetchUrl(
@@ -149,8 +148,8 @@ export class GithubUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const repoDetails = await this.getRepoDetails(url);
const commitSha = repoDetails.commitSha;
@@ -176,7 +175,10 @@ export class GithubUrlReader implements UrlReader {
);
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const repoDetails = await this.getRepoDetails(url);
const commitSha = repoDetails.commitSha;
@@ -209,8 +211,8 @@ export class GithubUrlReader implements UrlReader {
sha: string,
subpath: string,
init: RequestInit,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
// archive_url looks like "https://api.github.com/repos/owner/repo/{archive_format}{/ref}"
const archive = await this.fetchResponse(
archiveUrl
@@ -236,7 +238,7 @@ export class GithubUrlReader implements UrlReader {
sha: string,
query: string,
init: RequestInit,
): Promise<SearchResponseFile[]> {
): Promise<UrlReaderSearchResponseFile[]> {
function pathToUrl(path: string): string {
// TODO(freben): Use the integration package facility for this instead
// pathname starts as /backstage/backstage/blob/master/<path>
@@ -14,6 +14,15 @@
* limitations under the License.
*/
import {
UrlReaderService,
UrlReaderReadTreeOptions,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchOptions,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import {
getGitLabFileFetchUrl,
getGitLabIntegrationRelativePath,
@@ -26,17 +35,7 @@ import parseGitUrl from 'git-url-parse';
import { Minimatch } from 'minimatch';
import { Readable } from 'stream';
import { NotFoundError, NotModifiedError } from '@backstage/errors';
import {
ReadTreeResponseFactory,
ReaderFactory,
ReadTreeOptions,
ReadTreeResponse,
SearchOptions,
SearchResponse,
UrlReader,
ReadUrlResponse,
ReadUrlOptions,
} from './types';
import { ReadTreeResponseFactory, ReaderFactory } from './types';
import { trimEnd, trimStart } from 'lodash';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import { parseLastModified } from './util';
@@ -46,7 +45,7 @@ import { parseLastModified } from './util';
*
* @public
*/
export class GitlabUrlReader implements UrlReader {
export class GitlabUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, treeResponseFactory }) => {
const integrations = ScmIntegrations.fromConfig(config);
return integrations.gitlab.list().map(integration => {
@@ -70,8 +69,8 @@ export class GitlabUrlReader implements UrlReader {
async readUrl(
url: string,
options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
const { etag, lastModifiedAfter, signal } = options ?? {};
const builtUrl = await this.getGitlabFetchUrl(url);
@@ -119,8 +118,8 @@ export class GitlabUrlReader implements UrlReader {
async readTree(
url: string,
options?: ReadTreeOptions,
): Promise<ReadTreeResponse> {
options?: UrlReaderReadTreeOptions,
): Promise<UrlReaderReadTreeResponse> {
const { etag, signal } = options ?? {};
const { ref, full_name, filepath } = parseGitUrl(url);
@@ -236,7 +235,10 @@ export class GitlabUrlReader implements UrlReader {
});
}
async search(url: string, options?: SearchOptions): Promise<SearchResponse> {
async search(
url: string,
options?: UrlReaderSearchOptions,
): Promise<UrlReaderSearchResponse> {
const { filepath } = parseGitUrl(url);
const staticPart = this.getStaticPart(filepath);
const matcher = new Minimatch(filepath);
@@ -14,31 +14,27 @@
* limitations under the License.
*/
import * as GoogleCloud from '@google-cloud/storage';
import { ConfigReader } from '@backstage/config';
import { JsonObject } from '@backstage/types';
import { DefaultReadTreeResponseFactory } from './tree';
import { GoogleGcsUrlReader } from './GoogleGcsUrlReader';
import { UrlReaderPredicateTuple } from './types';
import packageinfo from '../../package.json';
import packageinfo from '../../../../package.json';
import { mockServices } from '@backstage/backend-test-utils';
const bucketGetFilesMock = jest.fn();
jest.mock('@google-cloud/storage', () => {
class Bucket {
getFiles(query: any) {
return bucketGetFilesMock(query);
}
class Bucket {
getFiles(query: any) {
return bucketGetFilesMock(query);
}
class Storage {
bucket() {
return new Bucket();
}
}
class Storage {
bucket() {
return new Bucket();
}
return {
__esModule: true,
Storage,
};
});
}
jest.spyOn(GoogleCloud, 'Storage').mockReturnValue(new Storage() as any);
describe('GcsUrlReader', () => {
const createReader = (config: JsonObject): UrlReaderPredicateTuple[] => {
@@ -80,7 +76,7 @@ describe('GcsUrlReader', () => {
});
it('check if userAgent has been called with this key value', async () => {
const getStorage: any = {
userAgent: `backstage/backend-common.GoogleGcsUrlReader/${packageinfo.version}`,
userAgent: `backstage/backend-defaults.GoogleGcsUrlReader/${packageinfo.version}`,
};
jest.mock('@google-cloud/storage', () => {
return {
@@ -89,7 +85,7 @@ describe('GcsUrlReader', () => {
});
const getUserAgent = getStorage.userAgent.toString();
expect(getUserAgent).toBe(
`backstage/backend-common.GoogleGcsUrlReader/${packageinfo.version}`,
`backstage/backend-defaults.GoogleGcsUrlReader/${packageinfo.version}`,
);
});
@@ -14,15 +14,15 @@
* limitations under the License.
*/
import { Storage } from '@google-cloud/storage';
import * as GoogleCloud from '@google-cloud/storage';
import {
ReaderFactory,
ReadTreeResponse,
ReadUrlOptions,
ReadUrlResponse,
SearchResponse,
UrlReader,
} from './types';
UrlReaderService,
UrlReaderReadTreeResponse,
UrlReaderReadUrlOptions,
UrlReaderReadUrlResponse,
UrlReaderSearchResponse,
} from '@backstage/backend-plugin-api';
import { ReaderFactory } from './types';
import getRawBody from 'raw-body';
import {
GoogleGcsIntegrationConfig,
@@ -30,7 +30,7 @@ import {
} from '@backstage/integration';
import { Readable } from 'stream';
import { ReadUrlResponseFactory } from './ReadUrlResponseFactory';
import packageinfo from '../../package.json';
import packageinfo from '../../../../package.json';
const GOOGLE_GCS_HOST = 'storage.cloud.google.com';
@@ -56,7 +56,7 @@ const parseURL = (
*
* @public
*/
export class GoogleGcsUrlReader implements UrlReader {
export class GoogleGcsUrlReader implements UrlReaderService {
static factory: ReaderFactory = ({ config, logger }) => {
if (!config.has('integrations.googleGcs')) {
return [];
@@ -64,21 +64,21 @@ export class GoogleGcsUrlReader implements UrlReader {
const gcsConfig = readGoogleGcsIntegrationConfig(
config.getConfig('integrations.googleGcs'),
);
let storage: Storage;
let storage: GoogleCloud.Storage;
if (!gcsConfig.clientEmail || !gcsConfig.privateKey) {
logger.info(
'googleGcs credentials not found in config. Using default credentials provider.',
);
storage = new Storage({
userAgent: `backstage/backend-common.GoogleGcsUrlReader/${packageinfo.version}`,
storage = new GoogleCloud.Storage({
userAgent: `backstage/backend-defaults.GoogleGcsUrlReader/${packageinfo.version}`,
});
} else {
storage = new Storage({
storage = new GoogleCloud.Storage({
credentials: {
client_email: gcsConfig.clientEmail || undefined,
private_key: gcsConfig.privateKey || undefined,
},
userAgent: `backstage/backend-common.GoogleGcsUrlReader/${packageinfo.version}`,
userAgent: `backstage/backend-defaults.GoogleGcsUrlReader/${packageinfo.version}`,
});
}
const reader = new GoogleGcsUrlReader(gcsConfig, storage);
@@ -88,7 +88,7 @@ export class GoogleGcsUrlReader implements UrlReader {
constructor(
private readonly integration: GoogleGcsIntegrationConfig,
private readonly storage: Storage,
private readonly storage: GoogleCloud.Storage,
) {}
private readStreamFromUrl(url: string): Readable {
@@ -106,18 +106,18 @@ export class GoogleGcsUrlReader implements UrlReader {
async readUrl(
url: string,
_options?: ReadUrlOptions,
): Promise<ReadUrlResponse> {
_options?: UrlReaderReadUrlOptions,
): Promise<UrlReaderReadUrlResponse> {
// TODO etag is not implemented yet.
const stream = this.readStreamFromUrl(url);
return ReadUrlResponseFactory.fromReadable(stream);
}
async readTree(): Promise<ReadTreeResponse> {
async readTree(): Promise<UrlReaderReadTreeResponse> {
throw new Error('GcsUrlReader does not implement readTree');
}
async search(url: string): Promise<SearchResponse> {
async search(url: string): Promise<UrlReaderSearchResponse> {
const { bucket, key: pattern } = parseURL(url);
if (!pattern.endsWith('*') || pattern.indexOf('*') !== pattern.length - 1) {

Some files were not shown because too many files have changed in this diff Show More