Mehrere Rechenzentren: Konfiguration
Bevor du beginnst
Eine Codesphere-Installation kann mehrere Rechenzentren umfassen. Sie teilen sich einen PostgreSQL-Server, eine Plattform-Domain und eine OpenFGA-Instanz; jedes Rechenzentrum betreibt sein eigenes Kubernetes-Cluster und sein eigenes Ceph-Cluster.
Diese Seite behandelt nur die Unterschiede zu einer Installation mit einem einzelnen Rechenzentrum, den grundlegenden Ablauf beschreibt der Installationsleitfaden. Für das Vorgehen siehe Mehrere Rechenzentren: Installation.
Jedes Rechenzentrum hat seine eigene config.yaml und seine eigene prod.vault.yaml.
Nichts führt sie zusammen: jeder oms install codesphere-Lauf installiert genau ein
Rechenzentrum.
codesphere.domain = cs.example.com
|
+---------------+---------------+
| |
Data center 1 Data center 2
k0s + Ceph cluster A k0s + Ceph cluster B
jumpbox 1 jumpbox 2
config.yaml + its vault config.yaml + its vault
| |
+---------------+---------------+
|
one PostgreSQL server, one OpenFGA
Jedes Rechenzentrum wird normalerweise von seiner eigenen Jumpbox aus betrieben, deshalb sind die Dateinamen unten auf jeder Maschine dieselben. Eine einzelne Jumpbox für die gesamte Installation funktioniert ebenfalls, dann muss jeder rechenzentrumsspezifische Pfad eindeutig gemacht werden, siehe Die Dateien anlegen.
Was geteilt wird
Komponenten
- Der PostgreSQL-Server mit der Codesphere-Datenbank — ihren Rollen, ihrem Schema und jeder Workspace-, Team- und Nutzerzeile. Ein Rechenzentrum installiert und betreibt ihn; jedes andere verbindet sich als externe Datenbank mit ihm.
- Die OpenFGA-Instanz mit den Autorisierungs-Tupeln, zusammen mit der CloudNativePG-Datenbank, die sie mitbringt. Ein Rechenzentrum deployt sie und veröffentlicht sie über sein Gateway; jedes andere ruft diese URL auf.
Gemeinsame Konfiguration
Identisch in der config.yaml jedes Rechenzentrums:
codesphere.domain— ein Plattform-Name für die gesamte Installation.dataCentersunddefaultDataCenterId— die Topologie, die jedes Rechenzentrum kennen muss.codesphere.plans,deployConfig,features,internal,preview,gitProviders,oauth,managedServices— Plattformverhalten, das von der geteilten Datenbank getragen wird.registry— jedes Rechenzentrum zieht dieselben Images aus derselben Registry.
Und identisch in der prod.vault.yaml jedes Rechenzentrums: die Authentifizierungs- und
Verschlüsselungsschlüssel, die Registry-Zugangsdaten und die Rollen der geteilten
Datenbank — jedes Secret, das am anderen Ende von etwas Geteiltem verbraucht wird.
tokenPrivateKey erzeugt die Sitzungen, die Rechenzentrumsgrenzen überschreiten,
mounterHmacSecret und mongoDbPasswordEncryptionKey signieren und verschlüsseln Zeilen
in der geteilten Datenbank, openFgaPresharedKey authentifiziert gegenüber der einen
OpenFGA-Instanz, und jedes Paar aus postgresUser* / postgresPassword* ist eine Rolle
auf dem einen Server.
warnung
Geteilte Werte lassen sich leicht in einer Konfiguration ändern und in der anderen
vergessen. Ein auseinandergelaufener plans-Block ist ein Workspace, der sich im einen
Rechenzentrum anlegen lässt und im anderen nicht, lange nach der Installation; ein
auseinandergelaufener tokenPrivateKey ist eine Nutzerin, die im einen Rechenzentrum
angemeldet ist und vom nächsten abgewiesen wird.
Was jedem Rechenzentrum gehört
Komponenten
Sein eigenes k0s-Cluster, sein eigenes Ceph-Cluster und seine eigenen drei extern erreichbaren Adressen — Plattform-Gateway, Workspace-Gateway und Workspace-SSH-Proxy. Nichts davon wird geteilt, und nichts in der Konfiguration eines Rechenzentrums darf auf die Hosts eines anderen zeigen.
Gemeinsame Konfiguration
dataCenter— die Identität dieses Rechenzentrums.secrets.baseDir, seine age-Identität und seine Vault-Datei.codesphere.workspaceHostingBaseDomain,customDomains.cNameBaseDomainundpublicIp— die Domains und die Adresse, unter denen die Workspaces dieses Rechenzentrums ausgeliefert werden.kubernetes.*,ceph.*,cluster.gatewayundcluster.publicGateway.operations.skip— welche Installer-Schritte dieses Rechenzentrum nie ausführt.
Dazu die Vault-Einträge, die an die Cluster dieses Rechenzentrums gebunden sind, aufgeführt unter Seine eigene Konfiguration weiter unten.
Das erste Rechenzentrum konfigurieren
Das Rechenzentrum, das PostgreSQL betreibt und OpenFGA deployt. Seine Konfiguration ist die übliche Konfiguration für ein einzelnes Rechenzentrum, ergänzt um die Topologie-Liste und die beiden Betreiberrollen.
Geteilte Konfiguration
Trage die vollständige Topologie in dataCenters ein und lege fest, wo neue Teams
landen:
# Byte-identical in config.yaml and config-dc2.yaml
dataCenters:
- id: 1
name: karlsruhe
city: Karlsruhe
countryCode: DE
- id: 2
name: frankfurt
city: Frankfurt
countryCode: DE
defaultDataCenterId: 1
Der Installer weist eine widersprüchliche Liste zurück: doppelte IDs, ein dataCenter,
das in dataCenters fehlt, ein Eintrag, dessen Name oder Stadt von dataCenter
abweicht, oder eine defaultDataCenterId, die nicht in der Liste steht.
warnung
dataCenters ganz wegzulassen ist der eine Fall, der still bleibt: die Liste fällt auf
[dataCenter] zurück und defaultDataCenterId auf dataCenter.id. Die Installation
gelingt, das Cluster ist gesund, und die Plattform verhält sich schlicht wie eine
Installation mit einem einzelnen Rechenzentrum — die Auswahl bietet nur das
Rechenzentrum an, in dem du angemeldet bist. Setze die Liste in jeder
Konfiguration, auch in dieser.
Dieses Rechenzentrum betreibt die beiden geteilten Komponenten. PostgreSQL behält die
übliche Konfiguration postgres.mode: install, und OpenFGA wird über das Gateway
veröffentlicht, damit die anderen Rechenzentren es erreichen:
codesphere:
domain: cs.example.com # shared by the whole installation
openFga:
# deploy defaults to true, apiUrl to the in-cluster service.
expose:
enabled: true
host: openfga.1.cs.example.com
expose.hostmuss auf die Plattform-Gateway-Adresse dieses Rechenzentrums auflösen und ist genau das, was die anderen Rechenzentren inapiUrleintragen. Ein Host unterhalb der Plattform-Domain dieses Rechenzentrums —openfga.1.cs.example.com— wird bereits vom Eintrag*.1.cs.example.comaus DNS-Einträge abgedeckt.- Das Gateway-Zertifikat wird von dem ClusterIssuer ausgestellt, der nach
codesphere.certIssuer.typebenannt ist. Bei ACME muss der Host öffentlich auflösbar sein. Bei einem selbstsignierten Issuer vertrauen die anderen Rechenzentren ihm nicht — siehe deren geteilte Konfiguration. - OpenFGA wird nur genutzt, wenn das Preview-Flag
openfga-authzaktiv ist (siehe Feature-Flags). Ohne dieses Flag lass den Block weg.
warnung
Der Preshared Key ist das, was OpenFGA absichert, sobald es das Cluster verlässt. Ohne
openFgaPresharedKey im Vault wird OpenFGA unauthentifiziert deployt, und das Chart
weigert sich dann, expose.enabled: true zu rendern — die openfga-Anwendung
synchronisiert nicht, statt einen offenen Autorisierungsspeicher zu veröffentlichen.
Füge den Schlüssel hinzu, bevor du OpenFGA exponierst:
SOPS_AGE_KEY_FILE=/etc/codesphere/secrets/age_key.txt \
oms update install-config \
--config /etc/codesphere/config.yaml \
--vault /etc/codesphere/secrets/prod.vault.yaml
Der Rest der geteilten Konfiguration ist das, was auch eine Installation mit einem einzelnen Rechenzentrum verwenden würde. Entscheidend ist, dass das nächste Rechenzentrum sie exakt wiederholt.
Seine eigene Konfiguration
Seine Identität, sein Secrets-Verzeichnis und die Domains und Adressen, unter denen seine eigenen Workspaces ausgeliefert werden:
dataCenter:
id: 1
name: karlsruhe
city: Karlsruhe
countryCode: DE
secrets:
baseDir: /etc/codesphere/secrets
codesphere:
workspaceHostingBaseDomain: 1.example.com
customDomains:
cNameBaseDomain: 1.example.com
publicIp: 203.0.113.20
dataCenter.id steht in jeder Workspace-Zeile der geteilten Datenbank und taucht in den
rechenzentrumsspezifischen Domains auf. dataCenter.name benennt das k0s-Cluster
(codesphere-<dataCenter.name>) und muss deshalb ebenfalls eindeutig sein.
Der Workspace-SSH-Proxy hat keinen eigenen Domain-Schlüssel. Pro Rechenzentrum
konfiguriert wird die Adresse, die sein ssh-workspace-proxy-Service erhält, unter
pcApps; die Domain ist nur ein DNS-Eintrag, der auf diese Adresse zeigt:
pcApps:
applications:
ssh-workspace-proxy:
enabled: true
valuesObject:
service:
enabled: true
type: LoadBalancer
loadBalancerIP: 203.0.113.30
kubernetes.*, ceph.*, cluster.gateway und cluster.publicGateway beschreiben die
eigenen Hosts und Adressen dieses Rechenzentrums, genau wie bei einer Installation mit
einem einzelnen Rechenzentrum.
Jedes weitere Rechenzentrum konfigurieren
Geteilte Konfiguration
Übernimm dataCenters, defaultDataCenterId, codesphere.domain, plans,
deployConfig, die Flag-Blöcke, gitProviders, oauth, managedServices und
registry unverändert aus der Konfiguration des ersten Rechenzentrums.
Richte dieses Rechenzentrum auf den geteilten PostgreSQL-Server, statt einen eigenen zu installieren:
postgres:
mode: external
# An IP address, not a hostname — see the warning below.
serverAddress: 10.10.0.10
port: 5432
# Copied verbatim from the hosting data center's config.yaml.
caCertPem: |
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
postgres.primary und postgres.replica entfallen — sie beschreiben einen Server, den
dieses Rechenzentrum nicht installiert. caCertPem liegt in der Konfiguration, nicht im
Vault, und lässt sich nicht aus dem CA-Schlüssel neu ableiten; kopiere den PEM-Block
also hinüber.
warnung
postgres.serverAddress muss die IP-Adresse des Servers sein, nicht sein
Hostname. Das von oms init install-config erzeugte Serverzertifikat enthält nur
IP-SANs; der Hostname steht im Common Name, den moderne TLS-Clients ignorieren. Ein
Hostname an dieser Stelle führt in jedem Service dieses Rechenzentrums zu einem
Zertifikatsfehler, ohne dass irgendetwas auf die Adresse als Ursache hinweist.
Der Vorgabewert des Assistenten für diese Abfrage ist postgres.example.com:5432 —
ersetze ihn durch die reine IP und setze den Port in postgres.port.
Ändert sich die IP des Servers, muss das Zertifikat für die neue IP neu ausgestellt und
serverAddress in jedem Rechenzentrum angepasst werden, das sich mit ihm verbindet.
Richte es auf die OpenFGA-Instanz, die das erste Rechenzentrum deployt, statt eine eigene zu deployen:
codesphere:
openFga:
deploy: false
apiUrl: https://openfga.1.cs.example.com
# Only with a self-signed cluster issuer: trust the CA that signed
# the OpenFGA gateway certificate.
extraCaPem: |
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----
apiUrl muss der expose.host des betreibenden Rechenzentrums sein. extraCaPem nimmt
dessen cluster.certificates.ca.certPem auf und wird nur gebraucht, wenn
codesphere.certIssuer.type auf self-signed steht — einem ACME-Zertifikat wird
ohnehin vertraut.
Schließlich müssen die geteilten Vault-Einträge byte-identisch zu denen des ersten Rechenzentrums sein. Das Vault abzuleiten statt ein frisches zu erzeugen ist das, was das sicherstellt, siehe Das Vault des zweiten Rechenzentrums ableiten.
Seine eigene Konfiguration
Alles unter Seine eigene Konfiguration oben gilt auch hier, mit
den eigenen Werten dieses Rechenzentrums: ein eindeutiger dataCenter-Block, seine
eigenen Workspace-Domains und publicIp, seine eigenen kubernetes.*, ceph.* und
Gateway-Adressen sowie seine eigene pcApps-SSH-Proxy-Adresse.
Es hat außerdem sein eigenes Vault in seinem eigenen Secrets-Verzeichnis und überspringt den Installer-Schritt für die Komponente, die es nicht betreibt:
secrets:
baseDir: /etc/codesphere/secrets
operations:
skip:
- postgres
secrets.baseDir ist ein Pfad auf der Maschine, die den Installer ausführt; auf der
eigenen Jumpbox dieses Rechenzentrums ist es also derselbe Pfad, den Rechenzentrum 1 auf
seiner Jumpbox verwendet — zwei Verzeichnisse auf zwei Maschinen, jedes mit einem Vault
und einer age-Identität. postgres in operations.skip verhindert, dass jeder Lauf
dieses Rechenzentrums — auch manuelle Wiederholungen — den geteilten Server anzufassen
versucht.
gefahr
Rechenzentren, die von einer Maschine aus installiert werden, dürfen sich kein
secrets.baseDir teilen.
Der Installer liest das Vault aus diesem Verzeichnis und schreibt Ergebnisse dorthin
zurück — der kubernetes-Schritt schreibt kubeConfig, der ceph-Schritt schreibt
sämtliche Ceph-Zugangsdaten. Betreibt eine gemeinsame Jumpbox beide Rechenzentren aus
einem Verzeichnis, überschreibt die Installation des zweiten die Einträge des ersten und
entschlüsselt dessen Vault mit dem age-Schlüssel des ersten. Zur Installationszeit
schlägt nichts fehl, aber der nächste oms install codesphere- oder
oms add-cluster-admin-Lauf für Rechenzentrum 1 liest kubeConfig aus dem Vault und
wendet die Konfiguration von Rechenzentrum 1 auf das Cluster von Rechenzentrum 2 an.
Gib jedem Rechenzentrum dort sein eigenes Verzeichnis — /etc/codesphere/secrets und
/etc/codesphere/secrets-dc2. Der Verzeichnisname benennt auch das Secrets-Verzeichnis,
das auf den Knoten dieses Rechenzentrums abgelegt wird, eindeutige Namen halten die
beiden also auch dort auseinander.
Eine eigene age-Identität pro Vault ist nicht zwingend erforderlich, hält aber den Schaden eines geleakten Schlüssels auf ein Rechenzentrum begrenzt.
Diese Vault-Einträge gehören zu den Clustern dieses Rechenzentrums und müssen für es neu erzeugt werden; jeder hier nicht aufgeführte Eintrag wird geteilt:
| Vault-Eintrag | Zugehöriges Konfigurationsfeld |
|---|---|
selfSignedCaKeyPem | cluster.certificates.ca.certPem |
cephSshPrivateKey | ceph.cephAdmSshKey.publicKey |
acmeEabMacKey | codesphere.certIssuer.acme.eabKeyId |
kubeConfig | — geschrieben vom kubernetes-Schritt oder von oms install k0s --vault |
Alles, was mit ceph, csi oder rgw beginnt | — geschrieben vom ceph-Schritt |
privNixSigningKey, pubNixSigningKey | — nur in wiederhergestellten Vaults vorhanden |
warnung
Ändere ein Konfigurationsfeld und sein Vault-Secret immer als Paar. Die Generatoren
hängen am Vault-Eintrag: fehlt selfSignedCaKeyPem, wird eine neue Ingress-CA erzeugt
und cluster.certificates.ca.certPem überschrieben. Fehlt der Vault-Eintrag, während
die Konfiguration noch das certPem des vorherigen Rechenzentrums trägt, entsteht ein
frischer Schlüssel neben einem veralteten Zertifikat — Ingress liefert dann Zertifikate
aus, die von einer CA signiert sind, der niemand vertraut, sichtbar nur als TLS-Fehler
im Browser. Dasselbe gilt für cephSshPrivateKey / ceph.cephAdmSshKey.publicKey und
für acmeEabMacKey / codesphere.certIssuer.acme.eabKeyId.
DNS-Einträge
codesphere.domain löst auf das Plattform-Gateway eines Rechenzentrums auf.
Workspaces und ihre SSH-Endpunkte lösen pro Rechenzentrum auf, damit der Verkehr eines
Workspace das Cluster erreicht, auf dem er läuft.
Mit der Basis-Domain example.com, codesphere.domain: cs.example.com und sechs
reservierten Adressen:
| Rechenzentrum 1 | Rechenzentrum 2 | |
|---|---|---|
Plattform-Gateway (gateway-controller) | 203.0.113.10 | 198.51.100.10 |
Workspace-Gateway (public-gateway-controller) | 203.0.113.20 | 198.51.100.20 |
Workspace-SSH-Proxy (ssh-workspace-proxy) | 203.0.113.30 | 198.51.100.30 |
lege an:
| Eintrag | Typ | Ziel |
|---|---|---|
cs.example.com, *.cs.example.com | A | 203.0.113.10 |
1.cs.example.com, *.1.cs.example.com | A | 203.0.113.10 |
2.cs.example.com, *.2.cs.example.com | A | 198.51.100.10 |
1.example.com, *.1.example.com | A | 203.0.113.20 |
2.example.com, *.2.example.com | A | 198.51.100.20 |
*.1.ssh.example.com | A | 203.0.113.30 |
*.2.ssh.example.com | A | 198.51.100.30 |
warnung
Die Zeilen <dc-id>.cs.example.com sind die, die übersehen werden. Die Plattform bildet
den Service-Endpunkt jedes Rechenzentrums als <dataCenter.id>.<codesphere.domain> und
der Browser ruft ihn direkt auf, bevor irgendetwas gerendert wird. Ohne expliziten
Eintrag fällt 2.cs.example.com auf die Wildcard *.cs.example.com zurück, löst auf
das Gateway von Rechenzentrum 1 auf, das keine Route dafür hat — und die gesamte
Oberfläche lädt nicht, nicht nur die Workspaces in Rechenzentrum 2.
Das Anlegen von 2.cs.example.com verhindert außerdem, dass *.cs.example.com Namen
darunter abdeckt; *.2.cs.example.com muss deshalb ebenfalls explizit angelegt werden.
Vor der Installation
Prüfe für die Konfiguration jedes Rechenzentrums:
-
dataCenter.idunddataCenter.namesind installationsweit eindeutig. -
dataCentersist vorhanden und in jeder Konfiguration identisch, unddefaultDataCenterIdnennt eine ID, die darin vorkommt. - Der Rest der geteilten Konfiguration — Domain, Plans, Deploy-Konfiguration, Flags, Provider, Managed Services, Registry — ist in jeder Konfiguration identisch.
-
secrets.baseDirenthält das eigene Vault dieses Rechenzentrums, und kein anderes Rechenzentrum wird aus demselben Verzeichnis installiert. - Genau eine Konfiguration hat
postgres.mode: install; jede andere hatmode: external,serverAddressauf die IP des Servers gesetzt,port, ein kopiertescaCertPem, keinprimary/replicaundpostgresinoperations.skip. - Genau eine Konfiguration hat
codesphere.openFga.expose.enabled: true; jede andere hatdeploy: falseund eineapiUrl, die darauf zeigt. - Die Workspace-Domains,
publicIp,kubernetes.*,ceph.*und beide Gateway-Adressen gehören diesem Rechenzentrum. - Die geteilten Vault-Einträge sind byte-identisch; die rechenzentrumsspezifischen sind frisch erzeugt, nicht geerbt.
Validiere anschließend das Dateipaar jedes Rechenzentrums auf der Jumpbox, die es hält:
oms init install-config --validate -c /etc/codesphere/config.yaml \
--vault /etc/codesphere/secrets/prod.vault.yaml
Die Validierung prüft eine Konfiguration für sich allein. Sie erkennt weder einen
doppelten dataCenter.name, noch zwei Rechenzentren, die aus einem Secrets-Verzeichnis
installiert werden, eine fehlende dataCenters-Liste oder ein auseinandergelaufenes
geteiltes Secret — dafür ist die Liste oben da.