Poznámka:
Přístup k této stránce vyžaduje autorizaci. Můžete se zkusit přihlásit nebo změnit adresáře.
Přístup k této stránce vyžaduje autorizaci. Můžete zkusit změnit adresáře.
Platí pro:SQL Server v Linuxu
Tento článek obsahuje osvědčené postupy a pokyny pro spouštění kontejnerů SQL Serveru v Kubernetes se stavovými sadami. V Kubernetes doporučujeme nasadit jeden kontejner (instanci) SQL Serveru na pod. Proto máte v clusteru Kubernetes nasazenou jednu instanci SQL Serveru na pod.
Doporučení skriptu nasazení je podobně nasadit jednu instanci SQL Serveru nastavením hodnoty replicas na 1. Pokud jako hodnotu 1 zadáte číslo větší než replicas, získáte tolik instancí SQL Serveru s korelovanými názvy. Pokud jste například v následujícím skriptu přiřadili číslo 2 jako hodnotu pro replicas, nasadili byste dva pody SQL Serveru s názvy mssql-0 a mssql-1.
Dalším důvodem, proč doporučujeme jeden SQL Server pro každý skript nasazení, je povolit změny hodnot konfigurace, edice, příznaků trasování a dalších nastavení nezávisle pro každou nasazenou instanci SQL Serveru.
V následujícím příkladu by název úlohy StatefulSet měl odpovídat hodnotě .spec.template.metadata.labels, která je v tomto případě mssql. Další informace viz StatefulSets.
Důležitý
Proměnná prostředí SA_PASSWORD je zastaralá. Místo toho použijte MSSQL_SA_PASSWORD.
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: mssql # name of the StatefulSet workload, the SQL Server instance name is derived from this. We suggest to keep this name same as the .spec.template.metadata.labels, .spec.selector.matchLabels and .spec.serviceName to avoid confusion.
spec:
serviceName: "mssql" # serviceName is the name of the service that governs this StatefulSet. This service must exist before the StatefulSet, and is responsible for the network identity of the set.
replicas: 1 # only one pod, with one SQL Server instance deployed.
selector:
matchLabels:
app: mssql # this has to be the same as .spec.template.metadata.labels
template:
metadata:
labels:
app: mssql # this has to be the same as .spec.selector.matchLabels. See <https://kubernetes.io/docs/concepts/workloads/controllers/statefulset/>:
spec:
securityContext:
fsGroup: 10001
containers:
- name: mssql # container name within the pod.
image: mcr.microsoft.com/mssql/server:2022-latest
ports:
- containerPort: 1433
name: tcpsql
env:
- name: ACCEPT_EULA
value: "Y"
- name: MSSQL_ENABLE_HADR
value: "1"
- name: MSSQL_AGENT_ENABLED
value: "1"
- name: MSSQL_SA_PASSWORD
valueFrom:
secretKeyRef:
name: mssql
key: MSSQL_SA_PASSWORD
volumeMounts:
- name: mssql
mountPath: "/var/opt/mssql"
volumeClaimTemplates:
- metadata:
name: mssql
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
Pokud se stále rozhodnete nasadit více než jednu repliku instance SQL Serveru pomocí stejného nasazení, tento scénář je popsaný v další části. Jedná se však o samostatné samostatné instance SQL Serveru a nikoli repliky (na rozdíl od replik skupiny dostupnosti v SQL Serveru).
Volba typu úlohy
Volba správného typu nasazení úlohy nemá vliv na výkon, ale StatefulSet poskytuje požadavky na stálost identity.
Pracovní zátěže StatefulSet
SQL Server je databázová aplikace, a proto by se měla většinou nasadit jako typ StatefulSet. Nasazení úloh jako StatefulSet pomáhá poskytovat funkce, jako jsou jedinečné síťové identifikace, trvalé a stabilní úložiště a další. Další informace o tomto typu úlohy najdete v dokumentaci Kubernetes.
Při nasazování více než jedné repliky kontejnerů SQL Serveru pomocí stejného skriptu YAML nasazení jako úloha StatefulSet je důležitým parametrem, který je potřeba vzít v úvahu, je zásady správy podů, tj. .spec.podManagementPolicy.
Pro toto nastavení jsou možné dvě hodnoty:
OrderedReady: Jedná se o výchozí hodnotu a chování je uvedeno v zárukách nasazení a škálování.
Paralelní: Jedná se o alternativní zásadu, která vytváří a spouští pody (v tomto případě pody SQL Serveru) paralelně, aniž by se čekalo na vytvoření dalších podů podobně, během ukončení se všechny pody odstraní paralelně. Tuto možnost můžete použít, když nasazujete instance SQL Serveru, které jsou nezávislé na sobě, a pokud nemáte v úmyslu postupovat podle pořadí spuštění nebo odstranění instancí SQL Serveru.
apiVersion: apps/v1 kind: StatefulSet metadata: name: mssql spec: serviceName: "mssql" replicas: 2 # two independent SQL Server instances to be deployed podManagementPolicy: Parallel selector: matchLabels: app: mssql template: metadata: labels: app: mssql spec: securityContext: fsGroup: 10001 containers: - name: mssql image: mcr.microsoft.com/mssql/server:2022-latest ports: - containerPort: 1433 name: tcpsql env: - name: ACCEPT_EULA value: "Y" - name: MSSQL_ENABLE_HADR value: "1" - name: MSSQL_AGENT_ENABLED value: "1" - name: MSSQL_SA_PASSWORD valueFrom: secretKeyRef: name: mssql key: MSSQL_SA_PASSWORD volumeMounts: - name: mssql mountPath: "/var/opt/mssql" volumeClaimTemplates: - metadata: name: mssql spec: accessModes: - ReadWriteOnce resources: requests: storage: 8Gi
Vzhledem k tomu, že pody SQL Serveru nasazené v Kubernetes jsou nezávislé na sobě, Parallel je hodnota běžně používaná pro podManagementPolicy.
Následující ukázka je příkladem výstupu pro kubectl get all, ihned po vytvoření podů pomocí zásady paralelního provedení:
NAME READY STATUS RESTARTS AGE
pod/mssql-0 0/1 ContainerCreating 0 4s
pod/mssql-1 0/1 ContainerCreating 0 4s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kubernetes ClusterIP 201.0.0.1 <none> 443/TCP 61d
NAME READY AGE
statefulset.apps/mssql 1/1 4s
Úlohy nasazení
Typ nasazení pro SQL Server můžete použít ve scénářích, kdy chcete nasadit kontejnery SQL Serveru jako bezstavové databázové aplikace, například v případě, že trvalost dat není kritická. Některé takové příklady jsou určené pro účely testování, kontroly kvality nebo CI/CD.
Izolace prostřednictvím oborů názvů
Jmenné prostory poskytují mechanismus pro izolaci skupin prostředků v rámci jednoho clusteru Kubernetes. Další informace o jmenných prostorech a jejich užití najdete v tématu Jmenné prostory.
Z pohledu SQL Serveru, pokud plánujete spouštět pody SQL Serveru v clusteru Kubernetes, který také hostuje další prostředky, měli byste pody SQL Serveru spouštět ve svém vlastním oboru názvů pro usnadnění správy a administrace. Představte si například, že máte několik oddělení, které sdílí stejný cluster Kubernetes, a chcete nasadit instanci SQL Serveru pro prodejní tým a další pro marketingový tým. Vytvoříte dva obory názvů s názvem sales a marketing, jak je znázorněno v následujícím příkladu:
kubectl create namespace sales
kubectl create namespace marketing
Chcete-li zkontrolovat, že obory názvů byly vytvořeny, spusťte kubectl get namespacesa zobrazí se seznam podobný následujícímu výstupu.
NAME STATUS AGE
default Active 39d
kube-node-lease Active 39d
kube-public Active 39d
kube-system Active 39d
marketing Active 7s
sales Active 26m
Teď můžete nasadit kontejnery SQL Serveru v každém z těchto oborů názvů pomocí ukázkového YAML uvedeného v následujícím příkladu. Všimněte si, že metadata namespace jsou přidána do YAML souboru nasazení, takže všechny kontejnery a služby tohoto nasazení jsou nasazené ve jmenném prostoru sales.
kind: StorageClass
apiVersion: storage.k8s.io/v1
metadata:
name: azure-disk
provisioner: kubernetes.io/azure-disk
parameters:
storageAccountType: Standard_LRS
kind: Managed
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: mssql-sales
namespace: sales
labels:
app: mssql-sales
spec:
serviceName: "mssql-sales"
replicas: 1
selector:
matchLabels:
app: mssql-sales
template:
metadata:
labels:
app: mssql-sales
spec:
securityContext:
fsGroup: 10001
containers:
- name: mssql-sales
image: mcr.microsoft.com/mssql/server:2022-latest
ports:
- containerPort: 1433
name: tcpsql
env:
- name: ACCEPT_EULA
value: "Y"
- name: MSSQL_ENABLE_HADR
value: "1"
- name: MSSQL_AGENT_ENABLED
value: "1"
- name: MSSQL_SA_PASSWORD
valueFrom:
secretKeyRef:
name: mssql
key: MSSQL_SA_PASSWORD
volumeMounts:
- name: mssql
mountPath: "/var/opt/mssql"
volumeClaimTemplates:
- metadata:
name: mssql
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
---
apiVersion: v1
kind: Service
metadata:
name: mssql-sales-0
namespace: sales
spec:
type: LoadBalancer
selector:
statefulset.kubernetes.io/pod-name: mssql-sales-0
ports:
- protocol: TCP
port: 1433
targetPort: 1433
name: tcpsql
Pokud chcete zobrazit prostředky, můžete spustit příkaz kubectl get all se zadaným oborem názvů a zobrazit tyto prostředky:
kubectl get all -n sales
NAME READY STATUS RESTARTS AGE
pod/mssql-sales-0 1/1 Running 0 17m
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/mssql-sales-0 LoadBalancer 10.0.251.120 20.23.79.52 1433:32052/TCP 17m
NAME READY AGE
statefulset.apps/mssql-sales 1/1 17m
Obory názvů se dají použít také k omezení prostředků a podů vytvořených v rámci oboru názvů pomocí rozsahu omezení nebo zásad kvót prostředků ke správě celkového vytváření prostředků v rámci oboru názvů.
Konfigurace kvality služby pro pod
Při nasazování více podů do jednoho clusteru Kubernetes musíte odpovídajícím způsobem sdílet prostředky, abyste zajistili efektivní provoz clusteru Kubernetes. Pody můžete nakonfigurovat tak, aby byly přiřazeny ke konkrétní technologii QoS (Quality of Service).
Kubernetes používá třídy QoS k rozhodování o plánování a vyřazování podů. Další informace o různých třídách QoS najdete v tématu Konfigurace kvality služby pro pody.
Z pohledu SQL Serveru doporučujeme nasadit pody SQL Serveru s QoS označeným jako Guaranteed pro produkční úlohy. Vzhledem k tomu, že pod SQL Serveru má spuštěnou pouze jednu instanci kontejneru SYSTÉMU SQL Server, která zajistí zaručenou technologii QoS pro tento pod, musíte zadat procesor a paměť požadavky pro kontejner, který by se měl rovnat limitům paměti a procesoru . Tím zajistíte, že uzly poskytují a přidělí požadované prostředky zadané během nasazení a mají předvídatelný výkon pro SQL Server pody.
Tady je ukázka nasazení YAML, která nasadí jeden kontejner SQL Serveru ve výchozím oboru názvů, a protože požadavky na prostředky nebyly zadány, ale limity byly zadány podle pokynů v garantované kvality služby příkladu, vidíme, že pod vytvořený v následujícím příkladu má QoS nastavenou jako Guaranteed. Pokud nezadáte požadavky na prostředky, Kubernetes považuje omezení prostředků rovna prostředkům požadavky.
kind: StorageClass
apiVersion: storage.k8s.io/v1
metadata:
name: azure-disk
provisioner: kubernetes.io/azure-disk
parameters:
storageaccounttype: Standard_LRS
kind: Managed
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: mssql
labels:
app: mssql
spec:
serviceName: "mssql"
replicas: 1
selector:
matchLabels:
app: mssql
template:
metadata:
labels:
app: mssql
spec:
securityContext:
fsGroup: 10001
containers:
- name: mssql
command:
- /bin/bash
- -c
- cp /var/opt/config/mssql.conf /var/opt/mssql/mssql.conf && /opt/mssql/bin/sqlservr
image: mcr.microsoft.com/mssql/server:2022-latest
resources:
limits:
memory: 2Gi
cpu: '2'
ports:
- containerPort: 1433
env:
- name: ACCEPT_EULA
value: "Y"
- name: MSSQL_ENABLE_HADR
value: "1"
- name: MSSQL_SA_PASSWORD
valueFrom:
secretKeyRef:
name: mssql
key: MSSQL_SA_PASSWORD
volumeMounts:
- name: mssql
mountPath: "/var/opt/mssql"
- name: userdata
mountPath: "/var/opt/mssql/userdata"
- name: userlog
mountPath: "/var/opt/mssql/userlog"
- name: tempdb
mountPath: "/var/opt/mssql/tempdb"
- name: mssql-config-volume
mountPath: "/var/opt/config"
volumes:
- name: mssql-config-volume
configMap:
name: mssql
volumeClaimTemplates:
- metadata:
name: mssql
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
- metadata:
name: userdata
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
- metadata:
name: userlog
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
- metadata:
name: tempdb
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 8Gi
Spuštěním příkazu kubectl describe pod mssql-0 můžete zobrazit QoS jako Guaranteeds výstupem podobným následujícímu fragmentu kódu.
...
QoS Class: Guaranteed
Node-Selectors: <none>
Tolerations: node.kubernetes.io/memory-pressure:NoSchedule op=Exists
node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
...
U neprodukčních úloh, u kterých výkon a dostupnost nejsou vysokou prioritou, můžete zvážit nastavení QoS na Burstable nebo BestEffort.
Ukázka pružné technologie QoS
Pokud chcete definovat příklad Burstable YAML, zadáte požadavkyprostředku, nikoli omezení, nebo zadáte omezení, která jsou vyšší než požadavky. Následující kód zobrazuje pouze rozdíl od předchozího příkladu, aby bylo možné definovat škálovatelnou úlohu.
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: mssql
labels:
app: mssql
spec:
serviceName: "mssql"
replicas: 1
selector:
matchLabels:
app: mssql
template:
metadata:
labels:
app: mssql
spec:
securityContext:
fsGroup: 10001
containers:
- name: mssql
command:
- /bin/bash
- -c
- cp /var/opt/config/mssql.conf /var/opt/mssql/mssql.conf && /opt/mssql/bin/sqlservr
image: mcr.microsoft.com/mssql/server:2022-latest
resources:
requests:
memory: 2Gi
cpu: '2'
Spuštěním příkazu kubectl describe pod mssql-0 můžete zobrazit QoS jako Burstables výstupem podobným následujícímu fragmentu kódu.
...
QoS Class: Burstable
Node-Selectors: <none>
Tolerations: node.kubernetes.io/memory-pressure:NoSchedule op=Exists
node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
...
Ukázka QoS v nejlepším úsilí
Pokud chcete definovat příklad BestEffort YAML, odeberte požadavky prostředků a omezení prostředků. Nakonec obdržíte třídu QoS s názvem BestEffort, jak je definováno v části , která se zabývá vytvořením podu přiřazeného do této kategorie. Stejně jako předtím následující kód zobrazuje pouze rozdíl oproti příkladu Guaranteed, k definování nejlepší možné pracovní zátěže. Jedná se o nejméně doporučované možnosti pro pody SQL Serveru, protože by se pravděpodobně jednalo o první, které by byly ukončeny v případě konfliktu prostředků. I pro scénáře testování a kontroly kvality doporučujeme použít možnost Burstable pro SQL Server.
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: mssql
labels:
app: mssql
spec:
serviceName: "mssql"
replicas: 1
selector:
matchLabels:
app: mssql
template:
metadata:
labels:
app: mssql
spec:
securityContext:
fsGroup: 10001
containers:
- name: mssql
command:
- /bin/bash
- -c
- cp /var/opt/config/mssql.conf /var/opt/mssql/mssql.conf && /opt/mssql/bin/sqlservr
image: mcr.microsoft.com/mssql/server:2022-latest
ports:
- containerPort: 1433
Spuštěním příkazu kubectl describe pod mssql-0 můžete zobrazit QoS jako BestEfforts výstupem podobným následujícímu fragmentu kódu.
...
QoS Class: BestEffort
Node-Selectors: <none>
Tolerations: node.kubernetes.io/memory-pressure:NoSchedule op=Exists
node.kubernetes.io/not-ready:NoExecute op=Exists for 300s
node.kubernetes.io/unreachable:NoExecute op=Exists for 300s
...
Podpora skupin ovládacích prvků (cgroup) v2
SQL Server zjistí a respektuje omezení kontrolní skupiny cgroup v2, počínaje SQL Serverem (verze 2025, 17.x) a SQL Serverem (verze 2022, 16.x) kumulativní aktualizací (CU) 20. Tato omezení poskytují jemně odstupňované řízení v jádru Linuxu nad prostředky procesoru a paměti a zlepšují izolaci prostředků v prostředích Docker, Kubernetes a OpenShift.
V dřívějších verzích můžou kontejnerizovaná nasazení v clusterech Kubernetes (například Azure Kubernetes Service v1.25+) zaznamenat chyby nedostatku paměti (OOM), protože SQL Server nevynucovala limity paměti definované ve specifikacích kontejnerů. Tento problém řeší podpora cgroup v2.
Kontrola verze cgroup
stat -fc %T /sys/fs/cgroup
Výsledky jsou následující:
| Result | Description |
|---|---|
cgroup2fs |
Použijete cgroup v2. |
cgroup |
Použijete cgroup v1. |
Přepnutí na cgroup v2
Nejjednodušší cestou je volba distribuce, která podporuje cgroup v2.
Pokud potřebujete přepnout ručně, přidejte do konfigurace GRUB následující parametr:
systemd.unified_cgroup_hierarchy=1
Pak aktualizujte GRUB. Například na Ubuntu spusťte:
sudo update-grub
V Red Hat Enterprise Linuxu (RHEL) spusťte:
sudo grub2-mkconfig -o /boot/grub2/grub.cfg
Hlášení o limitu CPU s cgroup v2
Když nakonfigurujete omezení procesoru pomocí cgroup v2, SQL Server v protokolu chyb nezobrazí nakonfigurovaný počet jader procesoru. Místo toho nadále hlásí celkový počet hostitelských procesorů.
Pokud chcete sladit SQL Server plánovače a plány dotazů (například rozhodnutí o paralelismu) se zamýšleným počtem procesorů definovaným v cgroup v2, použijte následující konfiguraci.
Konfigurace spřažení procesoru
Explicitně nastavte spřažení procesoru SQL Server tak, aby odpovídalo kvótě výkonu pro cgroup. V následujícím příkladu je kvóta cgroup čtyři procesory na osmijádrovém hostiteli.
ALTER SERVER CONFIGURATION
SET PROCESS AFFINITY CPU = 0 TO 3;
Tato konfigurace zajišťuje, že SQL Server vytváří plánovače pouze pro zamýšlený počet procesorů. Další informace naleznete v tématu ALTER SERVER CONFIGURATION a Use PROCESS AFFINITY pro uzel a/nebo CPU.
Povolení příznaku trasování 8002 (doporučeno)
Povolte příznak trasování 8002 pro použití měkkého spřažení ve vrstvě SQLPAL:
sudo /opt/mssql/bin/mssql-conf traceflag 8002 on
Ve výchozím nastavení jsou plánovače vázány na konkrétní procesory definované v maskě spřažení. Příznak trasování 8002 umožňuje plánovačům přesouvat se mezi procesory, což obecně zlepšuje výkon a zároveň respektuje přiřazení procesorů a omezení cgroup. Další informace naleznete v tématu DBCC TRACEON - Trace Flags.
Po povolení příznaku trasování restartujte SQL Server.
Očekávané chování
Po restartování:
SQL Server vytvoří pouze počet plánovačů definovaných nastavením spřažení (například čtyři plánovače).
Jádro Linuxu nadále vynucuje kvótu spouštění procesoru cgroup v2.
Rozhodnutí o optimalizaci dotazů a paralelismu jsou založená na zamýšleném počtu procesorů, nikoli na celkovém počtu procesorů hostitele.
Note
Protokol chyb SQL Server může i nadále zobrazovat celkový počet procesorů hostitele. Toto chování protokolování a zobrazení nemá vliv na skutečné využití procesoru, vytvoření plánovače nebo vynucení procesoru pomocí cgroup v2 nebo spřažení procesoru.
Další informace najdete v následujících zdrojích informací:
- Rychlý start: Nasazení kontejneru SQL Serveru s Linuxem do Kubernetes pomocí grafů Helm
- Control Group v2 (dokumentace k jádru Linuxu)