@redocly/revel 0.138.0-next.7 → 0.138.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +288 -0
- package/dist/api-schemas/mcp-fetch-count.d.ts +24 -0
- package/dist/api-schemas/mcp-fetch-count.js +1 -0
- package/dist/bin.js +0 -0
- package/dist/cli/build/analytics/collect-analytics.js +1 -1
- package/dist/cli/build/analytics/collectors/get-processed-config-stats-usage.js +1 -1
- package/dist/cli/build/index.js +1 -1
- package/dist/cli/develop.js +1 -1
- package/dist/cli/eject/ejectTheme.js +1 -1
- package/dist/cli/translations/collect-config-translations.js +1 -1
- package/dist/client/App.js +1 -1
- package/dist/client/app/ReviewComments/ReviewComments.js +2 -2
- package/dist/client/app/l10n/hooks/useTranslationKeys.js +1 -1
- package/dist/client/app/markdoc/custom-components/openapi/openapi-example.js +1 -1
- package/dist/client/app/markdoc/custom-components/openapi/openapi-response-sample.js +1 -1
- package/dist/client/app/markdoc/custom-components/openapi/replay-openapi.js +1 -1
- package/dist/client/app/markdoc/hooks/use-store.d.ts +2 -3
- package/dist/client/app/pages/Invite/Invite.js +1 -1
- package/dist/client/app/search/useSearch.js +1 -1
- package/dist/client/app/utils/loadAndNavigate.js +1 -1
- package/dist/client/polyfills.js +1 -1
- package/dist/client/runtime/loader.js +1 -1
- package/dist/client/utils/catalog/parse-filter-query.js +1 -1
- package/dist/compiled/svgo/svgo-node.js +39 -39
- package/dist/constants/api.d.ts +1 -0
- package/dist/constants/api.js +1 -1
- package/dist/constants/common.d.ts +6 -0
- package/dist/constants/common.js +1 -1
- package/dist/constants/l10n/langs/ar.js +1 -1
- package/dist/constants/l10n/langs/de.js +1 -1
- package/dist/constants/l10n/langs/en.js +1 -1
- package/dist/constants/l10n/langs/es.js +1 -1
- package/dist/constants/l10n/langs/fr.js +1 -1
- package/dist/constants/l10n/langs/hi.js +1 -1
- package/dist/constants/l10n/langs/it.js +1 -1
- package/dist/constants/l10n/langs/ja.js +1 -1
- package/dist/constants/l10n/langs/ko.js +1 -1
- package/dist/constants/l10n/langs/pl.js +1 -1
- package/dist/constants/l10n/langs/pt-BR.js +1 -1
- package/dist/constants/l10n/langs/pt.js +1 -1
- package/dist/constants/l10n/langs/ru.js +1 -1
- package/dist/constants/l10n/langs/uk.js +1 -1
- package/dist/constants/l10n/langs/zh.js +1 -1
- package/dist/markdoc/helpers/get-inner-text.js +2 -2
- package/dist/markdoc/helpers/guards/is-prompt-node.d.ts +13 -0
- package/dist/markdoc/helpers/guards/is-prompt-node.js +1 -0
- package/dist/server/config/env-config.d.ts +0 -4
- package/dist/server/config/env-schema.d.ts +0 -10
- package/dist/server/config/env-schemas/feature-flags.d.ts +0 -8
- package/dist/server/config/env-schemas/feature-flags.js +1 -1
- package/dist/server/constants/entitlements.js +1 -1
- package/dist/server/entitlements/entitlements-provider.js +1 -1
- package/dist/server/esbuild/esbuild.js +3 -3
- package/dist/server/esbuild/plugins/on-rebuild.js +1 -1
- package/dist/server/esbuild/plugins/styled-components-ssr.js +1 -1
- package/dist/server/esbuild/plugins/yaml-loader.js +1 -1
- package/dist/server/fs/content-fs.js +1 -1
- package/dist/server/fs/utils/is-l10n-root-file.d.ts +3 -0
- package/dist/server/fs/utils/is-l10n-root-file.js +1 -0
- package/dist/server/plugins/analytics/amplitude/index.js +1 -1
- package/dist/server/plugins/analytics/heap/browser-hooks.js +1 -1
- package/dist/server/plugins/api-docs/index.js +1 -1
- package/dist/server/plugins/api-docs/loader.js +3 -3
- package/dist/server/plugins/api-docs/spec-download.api.js +1 -1
- package/dist/server/plugins/api-docs/utils/apply-nav-item-to-root.js +1 -1
- package/dist/server/plugins/api-docs/utils/decorators.d.ts +11 -0
- package/dist/server/plugins/api-docs/utils/decorators.js +1 -1
- package/dist/server/plugins/arazzo-docs/arazzo-doc-loader.js +2 -2
- package/dist/server/plugins/catalog-entities/extensions/extractors/api-description/openapi-entities-extractor.js +1 -1
- package/dist/server/plugins/catalog-entities/utils/extract-parts-from-channels-message-ref.js +1 -1
- package/dist/server/plugins/config-parser/format-custom-tags.js +1 -1
- package/dist/server/plugins/config-parser/loaders/content-slugs-loader.js +1 -1
- package/dist/server/plugins/config-parser/loaders/versions-config-loader.js +1 -1
- package/dist/server/plugins/config-parser/resolve-mutual-exclusion.js +1 -1
- package/dist/server/plugins/config-parser/safe-parse.js +1 -1
- package/dist/server/plugins/default-theme/resolve-logo.js +1 -1
- package/dist/server/plugins/dev-onboarding/api/adapters/apigee/adapter.js +2 -2
- package/dist/server/plugins/dev-onboarding/api/adapters/gravitee/client.js +2 -2
- package/dist/server/plugins/dev-onboarding/api/combine.js +1 -1
- package/dist/server/plugins/dev-onboarding/template/components/ApiKeyOverview.js +3 -3
- package/dist/server/plugins/dev-onboarding/template/components/AppOverview.js +1 -1
- package/dist/server/plugins/dev-onboarding/template/components/useSortableData.js +1 -1
- package/dist/server/plugins/markdown/attribute-resolvers/code-walkthrough/file-chunk-parser.d.ts +1 -1
- package/dist/server/plugins/markdown/attribute-resolvers/index.js +1 -1
- package/dist/server/plugins/markdown/attribute-resolvers/resolve-link.js +1 -1
- package/dist/server/plugins/markdown/attribute-resolvers/resolve-svg-content.js +1 -1
- package/dist/server/plugins/markdown/attribute-resolvers/resolve-tag-raw-content.d.ts +4 -0
- package/dist/server/plugins/markdown/attribute-resolvers/resolve-tag-raw-content.js +2 -0
- package/dist/server/plugins/markdown/compiler.js +1 -1
- package/dist/server/plugins/markdown/create-source-lines-reader.d.ts +7 -0
- package/dist/server/plugins/markdown/create-source-lines-reader.js +1 -0
- package/dist/server/plugins/markdown/html/normalize-html-headings.d.ts +9 -0
- package/dist/server/plugins/markdown/html/normalize-html-headings.js +1 -0
- package/dist/server/plugins/markdown/markdoc/markdoc-options.js +1 -1
- package/dist/server/plugins/markdown/markdoc/plugins/utils.d.ts +1 -1
- package/dist/server/plugins/markdown/markdoc/plugins/utils.js +1 -1
- package/dist/server/plugins/markdown/markdown-static-data-loader.js +1 -1
- package/dist/server/plugins/markdown/search/get-ai-search-documents.js +2 -2
- package/dist/server/plugins/markdown/search/search-resolver.js +1 -1
- package/dist/server/plugins/markdown/search/to-markdown.js +13 -13
- package/dist/server/plugins/markdown/search/walk-sections.d.ts +3 -1
- package/dist/server/plugins/markdown/search/walk-sections.js +3 -3
- package/dist/server/plugins/markdown/utils/sanitize-malformed-md-content.js +2 -2
- package/dist/server/plugins/mcp/audit/audit-log.d.ts +1 -1
- package/dist/server/plugins/mcp/audit/audit-log.js +1 -1
- package/dist/server/plugins/mcp/audit/code-credentials.d.ts +9 -0
- package/dist/server/plugins/mcp/audit/code-credentials.js +2 -0
- package/dist/server/plugins/mcp/codemode/capabilities/fetch/index.js +5 -5
- package/dist/server/plugins/mcp/codemode/capabilities/types.d.ts +3 -1
- package/dist/server/plugins/mcp/codemode/capabilities/utils.d.ts +2 -1
- package/dist/server/plugins/mcp/codemode/capabilities/utils.js +3 -3
- package/dist/server/plugins/mcp/codemode/code-audit.d.ts +4 -3
- package/dist/server/plugins/mcp/codemode/code-execution-audit.js +1 -1
- package/dist/server/plugins/mcp/custom-tools/scan-custom-tools.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/tool-schemas.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/tools/core/utils.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/tools/core/whoami.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/tools/openapi/list-apis.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/tools/openapi/utils.d.ts +12 -3
- package/dist/server/plugins/mcp/docs-mcp/tools/openapi/utils.js +1 -1
- package/dist/server/plugins/mcp/docs-mcp/utils/resolve-refs.d.ts +2 -2
- package/dist/server/plugins/mcp/docs-mcp/utils/resolve-refs.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/allowed-http-methods.d.ts +11 -0
- package/dist/server/plugins/mcp/gateway-mcp/allowed-http-methods.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/api-call-operations.d.ts +32 -0
- package/dist/server/plugins/mcp/gateway-mcp/api-call-operations.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/callable-apis.d.ts +7 -4
- package/dist/server/plugins/mcp/gateway-mcp/callable-apis.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/caller-api-calls.d.ts +9 -0
- package/dist/server/plugins/mcp/gateway-mcp/caller-api-calls.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/credential-validation.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/elicitation.d.ts +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/elicitation.js +5 -5
- package/dist/server/plugins/mcp/gateway-mcp/eligibility.d.ts +8 -4
- package/dist/server/plugins/mcp/gateway-mcp/eligibility.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch/fetch-audit.d.ts +2 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch/fetch-audit.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch/fetch-bridge.d.ts +11 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch/fetch-bridge.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch/redact.d.ts +11 -0
- package/dist/server/plugins/mcp/gateway-mcp/fetch/redact.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/fetch-capability.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count-client.d.ts +4 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count-client.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count-secret.d.ts +4 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count-secret.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count.d.ts +11 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-count.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-counter-repository.d.ts +13 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-counter-repository.js +13 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{limits.d.ts → fetch-limiter/fetch-limits.d.ts} +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/fetch-limiter/fetch-limits.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{apply-edge-rate-limit.d.ts → request-limiter/apply-edge-rate-limit.d.ts} +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/request-limiter/apply-edge-rate-limit.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{edge-limiter.d.ts → request-limiter/edge-limiter.d.ts} +3 -3
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/request-limiter/edge-limiter.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/request-limiter/rate-limit-telemetry.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/request-limiter/request-limits.d.ts +6 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/request-limiter/request-limits.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/utils/ip-key.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{window-counter.d.ts → utils/window-counter.d.ts} +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/utils/window-counter.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/route-pattern.d.ts +18 -0
- package/dist/server/plugins/mcp/gateway-mcp/route-pattern.js +1 -0
- package/dist/server/plugins/mcp/gateway-mcp/secret-store.d.ts +9 -3
- package/dist/server/plugins/mcp/gateway-mcp/secret-store.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/subject.js +1 -1
- package/dist/server/plugins/mcp/gateway-mcp/upstream-auth-scheme.d.ts +2 -0
- package/dist/server/plugins/mcp/gateway-mcp/upstream-auth-scheme.js +2 -2
- package/dist/server/plugins/mcp/gateway-mcp/upstream-auth.d.ts +0 -2
- package/dist/server/plugins/mcp/gateway-mcp/upstream-auth.js +1 -1
- package/dist/server/plugins/mcp/handlers/credentials-page/constants.d.ts +7 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/constants.js +1 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/form-contract.d.ts +5 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/form-contract.js +1 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/form-page.d.ts +14 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/form-page.js +62 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/layout.d.ts +17 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/layout.js +11 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/outcome-pages.d.ts +10 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/outcome-pages.js +11 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/site-branding.d.ts +10 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/site-branding.js +1 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/styles.d.ts +4 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/styles.js +186 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/types.d.ts +32 -0
- package/dist/server/plugins/mcp/handlers/credentials-page/types.js +0 -0
- package/dist/server/plugins/mcp/handlers/docs-mcp-handler.js +1 -1
- package/dist/server/plugins/mcp/handlers/handle-mcp-request.js +1 -1
- package/dist/server/plugins/mcp/handlers/mcp-credentials-handler.d.ts +0 -1
- package/dist/server/plugins/mcp/handlers/mcp-credentials-handler.js +1 -1
- package/dist/server/plugins/mcp/index.js +1 -1
- package/dist/server/plugins/mcp/servers/docs-server.js +1 -1
- package/dist/server/plugins/mcp/servers/mcp-server.js +2 -2
- package/dist/server/plugins/mcp/types.d.ts +16 -1
- package/dist/server/plugins/mcp/utils/mode.d.ts +4 -1
- package/dist/server/plugins/mcp/utils/mode.js +1 -1
- package/dist/server/plugins/mcp/utils/xmcp-utils.d.ts +3 -5
- package/dist/server/plugins/mcp/utils/xmcp-utils.js +1 -1
- package/dist/server/plugins/nav-utils.js +1 -1
- package/dist/server/plugins/scorecard-classic/loaders/scorecard.js +1 -1
- package/dist/server/plugins/scorecard-classic/template/components.js +1 -1
- package/dist/server/plugins/scorecard-classic/template/useData.js +1 -1
- package/dist/server/plugins/scorecard-classic/template/views.js +1 -1
- package/dist/server/plugins/search/engines/flexsearch/index.js +2 -2
- package/dist/server/plugins/sidebars/index.js +2 -2
- package/dist/server/plugins/sidebars/tabs.js +1 -1
- package/dist/server/plugins/sidebars/utils.js +1 -1
- package/dist/server/providers/database/client.d.ts +5 -0
- package/dist/server/providers/database/client.js +1 -1
- package/dist/server/providers/database/copy-migrations.js +1 -1
- package/dist/server/providers/database/database-connections-manager.js +1 -1
- package/dist/server/providers/database/has-project-database.d.ts +3 -0
- package/dist/server/providers/database/has-project-database.js +1 -0
- package/dist/server/store.d.ts +2 -0
- package/dist/server/store.js +1 -1
- package/dist/server/tools/notifiers/formatter.js +1 -1
- package/dist/server/tools/notifiers/helpers/privacy/mask-email.js +1 -1
- package/dist/server/tools/notifiers/logger.js +1 -1
- package/dist/server/types/plugins/markdown.d.ts +2 -0
- package/dist/server/types/web-server.d.ts +1 -0
- package/dist/server/utils/codeframes/codeframes.js +2 -2
- package/dist/server/utils/entitlements/read-entitlement-number.d.ts +3 -0
- package/dist/server/utils/entitlements/read-entitlement-number.js +1 -0
- package/dist/server/utils/fs.js +1 -1
- package/dist/server/utils/is-api-download-link.d.ts +1 -0
- package/dist/server/utils/is-api-download-link.js +1 -1
- package/dist/server/utils/rbac.js +1 -1
- package/dist/server/utils/redact-url.d.ts +3 -2
- package/dist/server/utils/redact-url.js +1 -1
- package/dist/server/utils/sandbox-context.d.ts +7 -4
- package/dist/server/utils/sandbox-context.js +1 -1
- package/dist/server/web-server/auth.d.ts +0 -1
- package/dist/server/web-server/auth.js +4 -4
- package/dist/server/web-server/dev-server.js +1 -1
- package/dist/server/web-server/http.d.ts +2 -1
- package/dist/server/web-server/http.js +2 -2
- package/dist/server/web-server/jwt/token-types.d.ts +1 -0
- package/dist/server/web-server/jwt/token-types.js +1 -1
- package/dist/server/web-server/middleware/catalogAuthMiddleware.js +1 -1
- package/dist/server/web-server/middleware/dynamic-middleware/hono-compose.js +1 -1
- package/dist/server/web-server/middleware/responseHeadersMiddleware.js +1 -1
- package/dist/server/web-server/routes/auth.d.ts +1 -1
- package/dist/server/web-server/routes/auth.js +1 -1
- package/dist/server/web-server/routes/catalog/helpers/create-entity-schema.d.ts +1756 -1756
- package/dist/server/web-server/routes/catalog/helpers/create-entity-update-schema.d.ts +295 -295
- package/dist/server/web-server/routes/cors-proxy.js +2 -2
- package/dist/server/web-server/routes/index.js +1 -1
- package/dist/server/web-server/routes/mcp-routes/mcp-consent-page.d.ts +24 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-consent-page.js +35 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-fetch-count.d.ts +8 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-fetch-count.js +1 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-oauth-store.d.ts +15 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-oauth-store.js +1 -0
- package/dist/server/web-server/routes/mcp-routes/mcp-oauth.d.ts +3 -1
- package/dist/server/web-server/routes/mcp-routes/mcp-oauth.js +1 -1
- package/dist/server/web-server/routes/mcp-routes/mcp-routes.js +1 -1
- package/dist/server/web-server/routes/mcp-routes/mcp-server-card.js +1 -1
- package/dist/server/web-server/routes/resolve-route.js +1 -1
- package/dist/server/workers/worker-pool.js +1 -1
- package/dist/types/entitlements.d.ts +2 -0
- package/dist/utils/time/debounce.js +1 -1
- package/package.json +10 -11
- package/dist/client/app/utils/withLoadProgress.d.ts +0 -2
- package/dist/client/app/utils/withLoadProgress.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/apply-edge-rate-limit.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/edge-limiter.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/ip-key.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/limits.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/rate-limit-telemetry.js +0 -1
- package/dist/server/plugins/mcp/gateway-mcp/rate-limit/window-counter.js +0 -1
- package/dist/server/plugins/mcp/handlers/mcp-credentials-page.d.ts +0 -12
- package/dist/server/plugins/mcp/handlers/mcp-credentials-page.js +0 -225
- /package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{rate-limit-telemetry.d.ts → request-limiter/rate-limit-telemetry.d.ts} +0 -0
- /package/dist/server/plugins/mcp/gateway-mcp/rate-limit/{ip-key.d.ts → utils/ip-key.d.ts} +0 -0
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import{logger as n}from"../../../../../tools/notifiers/logger.js";import{canAccessResource as U}from"../../../../../utils/rbac.js";import{ApigeeDevOnboardingIntegrationAuthType as w,APIGEE_VERSION as m}from"./types.js";import{AlgorithmTypes as D}from"../../../../../web-server/jwt/types.js";import*as S from"../../../../../web-server/jwt/jwt.js";import{getFirstNameFromClaims as k,getLastNameFromClaims as T}from"../../../utils.js";import{HttpError as b}from"../../../../../utils/errors.js";const f="developer.service.DeveloperDoesNotExist",$=3600*24*365*1;function O(s){return s.replace(/\+/g,"%2B")}function y(s){return{id:s.consumerKey,clientId:s.consumerKey,clientSecret:s.consumerSecret,scopes:s.scopes,issuedAt:s.issuedAt,expiresAt:s.expiresAt,attributes:N(s.attributes),status:s.status,apiProductsStatus:s.apiProducts?.map(e=>({id:e.apiproduct,status:e.status,name:e.apiproduct}))||[],canBeRolled:!1,canBeRevoked:!0,valueToUseInHeader:"clientId"}}function A(s){const e=Object.fromEntries((s.attributes||[]).map(t=>[t.name,t.value]));return{id:s.name,name:e.DisplayName||s.name,description:e.Notes||"",...s.callbackUrl!==void 0?{callbackUrl:s.callbackUrl}:{},attributes:e,createdAt:s.createdAt,lastModifiedAt:s.lastModifiedAt,scopes:s.scopes,credentials:s.credentials?.map(y)||[],supportsLogs:!1,canCreateKey:!0}}function x(s){const e=Object.fromEntries((s.attributes||[]).map(t=>[t.name,t.value]));return{id:s.name,name:e.DisplayName||s.name,description:s.description,attributes:e,createdAt:s.createdAt,lastModifiedAt:s.lastModifiedAt,approvalType:s.approvalType,scopes:s.scopes}}function v(s){return Object.entries(s||{}).map(([e,t])=>({name:e,value:t}))}function N(s){return Object.fromEntries((s||[]).map(e=>[e.name,e.value]))}let h=null;async function I(s){h?(await h).expiresAt<Date.now()/1e3&&(n.info("Token expired, requesting new apigee access token"),h=C(s)):(n.info("Requesting apigee access token"),h=C(s));try{return(await h).token}catch(e){throw h=null,e}}async function C({auth:s}){switch(s.type){case w.OAUTH2:return j(s);case w.SERVICE_ACCOUNT:return _(s)}}async function j(s){const e={grant_type:"client_credentials",client_id:s.clientId,client_secret:s.clientSecret}
|
|
1
|
+
import{logger as n}from"../../../../../tools/notifiers/logger.js";import{canAccessResource as U}from"../../../../../utils/rbac.js";import{ApigeeDevOnboardingIntegrationAuthType as w,APIGEE_VERSION as m}from"./types.js";import{AlgorithmTypes as D}from"../../../../../web-server/jwt/types.js";import*as S from"../../../../../web-server/jwt/jwt.js";import{getFirstNameFromClaims as k,getLastNameFromClaims as T}from"../../../utils.js";import{HttpError as b}from"../../../../../utils/errors.js";const f="developer.service.DeveloperDoesNotExist",$=3600*24*365*1;function O(s){return s.replace(/\+/g,"%2B")}function y(s){return{id:s.consumerKey,clientId:s.consumerKey,clientSecret:s.consumerSecret,scopes:s.scopes,issuedAt:s.issuedAt,expiresAt:s.expiresAt,attributes:N(s.attributes),status:s.status,apiProductsStatus:s.apiProducts?.map(e=>({id:e.apiproduct,status:e.status,name:e.apiproduct}))||[],canBeRolled:!1,canBeRevoked:!0,valueToUseInHeader:"clientId"}}function A(s){const e=Object.fromEntries((s.attributes||[]).map(t=>[t.name,t.value]));return{id:s.name,name:e.DisplayName||s.name,description:e.Notes||"",...s.callbackUrl!==void 0?{callbackUrl:s.callbackUrl}:{},attributes:e,createdAt:s.createdAt,lastModifiedAt:s.lastModifiedAt,scopes:s.scopes,credentials:s.credentials?.map(y)||[],supportsLogs:!1,canCreateKey:!0}}function x(s){const e=Object.fromEntries((s.attributes||[]).map(t=>[t.name,t.value]));return{id:s.name,name:e.DisplayName||s.name,description:s.description,attributes:e,createdAt:s.createdAt,lastModifiedAt:s.lastModifiedAt,approvalType:s.approvalType,scopes:s.scopes}}function v(s){return Object.entries(s||{}).map(([e,t])=>({name:e,value:t}))}function N(s){return Object.fromEntries((s||[]).map(e=>[e.name,e.value]))}let h=null;async function I(s){h?(await h).expiresAt<Date.now()/1e3&&(n.info("Token expired, requesting new apigee access token"),h=C(s)):(n.info("Requesting apigee access token"),h=C(s));try{return(await h).token}catch(e){throw h=null,e}}async function C({auth:s}){switch(s.type){case w.OAUTH2:return j(s);case w.SERVICE_ACCOUNT:return _(s)}}async function j(s){const e={grant_type:"client_credentials",client_id:s.clientId,client_secret:s.clientSecret},t=await fetch(s.tokenEndpoint,{method:"POST",headers:{"Content-Type":"application/x-www-form-urlencoded"},body:new URLSearchParams(e).toString()});if(!t.ok)throw new Error(`Failed to get access token: ${t.statusText}
|
|
2
2
|
${await t.text()}`);const a=await t.json(),{access_token:i,expires_in:r}=a;return n.info("Apigee access token received"),{token:i,expiresAt:Math.floor(Date.now()/1e3)+r}}async function _(s){n.verbose(`Using service account to sign JWT token: Email: "%s" Private key:
|
|
3
3
|
%s
|
|
4
|
-
`,s.serviceAccountEmail,s.serviceAccountPrivateKey.slice(0,30)+"***"+s.serviceAccountPrivateKey.slice(-30));const t={grant_type:"urn:ietf:params:oauth:grant-type:jwt-bearer",assertion:await S.sign({sub:s.serviceAccountEmail,iss:s.serviceAccountEmail,aud:"https://www.googleapis.com/oauth2/v4/token",iat:Math.floor(Date.now()/1e3),exp:Math.floor(Date.now()/1e3)+3600,scope:"https://www.googleapis.com/auth/cloud-platform"},s.serviceAccountPrivateKey,D.RS256)};n.verbose("Exchanging JWT for access token",s.serviceAccountEmail,s.serviceAccountPrivateKey.slice(0,30)+"***"+s.serviceAccountPrivateKey.slice(-30));
|
|
4
|
+
`,s.serviceAccountEmail,s.serviceAccountPrivateKey.slice(0,30)+"***"+s.serviceAccountPrivateKey.slice(-30));const t={grant_type:"urn:ietf:params:oauth:grant-type:jwt-bearer",assertion:await S.sign({sub:s.serviceAccountEmail,iss:s.serviceAccountEmail,aud:"https://www.googleapis.com/oauth2/v4/token",iat:Math.floor(Date.now()/1e3),exp:Math.floor(Date.now()/1e3)+3600,scope:"https://www.googleapis.com/auth/cloud-platform"},s.serviceAccountPrivateKey,D.RS256)};n.verbose("Exchanging JWT for access token",s.serviceAccountEmail,s.serviceAccountPrivateKey.slice(0,30)+"***"+s.serviceAccountPrivateKey.slice(-30));const a=await fetch("https://oauth2.googleapis.com/token",{method:"POST",headers:{"Content-Type":"application/x-www-form-urlencoded"},body:new URLSearchParams(t).toString()});if(!a.ok)throw new Error(`Failed to get access token: ${a.statusText}
|
|
5
5
|
${await a.text()}`);const i=await a.json(),{access_token:r,expires_in:o}=i;return n.info("Apigee access token received"),{token:r,expiresAt:Math.floor(Date.now()/1e3)+o}}class F{apiUrl;developerUrl;accessToken=null;organizationName;email;organizationUrl;version;userClaims;config;ignoreApiProducts;catalogApiProducts;allowApiProductsOutsideCatalog;adapterId;stage;rbacConfig;constructor(e,t,a,i){const r=e;this.apiUrl=r.apiUrl||"https://apigee.googleapis.com/v1",this.organizationName=r.organizationName,this.email=a.email,this.organizationUrl=`${this.apiUrl}/organizations/${this.organizationName}`,this.developerUrl=`${this.organizationUrl}/developers/${O(this.email)}`,this.version=e.type==="APIGEE_X"?m.x:m.edge,this.userClaims=a,this.adapterId=r.organizationName,this.ignoreApiProducts=new Set(r.ignoreApiProducts||[]),this.catalogApiProducts=new Map(Object.entries(i)),this.allowApiProductsOutsideCatalog=r.allowApiProductsOutsideCatalog??!1,this.config=r,this.stage=r.stage||"non-production",this.rbacConfig=t}async setAuthHeader(e){return e=e||{},e.headers={...e.headers,"Accept-Encoding":"identity",accept:"application/json",Authorization:"Bearer "+await I(this.config),"X-Api-Key":this.config.auth.type===w.OAUTH2?this.config.auth.clientId:void 0},e}getErrorMessage(e){if(!e)return"Fetch error";try{const t=JSON.parse(e);return t.code===f?t.code:t.error.details[0]?.["@type"]==="type.googleapis.com/google.rpc.PreconditionFailure"&&t.error.details[0]?.violations[0]?.type===f?f:t?.message||t.error.message}catch{return e}}async fetchData(e,t){const a=await this.setAuthHeader(t),i=typeof e=="string"?e:e.url,r=typeof e=="string"?"GET":e.method;n.verbose(`${r.toUpperCase()} request to "${i}"`);const o=await fetch(e,a);if(!o.ok){const d=await o.text(),c=this.getErrorMessage(d);if(c===f){const p=this.userClaims,g=k(p),u=T(p),l=this.email;return await this.createDeveloper(this.email,g,u,l),await this.fetchData(e,t)}throw o.status!==404&&n.warn(`${r.toUpperCase()} request to "${i}" failed with ${o.status} code`),new b(o.status,c)}return o.headers.get("x-redocly-apigee-version")===m.x&&(this.version=m.x),n.verbose(`${r.toUpperCase()} request to "${i}" OK`),o.json()}async getApps(){const e=`${this.developerUrl}/apps?expand=true`,{app:t}=await this.fetchData(e),a=(t||[]).map(A);return{data:a,total:a.length}}async getApiProducts(){const e=`${this.organizationUrl}/apiproducts?expand=true`,{apiProduct:t}=await this.fetchData(e),a=(t||[]).filter(i=>U(this.catalogApiProducts.get(i.name)||{},this.userClaims,this.rbacConfig)&&(this.allowApiProductsOutsideCatalog||this.catalogApiProducts.has(i.name))&&!this.ignoreApiProducts.has(i.name)).map(x);return{data:a,total:a.length}}async getApp(e){const t=`${this.developerUrl}/apps/${e}${this.version===m.edge?"?expand=true":""}`,a=await this.fetchData(t);return A(a)}createDeveloper(e,t,a,i){const r=`${this.organizationUrl}/developers`;return this.fetchData(r,{headers:{"Content-type":"application/json"},body:JSON.stringify({email:e,firstName:t,lastName:a,userName:i}),method:"POST"})}async createApp(e){const t=`${this.developerUrl}/apps`;n.verbose(`Creating app ${e.id} ${e.apiProductIds}`);const a=await this.fetchData(t,{headers:{"Content-type":"application/json"},body:JSON.stringify({name:e.id,apiProducts:e.apiProductIds||[],...e.callbackUrl!==void 0?{callbackUrl:e.callbackUrl}:{},keyExpiresIn:1*365*24*60*60*1e3,attributes:v({...e.attributes,DisplayName:e.name,Notes:e.description||""})}),method:"POST"});if(e.credentials){const i=e.credentials[0];await this.fetchData(`${this.developerUrl}/apps/${e.id}/keys/create`,{headers:{"Content-type":"application/json"},body:JSON.stringify({consumerKey:i.clientId,consumerSecret:i.clientSecret,expiresInSeconds:P(i.expiresAt,$)}),method:"POST"}),n.info("Imported previously provided key");const r=a.credentials[0].consumerKey;await this.fetchData(`${this.developerUrl}/apps/${e.id}/keys/${r}`,{method:"DELETE"}),n.info("Deleted autogenerated key");const o=await this.fetchData(`${this.developerUrl}/apps/${e.id}/keys/${i.clientId}`,{headers:{"Content-type":"application/json"},body:JSON.stringify({apiProducts:e.apiProductIds||[]}),method:"POST"});a.credentials=[o]}return A(a)}async updateApp(e,t){const a=`${this.developerUrl}/apps/${e}`;try{const i=await this.getApp(e),r={...t.attributes};t.name&&(r.DisplayName=t.name),t.description&&(r.Notes=t.description);const o={attributes:v({...i.attributes,...r})};t.callbackUrl!==void 0&&(o.callbackUrl=t.callbackUrl);const d=await this.fetchData(a,{headers:{"Content-type":"application/json"},body:JSON.stringify(o),method:"PUT"});return A(d)}catch(i){if(i.message.includes("does not exist"))return;throw i}}async deleteApp(e){const t=`${this.developerUrl}/apps/${e}`;try{return await this.fetchData(t,{headers:{"Content-type":"application/json"},method:"DELETE"})}catch(a){if(a.message.includes("does not exist"))return;throw a}}async createCredential(e,t){const a=`${this.developerUrl}/apps/${e}`;let i;if(t.clientId&&t.clientSecret)await this.fetchData(`${this.developerUrl}/apps/${e}/keys/create`,{headers:{"Content-type":"application/json"},body:JSON.stringify({consumerKey:t.clientId,consumerSecret:t.clientSecret,expiresInSeconds:P(t.expiresAt,$)}),method:"POST"}),i=await this.fetchData(`${this.developerUrl}/apps/${e}/keys/${t.clientId}`,{headers:{"Content-type":"application/json"},body:JSON.stringify({apiProducts:t.apiProductIds||[]}),method:"POST"}),n.info("Imported previously provided key");else{const r=await this.getApp(e);i=(await this.fetchData(a,{headers:{"Content-type":"application/json"},method:"PUT",body:JSON.stringify({apiProducts:t.apiProductIds,attributes:v({...r.attributes,...t.attributes})})})).credentials[0]}return y(i)}async updateCredential(e,t,a){let i;try{i=await this.fetchData(`${this.developerUrl}/apps/${e}/keys/${t}`)}catch{i=void 0}if(!i)throw new b(404,"Cannot update credential that does not exist");const r=`${this.developerUrl}/apps/${e}/keys/${t}`,o=await this.fetchData(r,{headers:{"Content-type":"application/json"},method:"PUT",body:JSON.stringify({apiProducts:a.apiProductIds})}),d=o.apiProducts.filter(c=>!a.apiProductIds.includes(c.apiproduct)).map(c=>c.apiproduct);return await Promise.all(d.map(c=>this.fetchData(`${this.developerUrl}/apps/${e}/keys/${t}/apiproducts/${c}`,{method:"DELETE"}))),y(o)}async deleteCredential(e,t){const a=`${this.developerUrl}/apps/${e}/keys/${t}`;return y(await this.fetchData(a,{headers:{"Content-type":"application/octet-stream"},method:"DELETE"}))}async getAppLogDetails(e,t){throw new Error("Not implemented")}async getAppLogs(e,t){return{total:0,data:[]}}async getApiAccessStatus(e,t){const{data:a}=await this.getApps(),i=(a||[]).filter(p=>(p.credentials||[]).find(u=>u.apiProductsStatus.find(l=>l.id===e))),r=p=>i.find(g=>g.credentials?.find(l=>l.status===p&&l.apiProductsStatus.find(E=>E.id===e))),o=t?i.map(p=>{if(p.credentials?.find(u=>u.status==="approved"&&u.apiProductsStatus.find(l=>l.id===e)))return{id:p.id,title:p.name}}).filter(Boolean):void 0,d=r("approved");if(d)return{status:"ACCEPTED",appId:d.id,apps:o};const c=r("pending");return c?{status:"PENDING",appId:c.id,apps:o}:{status:"NONE"}}}function P(s,e){if(!(!s&&!e))return s=s||(Date.now()+e*1e3).toString(),Math.floor((parseInt(s,10)-Date.now())/1e3).toString()}export{F as ApigeeAdapter};
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{LRUCache as w}from"lru-cache";import{randomUUID as m}from"../../../../../utils/crypto/random-uuid.js";import{HTTP_METHOD_TO_QUERY_CODE as y}from"./constants.js";const h="developer.service.DeveloperDoesNotExist";function g(r,t){return{id:r.id,name:r.name,description:r.description,attributes:{},createdAt:Date.parse(r.created_at).toString(),lastModifiedAt:Date.parse(r.updated_at).toString(),scopes:[],credentials:t||[],clientId:r.settings?.app?.client_id||r.settings?.oauth?.client_id||void 0,apiProductIds:t?.flatMap(e=>e.apiProductIds||[])||[],canCreateKey:!t?.length,supportsLogs:!0}}function E({id:r,method:t,path:e,responseTime:s,status:a,timestamp:i,api:n}){return{id:r,timestamp:i.toString(),path:e,method:t,statusCode:a,responseTime:s,apiId:n}}function P({id:r,timestamp:t,metadata:e,status:s,requestContentLength:a,responseContentLength:i,request:n,response:c,path:d}){const o=Object.values(e).find(p=>p.ip)?.ip;return{id:r,timestamp:t.toString(),path:d,ipAddress:o,statusCode:s,request:{contentLength:a,body:n?.body,headers:n?.headers||{}},response:{contentLength:i,body:c?.body,headers:c?.headers||{}}}}function D(r){if(!r.apis?.length&&!r.methods?.length&&!r.statusCodes?.length)return;const t=[];return r.apis?.length&&t.push(`api:(${r.apis.join(" OR ")})`),r.methods?.length&&t.push(`method:(${r.methods.map(e=>y[e]).join(" OR ")})`),r.statusCodes?.length&&t.push(`status:(${r.statusCodes.join(" OR ")})`),t.join(" AND ")}function b({page:r,size:t,fromDate:e,toDate:s,order:a,filters:i}){return{page:r,size:t||50,from:e||Date.now()-1e3*60*60*24*90,to:s||Date.now(),order:a||"DESC",query:D(i)}}function l(r){switch(r){case"ACCEPTED":return"approved";case"REJECTED":case"PAUSED":return"revoked";case"PENDING":case"CLOSED":return"pending";default:throw new Error(`Unknown status: ${r}`)}}function S(r){return{id:r.id,name:r.name,description:r.description,attributes:{},createdAt:r.created_at?Date.parse(r.created_at).toString():"",lastModifiedAt:r.updated_at?Date.parse(r.updated_at).toString():"",scopes:[]}}const f=new w({max:1e4});async function $(r,t){console.log("Exchanging IdP token for new Gravitee token");
|
|
2
|
-
${await e.text()}`);console.log("Exchanged successfully");const s=await e.json(),{token:a,expires_in:i=3600*48}=s;return{token:a,expiresAt:Math.floor(Date.now()/1e3)+i}}async function T(r,t,e){if(!r.auth)return;if("static"in r.auth)return r.auth?.static;if(!e)throw new Error("No access token provided");let s=f.get(e);return(!s||(await s).expiresAt<Date.now()/1e3)&&(s=$(t,e).catch(a=>{throw f.delete(e),a}),f.set(e,s)),(await s).token}class U{apiUrl;accessToken;email;userClaims;config;catalogApiProducts;allowApiProductsOutsideCatalog;adapterId="";stage="";constructor(t,e,s,a){this.config=t,this.apiUrl=`${this.config.apiBaseUrl}/portal/environments/${this.config.env||"DEFAULT"}`,this.email=e.email,this.userClaims=e,this.accessToken=s,this.stage=t.stage||"non-production",this.catalogApiProducts=new Map(Object.entries(a)),this.allowApiProductsOutsideCatalog=t.allowApiProductsOutsideCatalog??!1}async setAuthHeader(t){return t=t||{},t.headers={...t.headers,"Accept-Encoding":"identity",accept:"application/json",Authorization:"Bearer "+await T(this.config,this.apiUrl,this.accessToken)},t}getErrorMessage(t){if(!t)return"Fetch error";try{const e=JSON.parse(t);return e.code===h?e.code:e.error.details[0]?.["@type"]==="type.googleapis.com/google.rpc.PreconditionFailure"&&e.error.details[0]?.violations[0]?.type===h?h:e?.message||e.error.message}catch{return t}}async fetchData(t,e){const s=await this.setAuthHeader(e),a=await fetch(t,s);if(!a.ok){const i=await a.json();throw new Error(i.message||i?.errors?.[0]?.message)}return a.json()}async fetchAppCredentials(t,e=!1){const s=[],a=await this.fetchData(`${this.apiUrl}/subscriptions?applicationId=${t.id}&size=-1&statuses=ACCEPTED&statuses=PAUSED&statuses=PENDING`),i=a.data[0],n=t.api_key_mode==="SHARED"?i?[i]:[]:a.data;return await Promise.all(n.map(async c=>{const d=await this.fetchData(`${this.apiUrl}/subscriptions/${c.id}?include=keys`);d.keys?.length||(s.push({id:d.id,expiresAt:"-1",issuedAt:"-1",canBeRolled:!0,canBeRevoked:!1,clientSecret:"",attributes:{},status:l(i.status),apiProductsStatus:t.api_key_mode==="SHARED"?a.data.map(o=>({id:o.id,apiId:o.api,name:a.metadata[o.api].name,status:l(o.status)})):[{id:c.id,apiId:c.api,name:a.metadata[c.api].name,status:l(c.status)}]}),s[s.length-1].apiProductIds=s[s.length-1].apiProductsStatus.map(o=>o.apiId));for(const o of d.keys||[])o.expired||o.revoked&&!e||(s.push({id:o.key,expiresAt:o.expire_at?Date.parse(o.expire_at).toString():"-1",canBeRolled:o.expire_at==null,canBeRevoked:!1,issuedAt:Date.parse(o.created_at).toString(),clientSecret:o.key,attributes:{},status:l(i.status),apiProductsStatus:t.api_key_mode==="SHARED"?a.data.map(p=>({id:p.id,apiId:p.api,name:a.metadata[p.api].name,status:l(p.status)})):o.subscriptions.map(p=>({id:c.id,apiId:p.api,name:a.metadata[p.api].name,status:l(c.status)}))}),s[s.length-1].apiProductIds=s[s.length-1].apiProductsStatus.map(p=>p.apiId))})),s}async unsubscribeFromApis(t,e){const s=await this.getApp(t),a=[],i=await this.setAuthHeader({});return e.map(n=>{const c=s.credentials.find(u=>u.apiProductIds?.includes(n)),d=c?.apiProductIds?.findIndex(u=>u===n),o=c?.apiProductsStatus[d??-1]?.id;if(!o)throw new Error("Not found");const p=`${this.apiUrl}/subscriptions/${o}/_close`;a.push(fetch(p,{...i,method:"POST"}))}),Promise.all(a)}async subscribeToApis(t,e){return Promise.all(e.map(async s=>{const a=await this.fetchData(`${this.apiUrl}/apis/${s}/plans?size=-1`),i=a.data.find(n=>n.security==="API_KEY"&&n.validation=="AUTO")||a.data.find(n=>n.security==="API_KEY")||a.data[0];if(!i)throw new Error("No plan found");return this.fetchData(`${this.apiUrl}/subscriptions`,{headers:{"Content-type":"application/json"},body:JSON.stringify({application:t,plan:i.id,request:""}),method:"POST"})}))}async getApps(){const t=`${this.apiUrl}/applications?size=-1`,e=await this.fetchData(t),{data:s}=e,a=(s||[]).map(i=>g(i));return{data:a,total:a.length}}async getApiProducts(){const t=`${this.apiUrl}/apis?size=-1`,e=await this.fetchData(t),{data:s}=e,a=(s||[]).filter(i=>this.allowApiProductsOutsideCatalog||this.catalogApiProducts.has(i.name)).map(i=>S(i));return{data:a,total:a.length}}async getApp(t){const e=`${this.apiUrl}/applications/${t}`,s=await this.fetchData(e)
|
|
1
|
+
import{LRUCache as w}from"lru-cache";import{randomUUID as m}from"../../../../../utils/crypto/random-uuid.js";import{HTTP_METHOD_TO_QUERY_CODE as y}from"./constants.js";const h="developer.service.DeveloperDoesNotExist";function g(r,t){return{id:r.id,name:r.name,description:r.description,attributes:{},createdAt:Date.parse(r.created_at).toString(),lastModifiedAt:Date.parse(r.updated_at).toString(),scopes:[],credentials:t||[],clientId:r.settings?.app?.client_id||r.settings?.oauth?.client_id||void 0,apiProductIds:t?.flatMap(e=>e.apiProductIds||[])||[],canCreateKey:!t?.length,supportsLogs:!0}}function E({id:r,method:t,path:e,responseTime:s,status:a,timestamp:i,api:n}){return{id:r,timestamp:i.toString(),path:e,method:t,statusCode:a,responseTime:s,apiId:n}}function P({id:r,timestamp:t,metadata:e,status:s,requestContentLength:a,responseContentLength:i,request:n,response:c,path:d}){const o=Object.values(e).find(p=>p.ip)?.ip;return{id:r,timestamp:t.toString(),path:d,ipAddress:o,statusCode:s,request:{contentLength:a,body:n?.body,headers:n?.headers||{}},response:{contentLength:i,body:c?.body,headers:c?.headers||{}}}}function D(r){if(!r.apis?.length&&!r.methods?.length&&!r.statusCodes?.length)return;const t=[];return r.apis?.length&&t.push(`api:(${r.apis.join(" OR ")})`),r.methods?.length&&t.push(`method:(${r.methods.map(e=>y[e]).join(" OR ")})`),r.statusCodes?.length&&t.push(`status:(${r.statusCodes.join(" OR ")})`),t.join(" AND ")}function b({page:r,size:t,fromDate:e,toDate:s,order:a,filters:i}){return{page:r,size:t||50,from:e||Date.now()-1e3*60*60*24*90,to:s||Date.now(),order:a||"DESC",query:D(i)}}function l(r){switch(r){case"ACCEPTED":return"approved";case"REJECTED":case"PAUSED":return"revoked";case"PENDING":case"CLOSED":return"pending";default:throw new Error(`Unknown status: ${r}`)}}function S(r){return{id:r.id,name:r.name,description:r.description,attributes:{},createdAt:r.created_at?Date.parse(r.created_at).toString():"",lastModifiedAt:r.updated_at?Date.parse(r.updated_at).toString():"",scopes:[]}}const f=new w({max:1e4});async function $(r,t){console.log("Exchanging IdP token for new Gravitee token");const e=await fetch(`${r}/auth/oauth2/gravitee-am-oidc/_exchange?token=`+t,{method:"POST",headers:{Accept:"application/json"}});if(!e.ok)throw new Error(`Failed to get access token: ${e.statusText}
|
|
2
|
+
${await e.text()}`);console.log("Exchanged successfully");const s=await e.json(),{token:a,expires_in:i=3600*48}=s;return{token:a,expiresAt:Math.floor(Date.now()/1e3)+i}}async function T(r,t,e){if(!r.auth)return;if("static"in r.auth)return r.auth?.static;if(!e)throw new Error("No access token provided");let s=f.get(e);return(!s||(await s).expiresAt<Date.now()/1e3)&&(s=$(t,e).catch(a=>{throw f.delete(e),a}),f.set(e,s)),(await s).token}class U{apiUrl;accessToken;email;userClaims;config;catalogApiProducts;allowApiProductsOutsideCatalog;adapterId="";stage="";constructor(t,e,s,a){this.config=t,this.apiUrl=`${this.config.apiBaseUrl}/portal/environments/${this.config.env||"DEFAULT"}`,this.email=e.email,this.userClaims=e,this.accessToken=s,this.stage=t.stage||"non-production",this.catalogApiProducts=new Map(Object.entries(a)),this.allowApiProductsOutsideCatalog=t.allowApiProductsOutsideCatalog??!1}async setAuthHeader(t){return t=t||{},t.headers={...t.headers,"Accept-Encoding":"identity",accept:"application/json",Authorization:"Bearer "+await T(this.config,this.apiUrl,this.accessToken)},t}getErrorMessage(t){if(!t)return"Fetch error";try{const e=JSON.parse(t);return e.code===h?e.code:e.error.details[0]?.["@type"]==="type.googleapis.com/google.rpc.PreconditionFailure"&&e.error.details[0]?.violations[0]?.type===h?h:e?.message||e.error.message}catch{return t}}async fetchData(t,e){const s=await this.setAuthHeader(e),a=await fetch(t,s);if(!a.ok){const i=await a.json();throw new Error(i.message||i?.errors?.[0]?.message)}return a.json()}async fetchAppCredentials(t,e=!1){const s=[],a=await this.fetchData(`${this.apiUrl}/subscriptions?applicationId=${t.id}&size=-1&statuses=ACCEPTED&statuses=PAUSED&statuses=PENDING`),i=a.data[0],n=t.api_key_mode==="SHARED"?i?[i]:[]:a.data;return await Promise.all(n.map(async c=>{const d=await this.fetchData(`${this.apiUrl}/subscriptions/${c.id}?include=keys`);d.keys?.length||(s.push({id:d.id,expiresAt:"-1",issuedAt:"-1",canBeRolled:!0,canBeRevoked:!1,clientSecret:"",attributes:{},status:l(i.status),apiProductsStatus:t.api_key_mode==="SHARED"?a.data.map(o=>({id:o.id,apiId:o.api,name:a.metadata[o.api].name,status:l(o.status)})):[{id:c.id,apiId:c.api,name:a.metadata[c.api].name,status:l(c.status)}]}),s[s.length-1].apiProductIds=s[s.length-1].apiProductsStatus.map(o=>o.apiId));for(const o of d.keys||[])o.expired||o.revoked&&!e||(s.push({id:o.key,expiresAt:o.expire_at?Date.parse(o.expire_at).toString():"-1",canBeRolled:o.expire_at==null,canBeRevoked:!1,issuedAt:Date.parse(o.created_at).toString(),clientSecret:o.key,attributes:{},status:l(i.status),apiProductsStatus:t.api_key_mode==="SHARED"?a.data.map(p=>({id:p.id,apiId:p.api,name:a.metadata[p.api].name,status:l(p.status)})):o.subscriptions.map(p=>({id:c.id,apiId:p.api,name:a.metadata[p.api].name,status:l(c.status)}))}),s[s.length-1].apiProductIds=s[s.length-1].apiProductsStatus.map(p=>p.apiId))})),s}async unsubscribeFromApis(t,e){const s=await this.getApp(t),a=[],i=await this.setAuthHeader({});return e.map(n=>{const c=s.credentials.find(u=>u.apiProductIds?.includes(n)),d=c?.apiProductIds?.findIndex(u=>u===n),o=c?.apiProductsStatus[d??-1]?.id;if(!o)throw new Error("Not found");const p=`${this.apiUrl}/subscriptions/${o}/_close`;a.push(fetch(p,{...i,method:"POST"}))}),Promise.all(a)}async subscribeToApis(t,e){return Promise.all(e.map(async s=>{const a=await this.fetchData(`${this.apiUrl}/apis/${s}/plans?size=-1`),i=a.data.find(n=>n.security==="API_KEY"&&n.validation=="AUTO")||a.data.find(n=>n.security==="API_KEY")||a.data[0];if(!i)throw new Error("No plan found");return this.fetchData(`${this.apiUrl}/subscriptions`,{headers:{"Content-type":"application/json"},body:JSON.stringify({application:t,plan:i.id,request:""}),method:"POST"})}))}async getApps(){const t=`${this.apiUrl}/applications?size=-1`,e=await this.fetchData(t),{data:s}=e,a=(s||[]).map(i=>g(i));return{data:a,total:a.length}}async getApiProducts(){const t=`${this.apiUrl}/apis?size=-1`,e=await this.fetchData(t),{data:s}=e,a=(s||[]).filter(i=>this.allowApiProductsOutsideCatalog||this.catalogApiProducts.has(i.name)).map(i=>S(i));return{data:a,total:a.length}}async getApp(t){const e=`${this.apiUrl}/applications/${t}`,s=await this.fetchData(e),a=await this.fetchAppCredentials(s);return g(s,a)}async createApp(t){const e=`${this.apiUrl}/applications`;if(!t.apiProductIds||!t.apiProductIds.length)throw new Error("At least one API Product is required");const s=await this.fetchData(e,{headers:{"Content-type":"application/json"},body:JSON.stringify({name:t.name,description:t.description||"",domain:t.attributes?.domain||null,picture:t.attributes?.picture||null,api_key_mode:"SHARED",background:void 0,settings:{app:{type:t.attributes?.appType||"",client_id:t.attributes?.clientId||m()}}}),method:"POST"});if(await this.subscribeToApis(s.id,t.apiProductIds||[]),t.credentials)throw new Error("Gravitee adapter does not support manual credentials");return this.getApp(s.id)}async getAppLogDetails(t,e){const s=`${this.apiUrl}/applications/${t}/logs/${e}`,a=await this.fetchData(s);return P(a)}async getAppLogs(t,e){const s=new URL(`${this.apiUrl}/applications/${t}/logs`),a=b(e);Object.keys(a).forEach(n=>{a[n]&&s.searchParams.append(n,a[n])});const i=await this.fetchData(s.toString());return{total:i.metadata.data.total,data:i.data.map(E)}}async updateApp(t,e){const s=`${this.apiUrl}/applications/${t}`,a=await this.getApp(t),i=await this.fetchData(s,{headers:{"Content-type":"application/json"},body:JSON.stringify({id:t,name:e.name||a.name,description:e.description||a.description||"",domain:e.attributes?.domain||a.attributes?.domain||null,picture:e.attributes?.picture||a.attributes?.picture||null,api_key_mode:"SHARED",background:void 0,settings:{app:{type:e.attributes?.appType||a.attributes?.appType||"",client_id:e.attributes?.clientId||a.attributes?.clientId||m()}}}),method:"PUT"});return this.getApp(i.id)}async deleteApp(t){const e=`${this.apiUrl}/applications/${t}`;await this.fetchData(e,{method:"DELETE"})}async createCredential(t,e){const s=await this.getApp(t),a=new Set(e.apiProductIds.filter(c=>!(s.apiProductIds||[]).includes(c))),i=new Set((s.apiProductIds||[]).filter(c=>!e.apiProductIds.includes(c)));return await this.subscribeToApis(t,Array.from(a)),await this.unsubscribeFromApis(t,Array.from(i)),(await this.getApp(t)).credentials[0]}async updateCredential(t,e,s){if(s.apiProductIds)return this.createCredential(t,s);const a=`${this.apiUrl}/applications/${t}`,i=await this.fetchData(a);let n;if(i.api_key_mode==="SHARED")n=`${this.apiUrl}/applications/${t}/keys/_renew`;else{const p=(await this.fetchAppCredentials(i)).find(A=>A.id===e);if(!p)throw new Error("Not found!");const u=p.apiProductsStatus[0].id;n=`${this.apiUrl}/subscriptions/${u}/keys/_renew`}const c=await fetch(n,await this.setAuthHeader({method:"POST"}));if(!c.ok)throw new Error(`Failed to renew the key: ${c.statusText}`);return(await this.fetchAppCredentials(i,!0)).find(o=>o.id===e)}async deleteCredential(t,e){const s=`${this.apiUrl}/applications/${t}`,a=await this.fetchData(s);let i;if(a.api_key_mode==="SHARED")i=`${this.apiUrl}/applications/${t}/keys/${e}/_revoke`;else{const o=(await this.fetchAppCredentials(a)).find(u=>u.id===e);if(!o)throw new Error("Not found!");const p=o.apiProductsStatus[0].id;i=`${this.apiUrl}/subscriptions/${p}/keys/${e}/_revoke`}const n=await fetch(i,await this.setAuthHeader({method:"POST"}));if(!n.ok)throw new Error(`Failed to remove the key: ${n.statusText}`);return(await this.fetchAppCredentials(a,!0)).find(d=>d.id===e)}async getApiAccessStatus(t,e){const s=`${this.apiUrl}/subscriptions?apiId=${t}&size=-1&statuses=ACCEPTED&statuses=PENDING`,a=await this.fetchData(s),i=e?a.data.map(d=>{if(d.status==="ACCEPTED")return{id:d.application,title:a.metadata[d.application]?.name||d.application}}).filter(Boolean):void 0,n=a.data.find(d=>d.status==="ACCEPTED");if(n)return{status:"ACCEPTED",appId:n.application,apps:i};const c=a.data.find(d=>d.status==="PENDING");return c?{status:"PENDING",appId:c.application,apps:i}:{status:"NONE"}}}export{U as GraviteeAdapter};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{isDefined as h}from"../../../../utils/guards/is-defined.js";import{unique as S}from"../../../../utils/array/unique.js";import{logger as C}from"../../../tools/notifiers/logger.js";import{addOrgToId as E,joinOrgsInIds as $,parseCombinedId as w}from"../utils.js";class D{adapters;adapterId="apigee-combined";constructor(e){this.adapters=e}async getApps(e){const a=(await Promise.all(this.adapters.map(t=>t.getApps(e)))).flatMap(t=>t.data),r={};for(const t of a)r[t.id]=s(t,r[t.id]);const i=Object.values(r);return{data:i.slice(0,e?.limit||i.length),total:i.length};function s(t,d){return{...t,...d,attributes:{...t.attributes,...d?.attributes},scopes:[...t.scopes||[],...d?.scopes||[]]}}}async getApp(e){const a=(await Promise.all(this.adapters.map(async s=>{try{const t=await s.getApp(e);return{...t,credentials:t.credentials?.map(d=>({...d,stage:s.stage,apiProductsStatus:d.apiProductsStatus.map(u=>({...u,id:E(u.id,s.adapterId)}))}))||[],_adapterIds:[s.adapterId]}}catch(t){if(t.status===404||t.message.includes("does not exist"))return;throw t}}))).filter(h);let r=a[0];for(const s of a.slice(1))r=i(s,r);return r;function i(s,t){return{...s,...t,attributes:{...s.attributes,...t?.attributes},_adapterIds:S([...s._adapterIds||[],...t?._adapterIds||[]]),scopes:[...s.scopes||[],...t?.scopes||[]],credentials:N(s.credentials,t?.credentials)}}}async getApiProducts(e){const a=(await Promise.all(this.adapters.map(async t=>{const d=await t.getApiProducts(e);return{...d,data:d.data.map(u=>({...u,id:E(u.id,t.adapterId)}))}}))).flatMap(t=>t.data),r={};for(const t of a){const{id:d}=w(t.id);r[d]=s(t,r[d])}const i=Object.values(r);return{data:i.slice(0,e?.limit||i.length),total:i.length};function s(t,d){return{...t,...d,id:$(t.id,d?.id),attributes:{...t.attributes,...d?.attributes},scopes:S([...t.scopes||[],...d?.scopes||[]])}}}async createApp(e){const a=e.apiProductIds?.map(c=>w(c))||[],r=new Set(a.map(({adapterIds:c})=>c).flat()),i=this.adapters.filter(c=>r.has(c.adapterId)),s=i.filter(c=>c.stage==="production"),t=i.filter(c=>c.stage!=="production");return(await Promise.all([u(s,"production"),u(t,"non-production")])).flat().filter(h)[0];async function u(c,A){if(c.length===0)return;const[I,...o]=c,n=await I.createApp(P(e,I)),p={...e,credentials:e.credentials||n.credentials};return C.info(`Created first app for ${A}`),await Promise.all(o.map(l=>l.createApp(P(p,l)))),C.info(`Created apps for ${A}`),n}function P(c,A){const I=c.apiProductIds?.map(o=>{const{id:n,adapterIds:p}=w(o);if(p.includes(A.adapterId))return n}).filter(h)||[];return{...c,apiProductIds:I}}}async getApiAccessStatus(e,a){const r=await Promise.all(this.adapters.map(async t=>{try{return await t.getApiAccessStatus(e,a)}catch(d){const u=d.message.toLowerCase();if(u.includes("does not exist")||u.includes("not found"))return{status:"NONE"};throw d}})),i=r.find(t=>t.status==="ACCEPTED");if(i)return i;const s=r.find(t=>t.status==="PENDING");return s||{status:"NONE"}}async getAppLogDetails(e,a){const r=(await Promise.all(this.adapters.map(async i=>{try{return await i.getAppLogDetails(e,a)}catch(s){if(s.message.includes("does not exist"))return;throw s}}))).filter(h);if(r.length>0)return r[0];throw new Error("Not found")}async getAppLogs(e,a){const r=(await Promise.all(this.adapters.map(async i=>{try{return await i.getAppLogs(e,a)}catch(s){if(s.message.includes("does not exist"))return;throw s}}))).filter(h);return r.length>0?r[0]:{data:[],total:0}}async createCredential(e,a){const r=a.apiProductIds?.map(n=>w(n))||[],i=new Set(r.map(({adapterIds:n})=>n).flat()),s=this.adapters.filter(n=>i.has(n.adapterId)),t=s.filter(n=>n.stage==="production"),d=s.filter(n=>n.stage!=="production"),u=await this.getApp(e),P=u._adapterIds||[];return(await Promise.all([A(t,"production"),A(d,"non-production")])).flat()[0];async function A(n,p){if(n.length===0)return;const l=n.find(b=>P.includes(b.adapterId))||n[0],f=n.filter(b=>b!==l)
|
|
1
|
+
import{isDefined as h}from"../../../../utils/guards/is-defined.js";import{unique as S}from"../../../../utils/array/unique.js";import{logger as C}from"../../../tools/notifiers/logger.js";import{addOrgToId as E,joinOrgsInIds as $,parseCombinedId as w}from"../utils.js";class D{adapters;adapterId="apigee-combined";constructor(e){this.adapters=e}async getApps(e){const a=(await Promise.all(this.adapters.map(t=>t.getApps(e)))).flatMap(t=>t.data),r={};for(const t of a)r[t.id]=s(t,r[t.id]);const i=Object.values(r);return{data:i.slice(0,e?.limit||i.length),total:i.length};function s(t,d){return{...t,...d,attributes:{...t.attributes,...d?.attributes},scopes:[...t.scopes||[],...d?.scopes||[]]}}}async getApp(e){const a=(await Promise.all(this.adapters.map(async s=>{try{const t=await s.getApp(e);return{...t,credentials:t.credentials?.map(d=>({...d,stage:s.stage,apiProductsStatus:d.apiProductsStatus.map(u=>({...u,id:E(u.id,s.adapterId)}))}))||[],_adapterIds:[s.adapterId]}}catch(t){if(t.status===404||t.message.includes("does not exist"))return;throw t}}))).filter(h);let r=a[0];for(const s of a.slice(1))r=i(s,r);return r;function i(s,t){return{...s,...t,attributes:{...s.attributes,...t?.attributes},_adapterIds:S([...s._adapterIds||[],...t?._adapterIds||[]]),scopes:[...s.scopes||[],...t?.scopes||[]],credentials:N(s.credentials,t?.credentials)}}}async getApiProducts(e){const a=(await Promise.all(this.adapters.map(async t=>{const d=await t.getApiProducts(e);return{...d,data:d.data.map(u=>({...u,id:E(u.id,t.adapterId)}))}}))).flatMap(t=>t.data),r={};for(const t of a){const{id:d}=w(t.id);r[d]=s(t,r[d])}const i=Object.values(r);return{data:i.slice(0,e?.limit||i.length),total:i.length};function s(t,d){return{...t,...d,id:$(t.id,d?.id),attributes:{...t.attributes,...d?.attributes},scopes:S([...t.scopes||[],...d?.scopes||[]])}}}async createApp(e){const a=e.apiProductIds?.map(c=>w(c))||[],r=new Set(a.map(({adapterIds:c})=>c).flat()),i=this.adapters.filter(c=>r.has(c.adapterId)),s=i.filter(c=>c.stage==="production"),t=i.filter(c=>c.stage!=="production");return(await Promise.all([u(s,"production"),u(t,"non-production")])).flat().filter(h)[0];async function u(c,A){if(c.length===0)return;const[I,...o]=c,n=await I.createApp(P(e,I)),p={...e,credentials:e.credentials||n.credentials};return C.info(`Created first app for ${A}`),await Promise.all(o.map(l=>l.createApp(P(p,l)))),C.info(`Created apps for ${A}`),n}function P(c,A){const I=c.apiProductIds?.map(o=>{const{id:n,adapterIds:p}=w(o);if(p.includes(A.adapterId))return n}).filter(h)||[];return{...c,apiProductIds:I}}}async getApiAccessStatus(e,a){const r=await Promise.all(this.adapters.map(async t=>{try{return await t.getApiAccessStatus(e,a)}catch(d){const u=d.message.toLowerCase();if(u.includes("does not exist")||u.includes("not found"))return{status:"NONE"};throw d}})),i=r.find(t=>t.status==="ACCEPTED");if(i)return i;const s=r.find(t=>t.status==="PENDING");return s||{status:"NONE"}}async getAppLogDetails(e,a){const r=(await Promise.all(this.adapters.map(async i=>{try{return await i.getAppLogDetails(e,a)}catch(s){if(s.message.includes("does not exist"))return;throw s}}))).filter(h);if(r.length>0)return r[0];throw new Error("Not found")}async getAppLogs(e,a){const r=(await Promise.all(this.adapters.map(async i=>{try{return await i.getAppLogs(e,a)}catch(s){if(s.message.includes("does not exist"))return;throw s}}))).filter(h);return r.length>0?r[0]:{data:[],total:0}}async createCredential(e,a){const r=a.apiProductIds?.map(n=>w(n))||[],i=new Set(r.map(({adapterIds:n})=>n).flat()),s=this.adapters.filter(n=>i.has(n.adapterId)),t=s.filter(n=>n.stage==="production"),d=s.filter(n=>n.stage!=="production"),u=await this.getApp(e),P=u._adapterIds||[];return(await Promise.all([A(t,"production"),A(d,"non-production")])).flat()[0];async function A(n,p){if(n.length===0)return;const l=n.find(b=>P.includes(b.adapterId))||n[0],f=n.filter(b=>b!==l),m=await I(l,a);if(!m)throw new Error("Failed to create credential");const y={...a,clientId:m.clientId,clientSecret:m.clientSecret};return C.info(`Created first credential for ${p}`),await Promise.all(f.map(async b=>await I(b,y))),C.info(`Created rest of the credentials for ${p}`),m}async function I(n,p){if(!P.includes(n.adapterId)){const l=o(p,n);return(await n.createApp({...u,apiProductIds:l.apiProductIds,credentials:p.clientId?[l]:void 0}))?.credentials?.[0]}return n.createCredential(e,o(p,n))}function o(n,p){const l=n.apiProductIds?.map(f=>{const{id:m,adapterIds:y}=w(f);if(y.includes(p.adapterId))return m}).filter(h)||[];return{...n,apiProductIds:l}}}async updateCredential(e,a,r){const i=this.adapters,s=i.filter(o=>o.stage==="production"),t=i.filter(o=>o.stage!=="production"),d=await this.getApp(e),u=d._adapterIds||[],P=d.credentials.find(o=>o.id===a);if(!P)throw new Error("Credential not found");return await(P.stage==="production"?A(s,"production"):A(t,"non-production"));async function A(o,n){if(o.length===0)return;const p=(await Promise.all(o.map(async f=>{const m=I(r,f);if(!u.includes(f.adapterId))return m.apiProductIds.length?(C.info(`Creating app for ${f.adapterId} for ${n}`),(await f.createApp({...d,apiProductIds:m.apiProductIds,credentials:[m]}))?.credentials?.[0]):void 0;try{return C.info(`Updating existing credential for ${f.adapterId} for ${n}`),f.updateCredential(e,a,m)}catch(y){if(y.status!==404)throw y}}))).filter(h);let l=p[0];for(const f of p.slice(1))l=v(l,f);return l}function I(o,n){const p=S(o.apiProductIds?.map(l=>{const{id:f,adapterIds:m}=w(l);if(m.includes(n.adapterId))return f}).filter(h)||[]);return{...o,apiProductIds:p}}}async deleteCredential(e,a){const r=this.adapters,i=(await Promise.all(r.map(async t=>{try{return await t.deleteCredential(e,a)}catch(d){if(d.status===404||d.message.match(/invalid consumer key/i))return;throw d}}))).filter(h);let s=i[0];for(const t of i.slice(1))s=v(s,t);return s}async deleteApp(e){const a=this.adapters;await Promise.all(a.map(r=>r.deleteApp(e)))}async updateApp(e,a){const r=this.adapters;return(await Promise.all(r.map(s=>s.updateApp(e,a)))).filter(Boolean)[0]}}function x(g){const e={};for(const a of g){const{id:r}=w(a.id);e[r]={...a,...e[a.id],status:O(a.status,e[a.id]?.status),id:r}}return Object.values(e)}function O(g,e){return g==="revoked"||e==="revoked"?"revoked":g==="pending"||e==="pending"?"pending":"approved"}function N(g,e){const a={};for(const r of[...g,...e||[]]){const{id:i}=w(r.id);a[i]=v(r,a[i])}return Object.values(a)}function v(g,e){return{...g,...e,status:O(g.status,e?.status),apiProductsStatus:x([...g.apiProductsStatus||[],...e?.apiProductsStatus||[]])}}export{D as CombineAdapter};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import*as t from"react";import
|
|
1
|
+
import*as t from"react";import a from"styled-components";import{Flex as l}from"@redocly/portal-legacy-ui";import{WarningAltIcon as n}from"@redocly/theme/icons/WarningAltIcon/WarningAltIcon";import s from"./ApiKeyRow";import c from"./CreatedAtRow";import m from"./ExpiresAtRow";import p from"./RevokeAPIKey";import d from"./RollAPIKey";import x from"./SecretRow";import f from"./StageRow";import u from"./StatusRow";function g(r){const{apiKey:e}=r,[i]=t.useState(()=>Date.now()),o=Number(e.expiresAt)>0&&Math.abs(Number(e.expiresAt)-i)<1440*60*1e3;return t.createElement(l,{flexDirection:"column",flexGrow:1},o&&t.createElement(E,null,t.createElement("div",null,"Expires soon"),t.createElement(n,{size:"24px",color:"#C8102E"})),t.createElement(v,{borderColor:o?"var(--color-error-border)":e.stage==="production"?"var(--color-success-border)":""},e.stage&&t.createElement(f,{stage:e.stage})||null,e.clientId&&t.createElement(s,{apiKey:e.clientId})||null,e.clientSecret&&t.createElement(x,{secret:e.clientSecret,hasClientId:!!e.clientId})||null,e.status&&t.createElement(u,{status:e.status})||null,t.createElement(c,{createdAt:e.issuedAt}),t.createElement(m,{expiresAt:e.expiresAt,expiresSoon:o})),e.canBeRolled&&t.createElement(d,{apiKey:e}),e.canBeRevoked&&t.createElement(p,{apiKey:e}))}const v=a.div`
|
|
2
2
|
display: flex;
|
|
3
3
|
flex-direction: column;
|
|
4
4
|
|
|
@@ -9,7 +9,7 @@ import*as t from"react";import i from"styled-components";import{Flex as a}from"@
|
|
|
9
9
|
> :not(:last-child) {
|
|
10
10
|
border-bottom: 1px solid var(--border-color-primary);
|
|
11
11
|
}
|
|
12
|
-
`,
|
|
12
|
+
`,E=a.div`
|
|
13
13
|
display: flex;
|
|
14
14
|
gap: var(--spacing-xs);
|
|
15
15
|
font-weight: var(--font-weight-regular);
|
|
@@ -20,4 +20,4 @@ import*as t from"react";import i from"styled-components";import{Flex as a}from"@
|
|
|
20
20
|
width: 18px;
|
|
21
21
|
height: 18px;
|
|
22
22
|
}
|
|
23
|
-
`;export{
|
|
23
|
+
`;export{g as default};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import*as e from"react";import{Flex as i}from"@redocly/portal-legacy-ui";import{H2 as m}from"@redocly/theme/components/Typography/H2";import{Dropdown as l}from"@redocly/theme/components/Dropdown/Dropdown";import{DropdownMenu as p}from"@redocly/theme/components/Dropdown/DropdownMenu";import{OverflowMenuHorizontalIcon as c}from"@redocly/theme/icons/OverflowMenuHorizontalIcon/OverflowMenuHorizontalIcon";import{Button as s}from"@redocly/theme/components/Button/Button";import{useTranslate as u}from"../../../../../client/app/hooks";import{DeleteAppDialog as d}from"./DeleteAppDialog";import{EditAppDialog as f}from"./EditAppDialog";function g(o){const r=e.useRef(null),t=e.useRef(null),{app:n}=o,{translate:a}=u();return e.createElement(i,{alignItems:"flex-start",justifyContent:"space-between",mb:"1.5rem"},e.createElement("div",null,e.createElement(m,{style:{marginBottom:"0.5rem"}},n.name)),e.createElement(l,{trigger:e.createElement(s,{variant:"text",icon:e.createElement(c,{size:"24px"})}),alignment:"end"},e.createElement(p,{items:[{onAction:()=>r.current.open(),content:a("dev.app.edit","Edit"),dataAttributes:{"data-translation-key":"dev.app.edit"}},{onAction:()=>t.current.open(),content:a("dev.app.delete","Delete"),dataAttributes:{"data-translation-key":"dev.app.delete"}}]})),e.createElement(f,{ref:r,appName:n.name,appDisplayName:n.name}),e.createElement(d,{ref:t}))}function R(o){const r={day:"numeric",month:"short",year:"numeric"},t=new Date(parseInt(o,10))
|
|
1
|
+
import*as e from"react";import{Flex as i}from"@redocly/portal-legacy-ui";import{H2 as m}from"@redocly/theme/components/Typography/H2";import{Dropdown as l}from"@redocly/theme/components/Dropdown/Dropdown";import{DropdownMenu as p}from"@redocly/theme/components/Dropdown/DropdownMenu";import{OverflowMenuHorizontalIcon as c}from"@redocly/theme/icons/OverflowMenuHorizontalIcon/OverflowMenuHorizontalIcon";import{Button as s}from"@redocly/theme/components/Button/Button";import{useTranslate as u}from"../../../../../client/app/hooks";import{DeleteAppDialog as d}from"./DeleteAppDialog";import{EditAppDialog as f}from"./EditAppDialog";function g(o){const r=e.useRef(null),t=e.useRef(null),{app:n}=o,{translate:a}=u();return e.createElement(i,{alignItems:"flex-start",justifyContent:"space-between",mb:"1.5rem"},e.createElement("div",null,e.createElement(m,{style:{marginBottom:"0.5rem"}},n.name)),e.createElement(l,{trigger:e.createElement(s,{variant:"text",icon:e.createElement(c,{size:"24px"})}),alignment:"end"},e.createElement(p,{items:[{onAction:()=>r.current.open(),content:a("dev.app.edit","Edit"),dataAttributes:{"data-translation-key":"dev.app.edit"}},{onAction:()=>t.current.open(),content:a("dev.app.delete","Delete"),dataAttributes:{"data-translation-key":"dev.app.delete"}}]})),e.createElement(f,{ref:r,appName:n.name,appDisplayName:n.name}),e.createElement(d,{ref:t}))}function R(o){const r={day:"numeric",month:"short",year:"numeric"},t=new Date(parseInt(o,10)),n=Math.abs(t-Date.now())<3600*24*1e3;return t.toLocaleString("en-US",{...r,...n?{hour:"numeric",minute:"numeric"}:{}})}export{g as default,R as getReadableDate};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import*as s from"react";const a=(i
|
|
1
|
+
import*as s from"react";const a=(o,i)=>{const[e,c]=s.useState(i),d=s.useMemo(()=>{const n=[...o];return e!==null&&n.sort((t,r)=>t[e.key]<r[e.key]?e.direction==="ascending"?-1:1:t[e.key]>r[e.key]?e.direction==="ascending"?1:-1:0),n},[o,e]),u=s.useCallback(n=>{c(t=>{let r="descending";return t&&t.key===n&&t.direction==="descending"&&(r="ascending"),{key:n,direction:r}})},[]);return{sortedItems:d,requestSort:u,sortConfig:e}};export{a as useSortableData};
|
package/dist/server/plugins/markdown/attribute-resolvers/code-walkthrough/file-chunk-parser.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { CodeWalkthroughNode, CodeWalkthroughFileMetadata } from '@redocly/
|
|
1
|
+
import type { CodeWalkthroughNode, CodeWalkthroughFileMetadata } from '@redocly/theme/core/types';
|
|
2
2
|
export declare function parseFileChunks(text: string, filePath: string): Promise<{
|
|
3
3
|
root: CodeWalkthroughNode[];
|
|
4
4
|
metadata: CodeWalkthroughFileMetadata;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{resolveOpenApiRef as e}from"./resolve-open-api-ref.js";import{resolveJsonSchemaRef as o}from"./resolve-json-schema-ref.js";import{resolveParsedYaml as r}from"./resolve-parsed-yaml.js";import{resolveRawContent as m}from"./resolve-raw-content.js";import{
|
|
1
|
+
import{resolveOpenApiRef as e}from"./resolve-open-api-ref.js";import{resolveJsonSchemaRef as o}from"./resolve-json-schema-ref.js";import{resolveParsedYaml as r}from"./resolve-parsed-yaml.js";import{resolveRawContent as m}from"./resolve-raw-content.js";import{resolveTagRawContent as t}from"./resolve-tag-raw-content.js";import{resolveSvgContent as i}from"./resolve-svg-content.js";import{resolveRelativePath as l}from"./resolve-relative-path.js";import{resolveLink as a}from"./resolve-link.js";import{resolveNativeMdLink as p}from"./resolve-native-md-link.js";import{resolveCodeSnippetFromFile as s}from"./resolve-code-snippet-from-file.js";import{resolveDiagramFromFile as n}from"./resolve-diagram-from-file.js";import{resolveHtmlSourceAttribute as v}from"./resolve-html-source-attribute.js";import{resolveHtmlHref as f}from"./resolve-html-href.js";import{resolveImageSrc as S}from"./resolve-image-src.js";import{resolveImageSrcSet as c}from"./resolve-image-src-set.js";import{resolveImageGallery as g}from"./resolve-image-gallery.js";import{resolveNavLinks as R}from"./resolve-nav-links.js";import{resolveRelativeOrCdnIcon as d}from"./resolve-relative-or-cdn-icon.js";import{resolveCodeWalkthroughFilesets as h}from"./code-walkthrough/filesets-resolver.js";import{resolveJsonExampleRef as C}from"./resolve-json-example-ref.js";import{resolveSampleFromJsonSchema as F}from"./resolve-sample-from-json-schema.js";import{resolveOpenapiCodeSamples as k}from"./resolve-openapi-code-samples.js";import{resolveOpenapiResponseSamples as u}from"./resolve-openapi-response-samples.js";const K={openapiRef:e,jsonSchemaRef:o,parsedYaml:r,rawContent:m,tagRawContent:t,svgContent:i,relativePath:l,link:a,nativeMdLink:p,codeSnippetFile:s,diagramFile:n,htmlSourceAttribute:v,htmlHref:f,imageSrc:S,imageSrcSet:c,imageGallery:g,navLinks:R,relativeOrCdnIcon:d,codeWalkthroughFilesets:h,jsonExampleRef:C,sampleFromJsonSchema:F,openapiCodeSamples:k,openapiResponseSamples:u};export{K as attributeResolvers};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import
|
|
1
|
+
import n from"node:path";import{API_DOCS_TEMPLATE_ID as y,ASYNC_API_DOCS_TEMPLATE_ID as F,GRAPHQL_TEMPLATE_ID as M,OPENAPI_DOCS_TEMPLATE_ID as U}from"../../../../constants/common.js";import{isLocalLink as C}from"../../../../utils/path/is-local-link.js";import{normalizeRouteSlug as P}from"../../../../utils/path/normalize-route-slug.js";import{removeFragment as B}from"../../../../utils/path/remove-fragment.js";import{getInnerText as W}from"../../../../markdoc/helpers/get-inner-text.js";import{getNodeAttribute as j}from"../../../../markdoc/helpers/get-node-attribute.js";import{setNodeAttributeValue as c}from"../../../../markdoc/helpers/set-node-attribute-value.js";import{isAuthRoutePath as $}from"../../../../utils/auth/is-auth-route-path.js";import{isApiDownloadLink as V}from"../../../utils/is-api-download-link.js";import{MdResolveError as A}from"./md-resolve-error.js";import{getLinkOriginalAttrName as b}from"./utils.js";import{isOpenApiURL as z}from"../../api-docs/utils/is-api-doc.js";import{parseBaseName as G}from"../../utils.js";import{isMarkdownPage as N}from"../is-markdown-page.js";import{copyStaticFile as q}from"../../../utils/fs.js";async function pt(i,r,p,{actions:w,context:u}){const{contentDir:D,outdir:T,getRouteByFsPath:x,getRouteBySlug:I,hasRouteOrRedirectBySlug:d}=w,k=b(r),o=i[k]||j(i,r);if(i[k]=o,!C(o)||V(o)||$(o))return;const[H,t="",R,L]=/^([^?#]+)?([^#]+)?(.+)?/.exec(o)||[],f=i.type==="image"?"IMAGE":"LINK",g=String(i.attributes.title||i.attributes.alt||W([i])||""),a=B(p);if(i.type!=="image"){const{isOpenapiDetected:e,isOpenapiValid:s}=await z(t,a,w,u);if(e&&!s)throw new A(`OpenAPI route ${o} does not exist`,{rawLink:o,link:t,title:g,brokenLinkType:f})}if(n.extname(t)===""){if(t.startsWith("/")){const e=P(t),s=d(e)?t:_(e,I);if(!s)throw new A(`Route ${t} does not exist`,{rawLink:o,link:t,title:g,brokenLinkType:f});c(i,r,s+(R||"")+(L||""))}if(!o.startsWith("#")&&!t.startsWith("/")&&N(a)){const e=x(a)?.slug;if(!e)return;const{isIndexFile:s}=G(a),h=s?P(n.posix.join(e,t)):P(n.posix.join(e,"../",t)),E=d(P(h))?h:_(h,I);if(!E)throw new A(`Route ${t} does not exist`,{rawLink:o,link:h,title:g,brokenLinkType:f});c(i,r,E+(R||"")+(L||""))}return}const l=t.startsWith("/")?t.substring(1):n.posix.join(n.posix.dirname(a),decodeURI(t)),v=t.startsWith("/")?n.posix.join("static",t.substring(1)):"",S=u.fs.exists(l),O=u.fs.exists(v),m=x(l);if(!S&&!m&&!O)throw c(i,r,"#"),new A(`File ${l} does not exist`,{rawLink:o,link:l,title:g,brokenLinkType:f});if(m){const e=[U,M,F].includes(m.templateId);c(i,r,(e?m.baseSlug:m.slug)+(L||""))}else if(S){const e=u.fs.getFileInfo(l);if(!e||e.isVirtual)return;const s=await q(D,e.realRelativePath,T);c(i,r,s)}}function _(i,r){const p=r(i.toLowerCase());return p?.templateId===y?p.slug:void 0}export{pt as resolveLink};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{getNodeAttribute as m}from"../../../../markdoc/helpers/get-node-attribute.js";import{setNodeAttributeValue as
|
|
1
|
+
import{getNodeAttribute as m}from"../../../../markdoc/helpers/get-node-attribute.js";import{setNodeAttributeValue as p}from"../../../../markdoc/helpers/set-node-attribute-value.js";import{optimize as l}from"../../../../compiled/svgo/svgo-node.js";import{slug as c}from"../../../utils/index.js";import{MdResolveError as d}from"./md-resolve-error.js";import{resolvePathInMarkdown as u}from"../resolve-path-in-markdown.js";async function b(e,r,n,{context:i,actions:s}){const o=m(e,r),a=s.contentDir;if(o){const t=u(o,n,a);if(!i.fs.exists(t))throw new d(`File ${t} does not exist`,{rawLink:o});const f=l(await i.fs.read(t),{plugins:[{name:"prefixIds",params:{prefix:c(t).replaceAll(/[/.]/g,"-")}}]}).data;p(e,r+"RawContent",f)}}export{b as resolveSvgContent};
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { Node } from '@markdoc/markdoc';
|
|
2
|
+
import type { MarkdocResolveContext } from '../../../types';
|
|
3
|
+
export declare function resolveTagRawContent(node: Node, attrName: string, _relativePath: string, { readSourceLines }: MarkdocResolveContext): Promise<void>;
|
|
4
|
+
//# sourceMappingURL=resolve-tag-raw-content.d.ts.map
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import l from"@markdoc/markdoc";import{setNodeAttributeValue as u}from"../../../../markdoc/helpers/set-node-attribute-value.js";async function P(t,r,e,{readSourceLines:n}){if(t.children.length===0&&typeof t.attributes[r]=="string")return;if(t.inline){u(t,r,m(t)),t.children=[];return}if(n===void 0)return;const[i,c,o]=t.lines;if(i===void 0||c===void 0||o===void 0)return;const s=n(),f=p(s[i]??""),a=s.slice(c,o).map(h=>g(h,f)),d=b(a).join(`
|
|
2
|
+
`).replace(/^(?:[ \t]*\n)+/,"").trimEnd();u(t,r,d),t.children=[]}function m(t){return l.format(new l.Ast.Node("inline",{},t.children)).trim()}function p(t){return t.slice(0,Math.max(t.indexOf("{%"),0)).split(">").length-1}function g(t,r){let e=t;for(let n=0;n<r;n+=1){const i=e.match(/^ {0,3}> ?/);if(!i)break;e=e.slice(i[0].length)}return e}function b(t){const r=t.filter(n=>n.trim()!=="").map(n=>n.match(/^[ \t]*/)?.[0]??""),e=r.reduce(x,r[0]??"");return t.map(n=>n.startsWith(e)?n.slice(e.length):n.trimStart())}function x(t,r){let e=0;for(;e<t.length&&e<r.length&&t[e]===r[e];)e+=1;return t.slice(0,e)}export{P as resolveTagRawContent};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import
|
|
1
|
+
import M from"@markdoc/markdoc";import*as _ from"path";import{GATED_MARKDOC_TAGS as F}from"../../constants/entitlements.js";import{logger as H}from"../../tools/notifiers/logger.js";import{reporter as z}from"../../tools/notifiers/reporter.js";import{sha1 as B}from"../../utils/crypto/sha1.js";import{formatMarkdocError as G}from"./errors.js";import{extractFirstHeading as C,SKIP as K,visit as j}from"./markdoc/plugins/utils.js";import{isPromptNode as $}from"../../../markdoc/helpers/guards/is-prompt-node.js";import{attributeResolvers as R}from"./attribute-resolvers/index.js";import{MdResolveError as V}from"./attribute-resolvers/md-resolve-error.js";import{processHtmlTokens as q}from"./html/process-html-tokens.js";import{normalizeHtmlHeadings as J}from"./html/normalize-html-headings.js";import{resolveRawPartials as Q}from"./markdoc/resolve-raw-partials.js";import{exampleContentTrees as X,reparseExampleFences as Z}from"./markdoc/reparse-example-fences.js";import{EntitlementsProvider as tt}from"../../entitlements/entitlements-provider.js";import{MARKDOC_PARTIALS_DEPS_KEY as et}from"../../constants/common.js";import{getLinkOriginalAttrName as at}from"./attribute-resolvers/utils.js";import{createSourceLinesReader as rt}from"./create-source-lines-reader.js";const ot="EMPTY";async function st(e,o,a){const n=tt.instance(),{actions:s}=a,{relativePath:l,resolveErrors:E}=e,w={...a,readSourceLines:rt(e.rawContent)},g=new Set,u=new Set,m=new Set,b=new Set,c={},y=new Set,L={},T={};function P(t,r){const D=r||ot;t[D]=(t[D]||0)+1}const I=[];e.resolveErrors.length=0;const x=X(e.ast),O=t=>{const r=D();I.push(r.then(k=>{k?.sharedDataIds&&k.sharedDataIds.forEach(d=>g.add(d))}).catch(Y(t)));async function D(){const k=[];switch(t.type){case"fence":P(L,t.attributes.language);break;case"link":case"image":await R.nativeMdLink(t,t.type==="link"?"href":"src",l,w);break;case"tag":{if(!t.tag)break;const d=o?.tags?.[t.tag];if(!d){F[t.tag]&&!n.canAccessFeature(F[t.tag])&&(t.errors.push({level:"warning",id:"invalid-tag",message:`Undefined tag: ${t.tag}`}),t.tag="",t.type="error",t.attributes={});break}const v=t.tag==="html"?t.attributes.name:t.tag;if((t.tag==="html"?y:b).add(v),c[v]=(c[v]||0)+1,v==="code-snippet"&&P(L,t.attributes.language),d.attributes?.__idx&&(t.attributes.__idx=c[t.tag]),d.dynamicComponentLib&&u.add(d.dynamicComponentLib),!d.attributes)break;if(v==="partial"&&t.attributes?.file){const i=at("file"),f=t[i]||t.attributes.file,h=f.startsWith("/")?f.slice(1):_.posix.normalize(_.posix.join(_.posix.dirname(l),f));m.add(h);const p=(s.getGlobalConfig(et)||{})[h];if(p?.dynamicComponents)for(const S of p.dynamicComponents)u.add(S);if(p?.sharedDataDeps)for(const S of p.sharedDataDeps)g.add(S)}for(const[i,f]of Object.entries(d.attributes)){const h=f.type;if(h&&(h.resolver||f.resolver)){const N=R[h.resolver||f.resolver],p=await N?.(t,i,l,w);p?.sharedDataId&&k.push(p.sharedDataId)}}if(v==="code-walkthrough")for(const i of t.attributes.resolvedFilesets||[])for(const f of i.files||[])P(T,f.language);const A=t.attributes?.attrs;if(A&&t.tag==="html")for(const i of Object.keys(A))i==="src"||i==="srcSet"?await R.htmlSourceAttribute(t,i,l,w):i==="href"&&await R.htmlHref(t,i,l,w);break}}return{sharedDataIds:k}}};function Y(t){return async r=>{if(!(r instanceof V)){await z.panicOnBuild(r.message);return}E.push(G({type:"resolve_link",meta:{...r.meta,link:r.meta.link??r.meta.rawLink},lines:t.lines,location:t.location,error:{id:"",level:"error",message:r.message,location:t.location}},e.relativePath,e.rawContent))}}j(e.ast,t=>(O(t),$(t)?K:void 0));for(const t of x)j(t,r=>(r.type==="tag"&&O(r),$(r)?K:void 0));return await Promise.all(I),e.sharedDataDeps=g,e.dynamicMarkdocComponents=u,e.validatedAtRevision<s.buildRevision&&(e.markdocErrors=[e.ast,...x].flatMap(t=>M.validate(t,o)).map(t=>G(t,l,e.rawContent)),e.validatedAtRevision=s.buildRevision),{sharedDataDeps:e.sharedDataDeps,dynamicMarkdocComponents:Array.from(e.dynamicMarkdocComponents?.values()??[]),partials:Array.from(m),tagList:Array.from(b),htmlTagsList:Array.from(y),tagOccurrence:c,codeSnippetLanguages:L,codeWalkthroughLanguages:T}}const U=new M.Tokenizer({html:!0,allowIndentation:!0,allowComments:!0});U.parser.block.ruler.getRules("reference").length=0;function W(e,o){const a=U.tokenize(e),n=q(a),s=M.parse(n,o);return J(s),s}function it(e,o){const a=W(o,{file:e,slots:!0});return Z(a,s=>W(s,{file:e})),{ast:a,rawContent:o,resolveErrors:[],markdocErrors:[],relativePath:e,sharedDataDeps:void 0,validatedAtRevision:-1}}async function Pt(e,o){const{data:a}=await o.cache.load(e,"markdown-ast");return C(a.ast)}async function St(e,o){z.clearMarkdocProblems();const a=e.getAllRoutes();let n=0;const s=H.isInteractive();for(const l of a)await e.resolveRouteStaticData(l,o,!0),n++,s&&n%100===0&&H.logInFooter("validate",` \u{1F50D} Status: validating markdoc (${n}/${a.length})`)}async function Mt(e,o,a,n){const s=e.content?B(e.content):"";return await a.context.cache.load(n||e.relativePath,{loader:E,name:"markdown-inline-parser"},[s,String(a.actions.buildRevision)]);async function E(w,g,u){let m;if(e.content){const c=await g.getConfig(),y=await Q(e.content,e.relativePath,c.markdown?.partialsFolders,g);m=it(e.relativePath,y)}else m=(await g.cache.load(e.relativePath,"markdown-ast")).data;let b={};if(a.actions.buildRevision!==0&&(b=await st(m,o,a)),!e.isVirtual){for(const c of m.markdocErrors)u(c);for(const c of m.resolveErrors)u(c)}return{ast:m.ast,info:b}}}export{Pt as extractMdFirstHeading,it as getAst,Mt as parseAndResolveMarkdoc,st as resolveAndValidateMarkdoc,St as validateAllMarkdowns};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Returns a reader that splits `source` into lines on first use and reuses the result,
|
|
3
|
+
* so every tag on a page shares one split. CRLF line ends are normalized to match the
|
|
4
|
+
* line numbers Markdoc reports.
|
|
5
|
+
*/
|
|
6
|
+
export declare function createSourceLinesReader(source: string): () => string[];
|
|
7
|
+
//# sourceMappingURL=create-source-lines-reader.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
function n(r){let e;return()=>(e??=r.split(/\r?\n/),e)}export{n as createSourceLinesReader};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { Node } from '@markdoc/markdoc';
|
|
2
|
+
/**
|
|
3
|
+
* Rewrites block-level raw HTML `<h1>`…`<h6>` elements into Markdoc `heading` nodes,
|
|
4
|
+
* so they get an anchor id, a TOC entry and a search section like Markdown headings.
|
|
5
|
+
* Keeps the element's `id` attribute and drops the rest. Mutates `ast` in place.
|
|
6
|
+
* HTML headings inside inline content are left untouched.
|
|
7
|
+
*/
|
|
8
|
+
export declare function normalizeHtmlHeadings(ast: Node): void;
|
|
9
|
+
//# sourceMappingURL=normalize-html-headings.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import s from"@markdoc/markdoc";const o=/^h([1-6])$/;function u(t){r(t,!1)}function r(t,i){const n=i||t.type==="inline";t.children=t.children.map(e=>{const l=(n?void 0:a(e))??e;return r(l,n),l});for(const e of Object.values(t.slots))r(e,n)}function a(t){if(t.type!=="tag"||t.tag!=="html")return;const i=o.exec(t.attributes.name)?.[1];if(!i)return;const n=t.attributes.attrs?.id,e=new s.Ast.Node("heading",{level:Number(i),...typeof n=="string"&&{id:n}},[new s.Ast.Node("inline",{},t.children)]);return e.lines=t.lines,e.location=t.location,e}export{u as normalizeHtmlHeadings};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import f from"@markdoc/markdoc";import*as p from"@redocly/theme/markdoc/default";import{reporter as g}from"../../../tools/notifiers/reporter.js";import*as
|
|
1
|
+
import f from"@markdoc/markdoc";import*as p from"@redocly/theme/markdoc/default";import{reporter as g}from"../../../tools/notifiers/reporter.js";import*as u from"../../../../markdoc/nodes/index.js";import d from"../../../../markdoc/tags/index.js";import{normalizeCustomTags as l}from"../../../../markdoc/helpers/normalize-custom-tags.js";import{includes as h}from"./functions/includes.js";import{importUserTags as O}from"./import-user-tags.js";import{concat as y}from"./functions/concat.js";const T=p.tags;function b(s){const{tags:c,functions:e={},...r}=s,n={...c,...r},a=Object.entries(n),o=[],t=[];for(const[i,m]of a)i in f.nodes?o.push([i,m]):t.push([i,m]);return{nodes:Object.fromEntries(o),tags:Object.fromEntries(t),functions:e}}async function _(s="../../../esbuild/cache/server/",c=""){let e;try{e=(await O(s)).schema}catch(t){throw t.code==="ERR_MODULE_NOT_FOUND"?(g.printErrors(),new Error("Please fix the errors above and try again.")):t}const{tags:r={},nodes:n={},functions:a={}}=b(e),o={tags:{schemaDefinition:{render:"SchemaDefinition",attributes:{schemaRef:{type:String},exampleRef:{type:String},showReadOnly:{type:Boolean},showWriteOnly:{type:Boolean}}}}};return{nodes:{...u,...n},tags:{...d,...T,...l(r),...o.tags},functions:{...f.functions,...a,includes:h,concat:y}}}export{_ as getMarkdocOptions};
|
|
@@ -11,9 +11,9 @@ export declare function getNumberedItemHeadingData(node: Tag | Node): {
|
|
|
11
11
|
} | undefined;
|
|
12
12
|
export declare function extractFirstHeading(ast: Node): undefined | string;
|
|
13
13
|
export declare const EXIT: unique symbol;
|
|
14
|
+
export declare const SKIP: unique symbol;
|
|
14
15
|
/**
|
|
15
16
|
* simplified version of unist-util-visit for our specific use-case
|
|
16
|
-
* TODO: implement SKIP and EXIT
|
|
17
17
|
* @see https://github.com/syntax-tree/unist-util-visit-parents/blob/main/index.js#L112
|
|
18
18
|
*/
|
|
19
19
|
export declare function visit<T extends Tag | Node>(node: T, visitor: (node: T) => symbol | void): symbol | void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{isNode as
|
|
1
|
+
import{isNode as p}from"../../../../../markdoc/helpers/guards/is-node.js";import{isStringNode as u}from"../../../../../markdoc/helpers/guards/is-string-node.js";import{getNodeAttribute as o}from"../../../../../markdoc/helpers/get-node-attribute.js";import{getInnerText as a}from"../../../../../markdoc/helpers/get-inner-text.js";import{isPromptNode as m}from"../../../../../markdoc/helpers/guards/is-prompt-node.js";function d(t){const r=o(t,"level");if(r)return{value:a(t.children),id:o(t,"id"),depth:r}}function y(t){const r=o(t,"headlineLevel"),e=o(t,"anchorId"),s=o(t,"headline");if(!(!r||!e||!Array.isArray(s)))return{value:a(s),id:e,depth:r}}function I(t){let r;return f(t,e=>{if(p(e)){if(m(e))return l;if(e.type==="heading")return r=d(e)?.value,c}}),r}const c=Symbol("Exit visitor"),l=Symbol("Skip children");function f(t,r){if(!t)return;const e=r(t);if(e===c)return e;if(e===l)return;for(const i of t.children){if(!i||u(i))continue;const n=f(i,r);if(n===c)return n}const s=t.slots||{};for(const i of Object.values(s)){if(!i||u(i))continue;const n=f(i,r);if(n===c)return n}}export{c as EXIT,l as SKIP,I as extractFirstHeading,d as getHeadingData,y as getNumberedItemHeadingData,f as visit};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import D from"path";import{REDOCLY_TEAMS_RBAC as v,REDOCLY_ROUTE_RBAC as A}from"@redocly/config";import{removeTrailingSlash as M}from"../../../utils/url/remove-trailing-slash.js";import{addLeadingSlash as N}from"../../../utils/url/add-leading-slash.js";import{shaHexShort as E}from"../../utils/crypto/sha-hex-short.js";import{isDefined as I}from"../../../utils/guards/is-defined.js";import{resolveFrontmatterKeys as L}from"../resolve-frontmatter-keys.js";import{resolveItem as _}from"../nav-utils.js";const R=new WeakMap;async function j(o,i,s,e,a){const d=await s.getConfig(),{ast:
|
|
1
|
+
import D from"path";import{REDOCLY_TEAMS_RBAC as v,REDOCLY_ROUTE_RBAC as A}from"@redocly/config";import{removeTrailingSlash as M}from"../../../utils/url/remove-trailing-slash.js";import{addLeadingSlash as N}from"../../../utils/url/add-leading-slash.js";import{shaHexShort as E}from"../../utils/crypto/sha-hex-short.js";import{isDefined as I}from"../../../utils/guards/is-defined.js";import{resolveFrontmatterKeys as L}from"../resolve-frontmatter-keys.js";import{resolveItem as _}from"../nav-utils.js";const R=new WeakMap;async function j(o,i,s,e,a){const d=await s.getConfig(),{ast:r,compoundHash:n,info:g}=await a.parseMarkdoc({input:o,context:s}),l={...d.markdown?.editPage,...e.markdown?.editPage},t=i.fsPath!=null?s.fs.getFileInfo(i.fsPath):null,f=!l?.hide&&l?.baseUrl?{to:M(l.baseUrl)+N(t?.realRelativePath||i.fsPath||"")}:void 0,w={...d.feedback,...e.feedback},m=e.feedback?{type:w.type||"sentiment",settings:w.settings||{},hide:e.feedback?.hide}:void 0;let h;Array.isArray(e.banner)&&(h=(await Promise.all(e.banner.map(async(B,O)=>{const{content:k,...b}=B;if(!k)return;const{ast:T}=await a.parseMarkdoc({input:{content:k,relativePath:o.relativePath,isVirtual:o.isVirtual},context:s,resource:`${o.relativePath}#banner${O}`});return{...b,...b.rbac?{[v]:b.rbac}:{},ast:JSON.stringify(T),hash:E(k)}}))).filter(I));const y=R.get(r);let c=y?.ast;(!c||y?.compoundHash!==n)&&(c=JSON.stringify(r),R.set(r,{ast:c,compoundHash:n}));let p;e.navigation&&(p={...e.navigation,nextButton:await S(e.navigation.nextButton,i,a,s),previousButton:await S(e.navigation.previousButton,i,a,s)});const u=e?.seo?await L(e.seo,["image"],i.fsPath||"",a,s):void 0,P=g.tagList;Array.isArray(P)&&P.includes("code-walkthrough")&&(e.markdown=e.markdown||{},e.markdown.toc={hide:!0},e.footer=e.footer||{},e.footer={hide:!0});const C=e?.seo?.title||await i.getNavText?.();return{ast:c,frontmatter:await L({...e,...m!==void 0?{feedback:m}:{},...u!==void 0?{seo:u}:{},...p!==void 0?{navigation:p}:{},...h!==void 0?{banner:h}:{}},d.markdown?.frontMatterKeysToResolve||["image","links"],i.fsPath||"",a,s),editPage:f,props:{metadata:{markdoc:{tagList:g.tagList}},seo:{...u,...C?{title:C}:{}}},[v]:i[v],[A]:i[A]}}async function S(o,i,s,e){if(!o||typeof o!="object")return;let a=o,d,r;if("page"in a&&typeof a.page=="string"){const{page:t,...f}=a;a=f,d=t}if("label"in a&&typeof a.label=="string"){const{label:t,...f}=a;a=f,r=t}let n;if(d){const t=await _({page:d},i.fsPath?D.dirname(i.fsPath):".",s,e,{navFile:i.fsPath||""});n=Array.isArray(t)?t[0]:t,n=n?.type!=="error"?n:void 0}const g=n?.routeSlug,l=r??n?.label;return{...a,label:l,link:g}}export{j as markdownStaticDataLoader};
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import M from"@markdoc/markdoc";import D from"node:path";import{AI_SEARCH_CHUNK_SIZE as R,AI_SEARCH_DOCUMENT_CHUNK_SIZE as v}from"../../../constants/plugins/search.js";import{slugger as I}from"../../../../utils/slugger.js";import{joinSectionContent as N}from"./join-section-content.js";import{toMarkdown as P}from"./to-markdown.js";import{AstToSearchNodeTransformer as w}from"./walk-sections.js";import{createRenderTagFn as x}from"./create-render-tag-fn.js";import{getBuildTranslateContext as K}from"../../../utils/l10n/get-build-translate-context.js";import{getLocaleFromRelativePath as L}from"../../../fs/utils/get-locale-from-relative-path.js";import{HeadingNode as b}from"./nodes/heading-node.js";import{extractDocumentSearchFacets as U}from"./search-facets.js";import{formatDocumentMetadata as y}from"../../search/utils.js";import{TagNode as H}from"./nodes/tag-node.js";import{MARKDOC_PARTIALS_DATA_KEY as O}from"../../../constants/common.js";const j=Symbol(),at=(n,o)=>async(e,r,i,c)=>{if(o?.excludeFromSearch)return;I.reset();const l=await e.getNavText?.()||D.basename(e.fsPath),f=M.Ast.fromJSON(r.ast),{locale:g,translate:A}=await K(e.slug,c.getGlobalData?.().l10n),s=new w({partials:c.getGlobalConfig(O)||{},renderTag:x(c.markdocOptions.tags,g,A),getInnerContent:P,ast:f,skipConditionals:!0}),d=Array.from(s.transform());return{async getLLMsTxts(){const u=o?.seo,t=u&&typeof u=="object"&&"description"in u?String(u.description):void 0,a=N(d);return[{title:l,description:t,slug:e.slug,fsPath:e.fsPath,content:a,includeInLLMsTxt:!0}]},async getSearchDocuments(){return F(e,d,n,l)}}};function F(n,o,e,r){const i=n.slug,c=new Map,l=n.metadata||{},f=U(l,e),g=y(l),A=g?`Metadata:
|
|
2
2
|
${g}
|
|
3
|
-
`:""
|
|
3
|
+
`:"",s=[];for(const t of o)if(t instanceof b){s.splice(t.attributes.level-1,6);const a=t.attributes.level>2,m=s[s.length-1]?.title,T=s[s.length-1]?.url,C=a&&m?m:W(r,t),S=a&&T?T:t.getUrl(i),p={title:C,content:"",url:S,level:t.attributes.level,toc:s.map(E=>h(E.section)).join(`
|
|
4
4
|
`)};(t.attributes.level>1||h(t)!==r)&&(p.content+=p.content?`
|
|
5
5
|
`:"",p.content+=t.content.trimEnd()),c.set(t.id,p),s.push({section:t,title:C,url:S})}else if(t instanceof H)c.set(t.id,{title:t.content,content:t.content,url:t.getUrl(i),level:t.attributes.level+1,toc:s.map(a=>h(a.section)).concat(t.content).join(`
|
|
6
6
|
`)});else{const a=t.parentNode?.id??j,m=c.get(a)??{title:r,content:"",url:i,level:1/0,toc:""};m.content+=m.content?`
|
|
7
7
|
`:"",m.content+=t.content.trimEnd(),c.set(a,m)}const d=$(Array.from(c.values())),u=L(n.fsPath);return d.filter(t=>t.content).map(t=>({title:t.title,url:t.url,content:[A,t.toc||`# ${r}`,t.content].filter(Boolean).join(`
|
|
8
8
|
`),fsPath:n.fsPath,locale:u,product:n.product?.name,facets:f}))}function _(n){return n.length/4}function $(n){if(n.length===0)return[];const o=[];let e=n[0];for(let r=1;r<n.length;r++){const i=n[r],c=_(e.content),l=_(i.content),f=r===n.length-1;l<R&&(c<v||f)&&i.level>e.level?e.content+=`
|
|
9
|
-
`+i.content:(o.push(e),e=i)}return o.push(e),o}const k=String.raw`\((?:[^()]|\([^()]*\))*\)`,G=new RegExp(String.raw`!\[[^\]]*\]`+k,"g"),z=new RegExp(String.raw`\[([^\]]*)\]`+k,"g");function W(n,o){const e=h(o);return o.content===n||!e?n:`${n} \u2192 ${e}`}function h(n){return B(n.content.replace(/^#+/,""))}function B(n){return n.replace(G,"").replace(z,"$1").trim()}export{at as getAiDocumentsStore};
|
|
9
|
+
`+i.content:(o.push(e),e=i)}return o.push(e),o}const k=String.raw`\((?:[^()]|\([^()]*\))*\)`,G=new RegExp(String.raw`!\[[^\]]*\]`+k,"g"),z=new RegExp(String.raw`\[(?<!\[[^\]()]*?\[)([^\]]*)\]`+k,"g");function W(n,o){const e=h(o);return o.content===n||!e?n:`${n} \u2192 ${e}`}function h(n){return B(n.content.replace(/^#+/,""))}function B(n){return n.replace(G,"").replace(z,"$1").trim()}export{at as getAiDocumentsStore};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import p from"@markdoc/markdoc";import{REDOCLY_ROUTE_RBAC as l,REDOCLY_TEAMS_RBAC as A}from"@redocly/config";import{getInnerText as
|
|
1
|
+
import p from"@markdoc/markdoc";import{REDOCLY_ROUTE_RBAC as l,REDOCLY_TEAMS_RBAC as A}from"@redocly/config";import{getInnerText as T}from"../../../../markdoc/helpers/get-inner-text.js";import{getSearchDocuments as h}from"./get-search-documents.js";import{AstToSearchNodeTransformer as R}from"./walk-sections.js";import{setDocumentSearchFacets as S,extractDocumentSearchFacets as C}from"./search-facets.js";import{MARKDOC_PARTIALS_DATA_KEY as D}from"../../../constants/common.js";import{normalizeFrontmatterKeywords as _}from"../../helpers/normalize-frontmatter-keywords.js";function K(e,m,o,c){return async(t,r,a)=>{if(e?.excludeFromSearch)return[];const i=p.Ast.fromJSON(r.ast),u=new R({ast:i,getInnerContent:T,partials:a.getGlobalConfig(D)||{},indexPromptTitles:!0}),f=t.metadata||{},n=C(f,o);S(n,o,c);const d=e?.seo?.title||m,{result:s}=_(e?.keywords);return h(u,t.slug,d,r[A],r[l],n,s||void 0)}}export{K as searchResolver};
|
|
@@ -1,29 +1,29 @@
|
|
|
1
|
-
import{isPrimitive as m}from"../../../../utils/guards/is-primitive.js";import{getNodeAttribute as c}from"../../../../markdoc/helpers/get-node-attribute.js";import{getVariable as f}from"../../../../markdoc/helpers/get-variable.js";import{isTag as $}from"../../../../markdoc/helpers/guards/is-tag.js";import{isNode as
|
|
2
|
-
`);break;case"fence":{const n=c(e,"process")===!1;t.push(u(e,r,n));break}case"list":{const n=c(e,"ordered")||!1,i=c(e,"marker"),l=e.children.map((o,h)=>`${" ".repeat((r?.indent??0)*2)}${n?h+1:""}${i} ${
|
|
3
|
-
`);break}case"item":t.push(e.children.map(n=>`${
|
|
4
|
-
`).join(""));break;case"thead":{const n=e.children.map(i=>
|
|
5
|
-
`);break}case"tr":{const n=e.children.map(i=>
|
|
6
|
-
`);break}case"em":t.push(`*${
|
|
1
|
+
import{isPrimitive as m}from"../../../../utils/guards/is-primitive.js";import{getNodeAttribute as c}from"../../../../markdoc/helpers/get-node-attribute.js";import{getVariable as f}from"../../../../markdoc/helpers/get-variable.js";import{isTag as $}from"../../../../markdoc/helpers/guards/is-tag.js";import{isNode as p}from"../../../../markdoc/helpers/guards/is-node.js";import{isConditionalNode as g}from"../../../../markdoc/helpers/guards/is-conditional-node.js";import{isVariable as k}from"../../../../markdoc/helpers/guards/is-variable.js";import{isExampleNode as b}from"../../../../markdoc/helpers/guards/is-example-node.js";import{isFenceNode as T}from"../../../../markdoc/helpers/guards/is-fence-node.js";import{isPromptNode as j}from"../../../../markdoc/helpers/guards/is-prompt-node.js";function s(a,r={}){const t=[];for(const e of a){if(m(e)){const n=r.isTrim?d(String(e)):String(e);n&&t.push(n)}else if(p(e))switch(e.type){case"text":t.push(s([c(e,"content")],r));break;case"code":t.push(`\`${s([c(e,"content")],r)}\``);break;case"blockquote":t.push(`> ${s(e.children,r)}
|
|
2
|
+
`);break;case"fence":{const n=c(e,"process")===!1;t.push(u(e,r,n));break}case"list":{const n=c(e,"ordered")||!1,i=c(e,"marker"),l=e.children.map((o,h)=>`${" ".repeat((r?.indent??0)*2)}${n?h+1:""}${i} ${s([o],{...r??{},indent:(r?.indent??0)+1})}`);t.push(`${l.join("")}
|
|
3
|
+
`);break}case"item":t.push(e.children.map(n=>`${s([n],r).trimEnd()}
|
|
4
|
+
`).join(""));break;case"thead":{const n=e.children.map(i=>s([i],r));t.push(`${n}| ${" --- |".repeat(e.children?.[0]?.children.length)}
|
|
5
|
+
`);break}case"tr":{const n=e.children.map(i=>s([i],r));t.push(`| ${n.join(" | ")} |
|
|
6
|
+
`);break}case"em":t.push(`*${s(e.children,r)}*`);break;case"strong":t.push(`**${s(e.children,r)}**`);break;case"softbreak":case"hardbreak":t.push(`
|
|
7
7
|
`);break;case"hr":t.push(`
|
|
8
8
|
|
|
9
9
|
---
|
|
10
10
|
|
|
11
|
-
`);break;case"heading":{const n=c(e,"level")??0;t.push(`${"#".repeat(n)} ${
|
|
12
|
-
`);break}case"image":{const n=c(e,"alt")||"",i=c(e,"src")||"";t.push(``);break}case"link":{const n=c(e,"href")||"";t.push(`[${
|
|
13
|
-
`);break;case"tag":if(
|
|
11
|
+
`);break;case"heading":{const n=c(e,"level")??0;t.push(`${"#".repeat(n)} ${s(e.children,r)}
|
|
12
|
+
`);break}case"image":{const n=c(e,"alt")||"",i=c(e,"src")||"";t.push(``);break}case"link":{const n=c(e,"href")||"";t.push(`[${s(e.children,r)}](${n})`);break}case"paragraph":case"table":t.push(`${s(e.children,r)}
|
|
13
|
+
`);break;case"tag":if(g(e)&&r.skipConditionals||j(e))continue;if(b(e)){t.push(...e.children.map(n=>{if(T(n)){const i=c(n,"process")!==!0;return u(n,r,i)}return s([n],r)}));continue}if(e.tag==="code-snippet"){const n=c(e,"rawContent");if(n){const i=c(e,"language"),l=c(e,"title"),h=`
|
|
14
14
|
\`\`\`${`${i||""}${l?`${i?" ":""}${l}`:""}`}
|
|
15
15
|
${n.trimEnd()}
|
|
16
16
|
\`\`\`
|
|
17
|
-
`;t.push(h)}continue}if(e.tag==="json-example"){const n=
|
|
17
|
+
`;t.push(h)}continue}if(e.tag==="json-example"){const n=S(e);n&&t.push(n);continue}if(e.tag==="json-schema"){const n=v(e);n&&t.push(n);continue}if(r.renderTag){const n=r.renderTag(e,{getBody:()=>s(e.children,r)});if(n!==void 0){t.push(n);continue}}t.push(`${s(e.children,r)}`);break;default:t.push(s(e.children,r));break}else $(e)&&t.push(s(e.children,r));k(e)&&t.push(s([f(e,r.variables)],r))}return r.isTrim?d(t.map(e=>d(e)).join("")):t.join("")}function d(a){return a.replace(/^[ \t\r\f]+|(?<![ \t\r\f])[ \t\r\f]+$/g,"")}function u(a,r={},t=!1){const e=c(a,"title"),n=c(a,"language"),i=`${n||""}${e?`${n?" ":""}${e}`:""}`,l=t?(c(a,"content")||"").trimEnd():s(a.children,r).trimEnd();return`
|
|
18
18
|
\`\`\`${i}
|
|
19
19
|
${l}
|
|
20
20
|
\`\`\`
|
|
21
|
-
`}function
|
|
21
|
+
`}function S(a){const r=c(a,"json")??c(a,"valueResolved")??c(a,"schemaResolved"),t=c(a,"title");return r===null?null:`
|
|
22
22
|
\`\`\`${`json${t?` ${t}`:""}`}
|
|
23
23
|
${JSON.stringify(r,null,2)}
|
|
24
24
|
\`\`\`
|
|
25
|
-
`}function
|
|
25
|
+
`}function v(a){const r=c(a,"schemaResolved");if(r===null)return null;const t=c(a,"title"),{components:e,openapi:n,...i}=r,{__root:l,...o}=e?.schemas||{},h=l?{...l,...Object.keys(o).length>0?{components:{schemas:o}}:{},...i}:r;return`
|
|
26
26
|
\`\`\`${`json${t?` ${t}`:""}`}
|
|
27
27
|
${JSON.stringify(h,null,2)}
|
|
28
28
|
\`\`\`
|
|
29
|
-
`}export{
|
|
29
|
+
`}export{s as toMarkdown};
|
|
@@ -8,10 +8,12 @@ type Params = {
|
|
|
8
8
|
skipConditionals?: boolean;
|
|
9
9
|
getInnerContent: GetInnerContentFn;
|
|
10
10
|
renderTag?: RenderTagFn;
|
|
11
|
+
/** Emits the prompt title, never the prompt body. Only the full-text search index takes it. */
|
|
12
|
+
indexPromptTitles?: boolean;
|
|
11
13
|
};
|
|
12
14
|
export declare class AstToSearchNodeTransformer {
|
|
13
15
|
#private;
|
|
14
|
-
constructor({ ast, partials, skipConditionals, getInnerContent, renderTag }: Params);
|
|
16
|
+
constructor({ ast, partials, skipConditionals, getInnerContent, renderTag, indexPromptTitles, }: Params);
|
|
15
17
|
transform(): Generator<SearchNode, void, any>;
|
|
16
18
|
}
|
|
17
19
|
export {};
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import{logger as
|
|
2
|
-
`)?
|
|
3
|
-
|
|
1
|
+
import{PROMPT_TAG as a}from"@redocly/theme/core/constants";import{logger as w}from"../../../tools/notifiers/logger.js";import{isNode as p}from"../../../../markdoc/helpers/guards/is-node.js";import{isConditionalNode as N}from"../../../../markdoc/helpers/guards/is-conditional-node.js";import{isContentNode as m}from"../../../../markdoc/helpers/guards/is-content-node.js";import{getNodeAttribute as f}from"../../../../markdoc/helpers/get-node-attribute.js";import{extractRbacFromCondition as b}from"../../../../markdoc/helpers/extract-rbac-from-condition-node.js";import{TextNode as n}from"./nodes/text-node.js";import{TAG_TITLE_ATTRIBUTES as g,TagNode as u}from"./nodes/tag-node.js";import{HeadingNode as y}from"./nodes/heading-node.js";import{joinSectionContent as d}from"./join-section-content.js";class G{#r;#e;#o;#s;#c;#n;constructor({ast:i,partials:t,skipConditionals:s=!1,getInnerContent:r,renderTag:e,indexPromptTitles:o=!1}){if(this.#r=i,this.#e=t,this.#o=s,this.#s=r,this.#c=e,this.#n=o,!this.#r||!p(this.#r))throw new Error("ast is not a valid Markdoc Node.")}#i(i={}){return{skipConditionals:this.#o,renderTag:this.#c,...i}}*transform(){yield*this.#l(this.#r,{parentNode:null})}*#l(i,t,s=this.#s){if(!(!i||!p(i))){if(N(i)){if(this.#o)return;const r=b(i);r&&r.length>0&&(yield*this.#t(i,{...t,rbacTeams:r},s));return}if(m(i)){yield new n({node:i,content:s([i],this.#i()),...t});return}if(i.type==="heading"){yield new y({node:i,content:s([i],this.#i()),rbacTeams:t?.rbacTeams});return}if(i.type==="tag"){yield*this.#h(i,t,s);return}yield*this.#t(i,t,s)}}*#h(i,t,s=this.#s){switch(i.tag){case"partial":{const r=i.attributes.file,e=i.attributes.variables??{};if(r&&this.#e[r]){yield*this.#l(this.#e[r],t,(o,h)=>s(o,{...h,variables:e}));return}w.warn(`Could not create search indexes for partial \u201C${r}\u201D: file not found`);return}case"html":case"cards":case"tabs":case"code-walkthrough":{yield*this.#t(i,t,s);return}case a:{const r=f(i,"title");this.#n&&r&&(yield new u({node:i,content:r,...t}));return}case"markdoc-example":{const r=s([i],this.#i());yield new n({node:i,content:r,...t});return}case"code-snippet":{const r=f(i,"title"),e=s([i],this.#i());if(r){const o=new u({node:i,content:r,...t});t={...t,parentNode:o},yield o}e&&(yield new n({node:i,content:e,...t}));return}default:{const r=this.#f(i,t,s);if(r!==void 0){yield new n({node:i,content:k(r),...t});return}const e=g.find(l=>l in i.attributes),o=(e&&f(i,e))??"",h=typeof o=="string"?o:s([o]);if(h){const l=new u({node:i,content:h,...t});t={...t,parentNode:l},yield l}if(T(i))yield*this.#t(i,t,s);else{const l=s([i],this.#i());l&&(yield new n({node:i,content:l,...t}))}return}}}#f(i,t,s){const r=()=>T(i)?d([...this.#t(i,t,s)]):"";return this.#c?.(i,{getBody:r})}*#t(i,t,s=this.#s){for(const r of[...Object.values(i.slots),...i.children])for(const e of this.#l(r,t,s))e instanceof y&&(t={...t,parentNode:e}),yield e}}function T(c){return c.children.length>0||Object.keys(c.slots).length>0}function k(c){return c.endsWith(`
|
|
2
|
+
`)?c:`${c}
|
|
3
|
+
`}export{G as AstToSearchNodeTransformer};
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
function
|
|
2
|
-
${e}`)}export{
|
|
1
|
+
function a(n){return n.replace(/\[(?<!\[[^\]()]*?\[)([^\]<]*<[^>]*>[^\]]*)\]\(([^)]+)\)/g,(r,s,t)=>`[${s.replace(/(`{1,16})[^`]+\1|[<>]/g,e=>e==="<"?"<":e===">"?">":e)}](${t})`).replace(/({%\s*(\w+)(?:\s[^%]*)?%})(\s*)({%\s*\/\2\s*%})/g,(r,s,t,c,e)=>`${s}
|
|
2
|
+
${e}`)}export{a as sanitizeMalformedMdContent};
|
|
@@ -27,7 +27,7 @@ export declare function auditOutputDigest(value: string): {
|
|
|
27
27
|
*/
|
|
28
28
|
export declare function auditHeaderNames(headers: Record<string, string> | undefined): string;
|
|
29
29
|
/** Full URL with its query string, credential-shaped parameter values replaced. */
|
|
30
|
-
export declare function auditUrl(rawUrl: string, injectedSecretValues?: readonly string[]): string;
|
|
30
|
+
export declare function auditUrl(rawUrl: string, injectedSecretValues?: readonly string[], credentialQueryParams?: readonly string[]): string;
|
|
31
31
|
/**
|
|
32
32
|
* Values are JSON-encoded so a multi-line payload (submitted code, an assembled prompt) stays on
|
|
33
33
|
* one log line, which is what makes one record one Grafana row.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{createHash as c}from"node:crypto";import{logger as s}from"../../../tools/notifiers/logger.js";import{redactUrl as f}from"../../../utils/redact-url.js";import{AUDIT_LOG_PREFIX as p}from"./constants.js";import{redactSecretsFromString as u}from"../gateway-mcp/fetch/redact.js";import{redactSecretShapes as a}from"./secret-patterns.js";import{AUDIT_LOG_PREFIX as L}from"./constants.js";const i=4096;function d(t){return c("sha256").update(t,"utf8").digest("hex")}function m(t){if(t.length<=i)return t;const r=t.slice(0,i),o=r.search(/\s\S*$/),e=o>0?r.slice(0,o):r;return`${e}\u2026[truncated: kept ${e.length} of ${t.length} chars]`}function h(t,r=[]){return a(u(m(t),r))}function _(t){return{sha256:d(t),bytes:Buffer.byteLength(t,"utf8")}}function l(t){return Object.keys(t??{}).map(r=>r.toLowerCase()).sort().join(",")}function O(t,r=[]){return h(f(t),r)}function y(t,r){const o=Object.entries(r).filter(([,e])=>e!==void 0&&e!=="").map(([e,n])=>typeof n=="string"?`${e}=${JSON.stringify(n)}`:`${e}=${String(n)}`).join(" ");try{s.infoPreSanitized(`${p} ${t} ${o}`)}catch{}}export{i as AUDIT_FIELD_MAX_CHARS,L as AUDIT_LOG_PREFIX,l as auditHeaderNames,h as auditInput,_ as auditOutputDigest,d as auditSha256,O as auditUrl,y as logAuditRecord,m as truncateAuditField};
|
|
1
|
+
import{createHash as c}from"node:crypto";import{logger as s}from"../../../tools/notifiers/logger.js";import{redactUrl as f}from"../../../utils/redact-url.js";import{AUDIT_LOG_PREFIX as p}from"./constants.js";import{redactSecretsFromString as u}from"../gateway-mcp/fetch/redact.js";import{redactSecretShapes as a}from"./secret-patterns.js";import{AUDIT_LOG_PREFIX as L}from"./constants.js";const i=4096;function d(t){return c("sha256").update(t,"utf8").digest("hex")}function m(t){if(t.length<=i)return t;const r=t.slice(0,i),o=r.search(/\s\S*$/),e=o>0?r.slice(0,o):r;return`${e}\u2026[truncated: kept ${e.length} of ${t.length} chars]`}function h(t,r=[]){return a(u(m(t),r))}function _(t){return{sha256:d(t),bytes:Buffer.byteLength(t,"utf8")}}function l(t){return Object.keys(t??{}).map(r=>r.toLowerCase()).sort().join(",")}function O(t,r=[],o=[]){return h(f(t,o),r)}function y(t,r){const o=Object.entries(r).filter(([,e])=>e!==void 0&&e!=="").map(([e,n])=>typeof n=="string"?`${e}=${JSON.stringify(n)}`:`${e}=${String(n)}`).join(" ");try{s.infoPreSanitized(`${p} ${t} ${o}`)}catch{}}export{i as AUDIT_FIELD_MAX_CHARS,L as AUDIT_LOG_PREFIX,l as auditHeaderNames,h as auditInput,_ as auditOutputDigest,d as auditSha256,O as auditUrl,y as logAuditRecord,m as truncateAuditField};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Masks the credentials that sandbox code writes as string literals, whatever their shape: values
|
|
3
|
+
* under a credential-named header, field or variable (`Authorization`, `X-Api-Key`, `apiKey`,
|
|
4
|
+
* `client_secret`), `headers.set(name, value)` calls, `Bearer`/`Basic` values and credential query
|
|
5
|
+
* parameters inside URLs. The code keeps its structure. Code that does not parse comes back
|
|
6
|
+
* unchanged; the shape patterns of `auditInput` still apply to it.
|
|
7
|
+
*/
|
|
8
|
+
export declare function maskCodeCredentials(code: string): string;
|
|
9
|
+
//# sourceMappingURL=code-credentials.d.ts.map
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{parse as d}from"acorn";const m="[REDACTED:credential]",h={apikey:!0,auth:!0,authorization:!0,bearer:!0,cookie:!0,credential:!0,credentials:!0,key:!0,passwd:!0,password:!0,pwd:!0,secret:!0,sessionid:!0,signature:!0,token:!0},C=/^(?:Bearer|Basic|Token|Digest)\s+/i,k=/\b(Bearer|Basic)(\s+)[^\s'"`]+/gi,w=/([a-z0-9])([A-Z])/g,R=/[^a-z0-9]+/,_=`&#
|
|
2
|
+
\r'"\``;function N(e){let t;try{t=d(e,{ecmaVersion:"latest",sourceType:"script",allowAwaitOutsideFunction:!0,allowReturnOutsideFunction:!0})}catch{return e}const r=new Set,i=[];y(t,s=>{for(const a of D(s))if(a.type==="TemplateLiteral")for(const c of a.quasis)r.add(c);else r.add(a);(g(s)||s.type==="TemplateElement")&&i.push(s)});let n=e;for(const s of i.sort((a,c)=>c.start-a.start)){const[a,c]=s.type==="Literal"?[s.start+1,s.end-1]:[s.start,s.end],f=e.slice(a,c),A=r.has(s)?L(f):T(f);A!==f&&(n=n.slice(0,a)+A+n.slice(c))}return n}function y(e,t){if(Array.isArray(e)){for(const r of e)y(r,t);return}if(p(e)){t(e);for(const r of Object.values(e))typeof r=="object"&&r!==null&&y(r,t)}}function D(e){switch(e.type){case"Property":return u(o(e.key,e.computed))?l(e.value):[];case"VariableDeclarator":return u(o(e.id,!1))?l(e.init):[];case"AssignmentExpression":{const t=e.left,r=t.type==="MemberExpression"?o(t.property,t.computed):o(t,!1);return u(r)?l(e.right):[]}case"CallExpression":{const t=e.callee,[r,i]=e.arguments,n=t.type==="MemberExpression"?o(t.property,t.computed):"";return(n==="set"||n==="append")&&u(E(r))?l(i):[]}case"ArrayExpression":{const t=e.elements;return t.length===2&&u(E(t[0]))?l(t[1]):[]}default:return[]}}function l(e){return p(e)&&(g(e)||e.type==="TemplateLiteral")?[e]:[]}function o(e,t){return p(e)?e.type==="Identifier"&&!t?e.name:E(e):""}function E(e){return p(e)&&g(e)?e.value:""}function g(e){return e.type==="Literal"&&typeof e.value=="string"}function p(e){return typeof e=="object"&&e!==null&&typeof e.type=="string"}function u(e){const t=e.replace(w,"$1 $2").toLowerCase().split(R).filter(Boolean),r=t.at(-1);return r!==void 0&&(h[r]||h[t.join("")])===!0}function L(e){const t=C.exec(e)?.[0]??"";return e.length>t.length?`${t}${m}`:e}function T(e){return O(e.replace(k,`$1$2${m}`))}function O(e){let t="",r=0;for(;r<e.length;){const i=e[r++];if(t+=i,i!=="?"&&i!=="&")continue;let n=r;for(;n<e.length&&!_.includes(e[n]);)n++;const s=e.slice(r,n),a=s.indexOf("="),c=a>0&&a<s.length-1&&u($(s.slice(0,a)));t+=c?`${s.slice(0,a+1)}${m}`:s,r=n}return t}function $(e){try{return decodeURIComponent(e)}catch{return e}}export{N as maskCodeCredentials};
|