Che cos'è Backstage e che cosa non è
Backstage è un framework open source (licenza Apache-2.0) per costruire portali per sviluppatori, nato in Spotify. Il CNCF lo ha accettato l'8 settembre 2020 e dal 15 marzo 2022 è progetto in incubazione, ancora oggi non graduated (pagina del progetto, consultata il 2026-11-13). Il punto da capire prima di tutto: è un framework, non un prodotto da installare. Si crea un'applicazione con npx @backstage/create-app@latest, si aggiungono i plugin nel codice, si compila e si distribuisce. Chi lo adotta gestisce quindi un'applicazione Node con un proprio ciclo di aggiornamenti: l'ultima release al 2026-11-13 è la 1.56.5 (pagina delle release su GitHub).
Le funzioni centrali sono tre, e coincidono con le pagine di panoramica della documentazione: il Software Catalog, che tiene l'inventario di componenti, API e risorse con i loro proprietari; i Software Templates, che creano nuovi progetti dal portale (li ho trattati con un esempio completo nell'articolo 3); e TechDocs, la documentazione scritta in Markdown accanto al codice e mostrata nel portale. Non ho eseguito create-app: richiede l'installazione di un intero progetto, e qui mi limito a ciò che si verifica senza. In questo articolo ho validato con i pacchetti ufficiali il catalogo e la configurazione, con mkdocs la documentazione e con helm template il rilascio.
Come è fatto: applicazione, backend e plugin
Un'installazione si compone di tre parti:
- L'applicazione frontend, una pagina React che si personalizza con temi, layout e plugin.
- Il backend, un processo Node.js che espone le API, parla con il database e ospita i plugin lato server; nel sistema backend attuale i moduli si aggiungono con
backend.add(import('...'))nel punto d'ingresso. - I plugin, pacchetti con una parte frontend, una backend o entrambe; il catalogo, il generatore di progetti e TechDocs sono essi stessi plugin.
La conseguenza pratica è che il portale non ha un pannello per attivare un'integrazione: ogni plugin è una dipendenza da installare, configurare e aggiornare insieme al resto. Il vantaggio è la componibilità, il costo è che le versioni dei plugin devono restare compatibili con quella del nucleo.
La configurazione sta in app-config.yaml. Il file seguente è un esempio minimo per un'installazione con autenticazione GitHub e database PostgreSQL; i valori riservati sono variabili d'ambiente, con la sintassi ${NOME}. Due dettagli contano. Il blocco signIn.resolvers è indispensabile: la documentazione spiega che ogni provider di autenticazione, per impostazione predefinita, serve solo a delegare l'accesso a sistemi esterni, e che per far entrare gli utenti bisogna abilitare il login e dire come mappare l'identità esterna su un'entità utente del catalogo. E il provider «guest» incluso in create-app condivide un'unica identità fra tutti e non va usato in produzione.
app:
title: Portale sviluppatori di esempio
baseUrl: https://backstage.example.com
backend:
baseUrl: https://backstage.example.com
listen:
port: 7007
database:
client: pg
connection:
host: ${POSTGRES_HOST}
port: ${POSTGRES_PORT}
user: ${POSTGRES_USER}
password: ${POSTGRES_PASSWORD}
integrations:
github:
- host: github.com
token: ${GITHUB_TOKEN}
auth:
environment: production
providers:
github:
production:
clientId: ${AUTH_GITHUB_CLIENT_ID}
clientSecret: ${AUTH_GITHUB_CLIENT_SECRET}
signIn:
resolvers:
- resolver: usernameMatchingUserEntityName
catalog:
rules:
- allow: [Component, System, API, Resource, Location, Group, User]
locations:
- type: url
target: https://github.com/example-org/catalogo/blob/main/catalog.yaml
Per sapere che cosa succede quando una variabile manca, ho caricato il file con il caricatore di configurazione ufficiale (@backstage/config-loader 1.11.4) e ho letto quattro valori obbligatori, una volta con tutte le variabili impostate e una senza POSTGRES_PASSWORD. Per avere un ambiente pulito ho lanciato lo script con env -i, che passa solo le variabili elencate.
// Carica app-config.yaml con il caricatore di configurazione di Backstage
// e controlla i valori obbligatori, uno per uno.
const path = require("path");
const mod = (n) => require(path.join(__dirname, "node_modules", n));
const { ConfigSources } = mod("@backstage/config-loader");
const OBBLIGATORI = {
"backend.database.connection.host": (c) => c.getString("backend.database.connection.host"),
"backend.database.connection.password": (c) => c.getString("backend.database.connection.password"),
"integrations.github[0].token": (c) => c.getConfigArray("integrations.github")[0].getString("token"),
"auth.providers.github.production.clientSecret": (c) => c.getString("auth.providers.github.production.clientSecret"),
};
(async () => {
const sorgente = ConfigSources.default({ argv: ["--config", process.argv[2]], remote: undefined });
const config = await ConfigSources.toConfig(sorgente);
for (const [chiave, leggi] of Object.entries(OBBLIGATORI)) {
try {
leggi(config);
console.log(`${chiave}: presente`);
} catch (e) {
console.log(`${chiave}: ${e.message}`);
process.exitCode = 1;
}
}
config.close();
})();
// Output:
// [tutte le variabili impostate]
// backend.database.connection.host: presente
// backend.database.connection.password: presente
// integrations.github[0].token: presente
// auth.providers.github.production.clientSecret: presente
// uscita: 0
// [senza POSTGRES_PASSWORD]
// backend.database.connection.host: presente
// backend.database.connection.password: Missing required config value at 'backend.database.connection.password' in 'app-config.yaml'
// integrations.github[0].token: presente
// auth.providers.github.production.clientSecret: presente
// uscita: 1
Senza la variabile, il caricatore non si ferma all'avvio: sostituisce il segnaposto con un valore assente, e l'errore compare solo quando qualcuno prova a leggere quel valore («Missing required config value»). Un controllo come questo, lanciato nella pipeline prima del rilascio, trasforma un guasto all'avvio in un rifiuto prima del deploy. Il token dell'integrazione GitHub è il modo semplice; per un'organizzazione la documentazione propone anche le GitHub App, con permessi più stretti.
Software Catalog: il descrittore e le relazioni
Ogni voce del catalogo è un file YAML, tipicamente catalog-info.yaml nella radice del repository. I tipi di entità sono nove: Component, API, Resource, System, Domain, Group, User, Location e Template, quest'ultimo per i generatori di progetti. Quelli di uso quotidiano sono:
- Component: un servizio, un sito, una libreria, un flusso di dati.
- API: il confine fra componenti, in un formato leggibile da macchina (OpenAPI, gRPC, GraphQL).
- Resource: l'infrastruttura di cui un componente ha bisogno, per esempio un database.
- System: un insieme di componenti e risorse che espone una o più API pubbliche, e che permette di nascondere ai consumatori i dettagli interni.
- Group e User: le persone e i team a cui le altre entità rimandano come proprietari.
Sono le definizioni del modello di sistema della documentazione. La parte che conta di più nel lavoro quotidiano è il «proprietario» e il fatto che il campo spec.owner è «a scopo di visualizzazione»: la documentazione precisa che non va usato per assegnare autorizzazioni nei sistemi in esecuzione. È un'informazione di responsabilità, non un permesso.
Un file di catalogo contiene molti riferimenti fra entità, e ogni riferimento è una stringa nella forma [kind:][namespace/]nome. Se il kind manca, vale un predefinito che dipende dal campo: owner rimanda per impostazione predefinita a un Group, dependsOn a un Component (per una risorsa serve scrivere resource:). L'esempio seguente descrive un piccolo sistema con due team, due componenti, due API e un database. Il checker che lo accompagna usa i validatori ufficiali di @backstage/catalog-model 1.10.2 per lo schema, e poi verifica che ogni riferimento punti a un'entità esistente, cosa che lo schema non controlla.
apiVersion: backstage.io/v1alpha1
kind: Group
metadata:
name: team-checkout
spec:
type: team
children: []
---
apiVersion: backstage.io/v1alpha1
kind: Group
metadata:
name: team-inventario
spec:
type: team
children: []
---
apiVersion: backstage.io/v1alpha1
kind: System
metadata:
name: e-commerce
spec:
owner: team-checkout
---
apiVersion: backstage.io/v1alpha1
kind: Component
metadata:
name: checkout-service
description: Gestisce il carrello e il pagamento
annotations:
github.com/project-slug: example-org/checkout-service
backstage.io/techdocs-ref: dir:.
tags: [typescript, pagamenti]
spec:
type: service
lifecycle: production
owner: team-checkout
system: e-commerce
providesApis: [checkout-api]
consumesApis: [inventario-api]
dependsOn:
- resource:checkout-db
- component:inventario-service
---
apiVersion: backstage.io/v1alpha1
kind: Component
metadata:
name: inventario-service
spec:
type: service
lifecycle: production
owner: team-inventario
system: e-commerce
providesApis: [inventario-api]
---
apiVersion: backstage.io/v1alpha1
kind: API
metadata:
name: checkout-api
spec:
type: openapi
lifecycle: production
owner: team-checkout
system: e-commerce
definition: |
openapi: 3.0.3
info: {title: Checkout, version: 1.0.0}
paths: {}
---
apiVersion: backstage.io/v1alpha1
kind: API
metadata:
name: inventario-api
spec:
type: openapi
lifecycle: production
owner: team-inventario
system: e-commerce
definition: |
openapi: 3.0.3
info: {title: Inventario, version: 1.0.0}
paths: {}
---
apiVersion: backstage.io/v1alpha1
kind: Resource
metadata:
name: checkout-db
spec:
type: database
owner: team-checkout
system: e-commerce
Il file mostra tre convenzioni. Le annotazioni (github.com/project-slug, backstage.io/techdocs-ref) sono chiavi lette dai plugin: lo schema le accetta tutte, quindi un'annotazione scritta male non produce errori ma il plugin corrispondente non trova nulla. Le due dipendenze di checkout-service usano prefissi diversi (resource: e component:) perché il predefinito di dependsOn è Component. E le API portano la definizione dentro la voce, mentre nei progetti reali si preferisce spesso un riferimento a un file.
// Valida un file di catalogo con i validatori ufficiali di Backstage e controlla che ogni
// riferimento fra entità (owner, system, API, dipendenze) punti a un'entità che esiste.
const fs = require("fs");
const path = require("path");
const mod = (n) => require(path.join(__dirname, "node_modules", n));
const YAML = mod("yaml");
const cm = mod("@backstage/catalog-model");
const VALIDATORI = {
Component: cm.componentEntityV1alpha1Validator, API: cm.apiEntityV1alpha1Validator,
Resource: cm.resourceEntityV1alpha1Validator, System: cm.systemEntityV1alpha1Validator,
Group: cm.groupEntityV1alpha1Validator,
};
// campo -> kind predefinito quando il riferimento non lo dichiara (regole della documentazione)
const CAMPI = { owner: "Group", system: "System", providesApis: "API", consumesApis: "API", dependsOn: "Component" };
async function main(file) {
const entita = YAML.parseAllDocuments(fs.readFileSync(file, "utf8")).map((d) => d.toJS());
let errori = 0;
for (const e of entita) {
try { await VALIDATORI[e.kind].check(e); }
catch (err) { errori++; console.log(`${e.kind} ${e.metadata.name}: schema non valido (${err.message})`); }
}
const esistenti = new Set(entita.map((e) => cm.stringifyEntityRef(e)));
let riferimenti = 0;
for (const e of entita) {
for (const [campo, kind] of Object.entries(CAMPI)) {
for (const ref of [].concat(e.spec[campo] ?? [])) {
riferimenti++;
const completo = cm.stringifyEntityRef(cm.parseEntityRef(ref, { defaultKind: kind, defaultNamespace: "default" }));
if (!esistenti.has(completo)) { errori++; console.log(`${e.kind} ${e.metadata.name}: ${campo} -> ${completo} non esiste`); }
}
}
}
console.log(`${entita.length} entità, ${riferimenti} riferimenti, ${errori} problemi`);
process.exitCode = errori ? 1 : 0;
}
main(process.argv[2]);
// Output:
// [catalog.yaml]
// 8 entità, 16 riferimenti, 0 problemi
// uscita: 0
// [catalog-sbagliato.yaml]
// Component checkout-service: owner -> group:default/team-chekout non esiste
// Component checkout-service: dependsOn -> resource:default/checkout-db non esiste
// 7 entità, 14 riferimenti, 2 problemi
// uscita: 1
Il file corretto passa: 8 entità e 16 riferimenti, nessun problema. Nella seconda esecuzione ho rovinato una copia togliendo il database e scrivendo team-chekout al posto del proprietario. Lo schema non protesta (le due entità sono strutturalmente valide), ed è il controllo dei riferimenti a trovarli entrambi. È il motivo per cui conviene far girare un controllo come questo in una pipeline, sul repository che contiene il catalogo: i riferimenti rotti sono il difetto più silenzioso di un inventario, ed è quello che il catalogo di cui parla l'articolo 6 deve evitare.
TechDocs: documentazione accanto al codice, e un rischio da conoscere
TechDocs prende i file Markdown del repository, li compila con MkDocs e li mostra nella pagina del componente. Il collegamento passa dall'annotazione backstage.io/techdocs-ref: dir:., che dice che la documentazione sta nella stessa cartella del descrittore. Il vantaggio è che i documenti si modificano nella stessa richiesta di modifica del codice. Per la produzione la documentazione di Backstage raccomanda di non farli costruire al backend: un passo della pipeline genera i file statici con techdocs-cli e li pubblica su uno storage in cloud, da cui il backend li legge.
Il file mkdocs.yml qui sotto descrive il sito: un titolo, un menu di navigazione e il plugin techdocs-core, che prepara MkDocs per TechDocs. L'ho costruito con mkdocs 1.6.1 e mkdocs-techdocs-core 1.7.1 in un ambiente virtuale temporaneo, con cinque pagine di prova, in modalità --strict: ogni avviso diventa un errore. Il secondo caso è lo stesso file con una voce di menu che punta a una pagina inesistente.
site_name: Checkout Service
site_description: Documentazione tecnica del servizio checkout
nav:
- Home: index.md
- Architettura:
- Panoramica: architecture/overview.md
- Sviluppo:
- Primo avvio: development/getting-started.md
- Operazioni:
- Runbook: operations/runbook.md
- ADR:
- "001 - Scelta del database": adr/001-database.md
plugins:
- techdocs-core
# Output:
# [mkdocs.yml]
# uscita: 0
# [mkdocs-rotto.yml]
# WARNING - A reference to 'operations/runbook-mancante.md' is included in the 'nav' configuration, which is not found in the documentation files.
# Aborted with 1 warnings in strict mode!
# uscita: 1
Senza --strict un riferimento rotto nel menu produce solo un avviso e il sito si genera lo stesso, con un link morto: con l'opzione, la pipeline si ferma. Una precisazione: per generare l'output da pubblicare, la documentazione di TechDocs chiede di usare techdocs-cli (o il contenitore ufficiale), perché aggiunge un file di metadati necessario al lettore. Il mio controllo vale per la struttura del sito, non sostituisce quel passo.
Il rischio riguarda il motore. Il 17 aprile 2026 i maintainer di Backstage hanno aperto una richiesta di commenti (RFC #33990, ancora aperta il 2026-11-13) in cui scrivono che MkDocs non ha rilasci dalla versione 1.6.1 dell'agosto 2024, che la riscrittura 2.0 proposta eliminerebbe il sistema di plugin (compreso mkdocs-techdocs-core) e che il tema Material su cui TechDocs si appoggia è in sola manutenzione; propongono di passare a Zensical, un motore che legge mkdocs.yml. Anche l'avviso che il pacchetto Material stampa a ogni build, e che compare nelle mie esecuzioni, va nella stessa direzione. In pratica: fissa le versioni di MkDocs e del tema, genera la documentazione in pipeline e non usare estensioni esotiche, così il giorno del cambio di motore il lavoro resta contenuto.
Distribuire Backstage su Kubernetes con Helm
La documentazione descrive il metodo che Spotify usa: costruire un'immagine Docker, pubblicarla su un registro, citarla in un Deployment Kubernetes e applicarlo. Esiste anche un chart Helm mantenuto dalla comunità nel repository backstage/charts (versione 2.10.2 al 2026-11-13). Qui il punto non è il chart ma i valori: sono lo schema da adattare, e li ho resi con helm template (helm 3.16.0, nessun cluster), che produce i manifest senza applicarli.
backstage:
image:
registry: ghcr.io
repository: example-org/backstage
tag: "1.0.0"
replicas: 2
resources:
requests:
cpu: 500m
memory: 512Mi
limits:
cpu: "1"
memory: 1Gi
extraEnvVars:
- name: POSTGRES_HOST
valueFrom:
secretKeyRef:
name: backstage-db
key: host
- name: GITHUB_TOKEN
valueFrom:
secretKeyRef:
name: backstage-github
key: token
ingress:
enabled: true
className: nginx
host: backstage.example.com
tls:
enabled: true
secretName: backstage-tls
postgresql:
enabled: false
# Output (helm template backstage backstage/backstage --version 2.10.2 -f values-backstage.yaml | grep -E ...):
# kind: Service
# kind: Deployment
# replicas: 2
# image: ghcr.io/example-org/backstage:1.0.0
# kind: Ingress
# ingressClassName: "nginx"
# secretName: backstage-tls
# - host: backstage.example.com
Quattro scelte nel file. L'immagine ha un tag fisso e non latest, perché il valore predefinito del chart è proprio latest e un riavvio potrebbe portare una versione diversa da quella provata. Le credenziali arrivano da secretKeyRef, non scritte nel file. Il blocco ingress sta alla radice dei valori e non sotto backstage, e tls è un oggetto con enabled e secretName, non una lista come nell'Ingress di Kubernetes. Infine postgresql.enabled: false: il sottochart PostgreSQL incluso usa per impostazione predefinita l'immagine docker.io/bitnamilegacy/postgresql, e per un portale che conserva il catalogo conviene un database gestito da te, con i backup che ne conseguono.
La terza scelta è anche l'errore più facile da commettere. Con i valori sotto, che mettono l'Ingress dentro backstage, il chart rifiuta il file:
backstage:
image:
registry: ghcr.io
repository: example-org/backstage
tag: "1.0.0"
replicas: 2
ingress:
enabled: true
host: backstage.example.com
tls:
- secretName: backstage-tls
hosts:
- backstage.example.com
# Output (helm template ... -f values-sbagliato.yaml):
# Error: values don't meet the specifications of the schema(s) in the following chart(s):
# backstage:
# - backstage: Additional property ingress is not allowed
Il chart ha uno schema dei valori che respinge le chiavi sconosciute: un errore che con altri chart passerebbe in silenzio e lascerebbe l'applicazione senza Ingress. Il messaggio nomina la chiave sbagliata, non la causa, quindi conviene sapere dove cercare. La validazione dei manifest generati contro lo schema di Kubernetes, con kubeconform, è il passo successivo e l'ho mostrata nell'articolo 2.
Quando non installare Backstage: un catalogo senza portale, e dove ha ceduto
Il repo di questo sito non usa Backstage, e conviene dire perché con un esempio. Ha tre servizi, un solo
manutentore e un catalogo da gestire a mano: i documenti in docs/ con un indice per aspetto,
un file CLAUDE.md che li mappa, e un registro dei contenuti. Non c'è un portale perché i
lettori del catalogo sono uno (l'autore) e gli agenti automatici che lavorano sul repo, e per entrambi un
file di testo ben indicizzato è più economico di un'applicazione Node con il suo database.
Il costo di un portale, contato
- Un servizio in più da far girare e aggiornare. Backstage è un'app Node con un backend, un database e plugin con versioni proprie. Aggiornare un plugin rotto da un aggiornamento del core è lavoro ricorrente.
- Un modello di dati da mantenere. Ogni componente richiede un
catalog-info.yamle un proprietario. Con tre servizi i descrittori costerebbero più di quanto fa risparmiare la ricerca. - Il beneficio cresce con il numero di proprietari. Il valore del catalogo è rispondere a «di chi è questo servizio e come lo uso»: vale quando la risposta non sta nella testa di chi legge.
Le tre voci hanno una cosa in comune: sono costi che si pagano ogni mese e non una volta sola, mentre il beneficio compare solo quando qualcuno cerca davvero qualcosa nel catalogo. Prima di installare un portale conviene stimare quanto spesso, e da quante persone diverse, viene cercata la risposta alla domanda «di chi è questo servizio e come lo uso».
Dove il catalogo manuale ha ceduto: due fonti di verità
Il difetto che un catalogo vero previene si è presentato lo stesso. Il catalogo degli strumenti business è un file JSON in due copie: una canonica nel backend e una nel frontend, ricopiata sopra la seconda a ogni build da uno script di prebuild. Chi modificava solo la copia del frontend vedeva la modifica sovrascritta senza un errore: i nuovi strumenti non comparivano nella pagina del catalogo e nessun test falliva. La regola scritta nel progetto è «aggiungi sempre al file del backend, poi rigenera la copia». È la stessa cosa che Backstage risolve con il principio di una sola origine per l'entità, ottenuto qui con una regola e uno script anziché con un prodotto.
Il discrimine. Un portale si giustifica quando i servizi sono più di quanti una persona tiene a mente e quando almeno tre team hanno bisogno di scoprire gli strumenti degli altri (una soglia indicativa, mia, non misurata). Sotto quella soglia la domanda utile non è «quale portale» ma «dove sta l'unica copia di ogni dato, e che cosa succede se qualcuno modifica quella sbagliata», e la risposta è un test che fallisce, non un portale.
Che cosa installare per primo
Parti con il minimo: catalogo, TechDocs e due o tre plugin che rispondono a una domanda che i tuoi sviluppatori fanno davvero (di solito lo stato della pipeline e dove gira il servizio). Aggiungi un plugin alla volta, in base alle richieste, e dopo ogni aggiunta controlla due cose: quanto costa l'aggiornamento e se qualcuno lo usa. Un portale troppo ricco al lancio confonde invece di aiutare, ed è un giudizio mio, non un risultato di ricerca. Le metriche per capire se il portale sta servendo sono quelle dell'articolo 7.
Che cosa sai fare adesso
Sai che Backstage è un framework da compilare e gestire, e con quali parti (applicazione, backend, plugin). Sai scrivere un catalogo e verificarne schema e riferimenti con i validatori ufficiali, controllare in pipeline che la configurazione sia completa, e proteggere il sito TechDocs da un menu rotto. Sai impostare i valori Helm per un rilascio e riconoscere i due errori tipici (Ingress al posto sbagliato, tag mobile). Il prossimo articolo allarga lo sguardo all'infrastruttura come codice, la parte che il portale chiama quando una richiesta deve creare qualcosa.
Domande frequenti
Backstage è un prodotto da installare?
No, è un framework: si crea un'applicazione Node con @backstage/create-app, si aggiungono i plugin nel codice e si distribuisce. Chi lo adotta ne gestisce gli aggiornamenti e la compatibilità fra plugin e nucleo.
Che cosa fa il Software Catalog?
Tiene l'inventario di componenti, API, risorse, sistemi e team, descritti da file YAML nei repository. Il campo owner indica la responsabilità ed è a scopo di visualizzazione: non assegna permessi nei sistemi in esecuzione.
Come si distribuisce Backstage in produzione?
La documentazione descrive la costruzione di un'immagine Docker, la pubblicazione su un registro e un Deployment Kubernetes; esiste anche un chart Helm della comunità. Servono un database PostgreSQL, un autenticatore con la risoluzione dell'identità e un tag di immagine fisso.
TechDocs è a rischio per il futuro di MkDocs?
È un rischio dichiarato dai maintainer di Backstage: MkDocs non ha rilasci dal 1.6.1 (agosto 2024) e la versione 2.0 proposta toglierebbe i plugin. Un'RFC aperta a aprile 2026 valuta il passaggio a Zensical. Conviene fissare le versioni e generare la documentazione in pipeline.
Nella stessa serie trovi anche l'introduzione alla piattaforma interna, la developer experience e i cicli di feedback, il piano di implementazione di una IDP e il confronto fra AI on-prem e cloud.
Fonti
- Backstage: Descriptor Format of Catalog Entities - campi
spec.ownerespec.dependsOn, kind predefiniti, scopo del campo owner, consultata il 2026-11-13 - Backstage: System Model - definizione di Component, API, Resource, System, Group e User, consultata il 2026-11-13
- Backstage: Entity References - forma
[kind:][namespace/]nome, consultata il 2026-11-13 - Backstage: Sign-in Identities and Resolvers - login con risoluzione dell'identità, provider guest non per la produzione, consultata il 2026-11-13
- Backstage: TechDocs Architecture - distribuzione raccomandata con generazione in pipeline e storage in cloud, uso di
techdocs-cli, consultata il 2026-11-13 - backstage/backstage, issue 33990: RFC su Zensical come motore di TechDocs - stato di MkDocs e proposta dei maintainer, consultata il 2026-11-13
- Backstage: Deploying Backstage - il metodo con immagine Docker e Deployment, consultata il 2026-11-13
- backstage/charts - chart Helm 2.10.2, struttura dei valori e schema, consultata il 2026-11-13
- CNCF: Backstage - date di accettazione (2020-09-08) e di passaggio a incubazione (2022-03-15), consultata il 2026-11-13
Gli script sono stati eseguiti due volte con uscita identica (Node 24 con @backstage/catalog-model 1.10.2, @backstage/config-loader 1.11.4 e yaml; mkdocs 1.6.1 con mkdocs-techdocs-core 1.7.1; helm 3.16.0 con helm template, senza cluster). create-app, l'avvio di Backstage e il rilascio su un cluster non sono stati eseguiti: i valori Helm sono uno schema da adattare. I nomi di organizzazione e di dominio sono inventati.

Commenti
Caricamento commenti...
Accedi per commentare