首页 > 解决方案 > 使用 Kubernetes 部署 PostgreSQL 数据库

问题描述

在使用 Kubernetes 部署我的 Django 应用程序的 PostgreSQL 数据库时,我感到很困惑。以下是我构建 deployment-definition.yml 文件的方式:

apiVersion: apps/v1beta1
kind: Deployment
metadata:
  name: postgres
spec:
  replicas: 1
  selector:
    matchLabels:
      app: postgres-container
  template:
    metadata:
      labels:
        app: postgres-container
        tier: backend
    spec:
      containers:
        - name: postgres-container
          image: postgres:9.6.6
          env:
            - name: POSTGRES_USER
              valueFrom:
                secretKeyRef:
                  name: postgres-credentials
                  key: user

            - name: POSTGRES_PASSWORD
              valueFrom:
                secretKeyRef:
                  name: postgres-credentials
                  key: password

            - name: POSTGRES_DB
              value: agent_technologies_db
          ports:
            - containerPort: 5432
          volumeMounts:
            - name: postgres-volume-mount
              mountPath: /var/lib/postgresql/data

      volumes:
        - name: postgres-volume-mount
          persistentVolumeClaim:
            claimName: postgres-pvc
        - name: postgres-credentials
          secret:
            secretName: postgres-credentials

我不明白的是这个。如果我在 Kubernetes 部署对象的规范中指定(像我一样)现有的 PostgreSQL 映像,我如何实际运行我的应用程序?我需要在我的 settings.py 文件中指定什么作为 HOST ?

这是我的 settings.py 文件现在的样子:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql_psycopg2',
        'NAME': 'agent_technologies_db',
        'USER': 'stefan_radonjic',
        'PASSWORD': 'cepajecar995',
        'HOST': 'localhost', 
        'PORT': '',
        }
}

它是这样构建的,因为我仍在设计应用程序,我还不想将它部署到 Kubernetes 集群。但是当我这样做时,我应该为 :HOST和指定PORT什么?而且,这是将 PostgreSQL 部署到 Kubernetes 集群的正确方法吗?

先感谢您!

*** 问题更新 ***

按照建议,我创建了 service.yml:

apiVersion: v1
kind: Service
metadata:
  name: postgres-service
spec:
  selector:
    app: postgres-container
    tier: backend
  ports:
    - protocol: TCP
      port: 5432
      targetPort: 5432
  type: ClusterIP

我已经更新了我的 settings.py 文件:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql_psycopg2',
        'NAME': 'agent_technologies_db',
        'USER': 'stefan_radonjic',
        'PASSWORD': 'cepajecar995',
        'HOST': 'postgres-service', 
        'PORT': 5432,
        }
}

但我收到以下错误:

在此处输入图像描述

标签: djangopostgresqlkubernetes

解决方案


为了允许与 Kubernetes 中的 PostreSQL 部署进行通信,您需要设置一个Service对象。如果您的 Django 应用程序将与您的 PostgreSQL 部署在同一个集群中,那么您将需要一个ClusterIP类型服务;否则,如果您的 Django 应用程序位于集群之外,您将需要一个LoadBalancerNodePort类型的服务。

创建服务有两种方式:

YAML

第一种是通过 yaml 文件,在您的情况下,该文件如下所示:

kind: Service
apiVersion: v1
metadata:
  name: postgres
spec:
  selector:
    app: postgres-container
    tier: backend
  ports:
  - name: postgres
    protocol: TCP
    port: 5432
    targetPort: 5432

.spec.selector字段定义Service. 该服务将针对带有标签app=postgres-containertier=backend. 它暴露了容器的 5432 端口。在您的 Django 配置中,您可以将服务的名称作为HOST: 在这种情况下,名称只是postgres. Kubernetes 会将服务名称解析为匹配的 Pod IP 并将流量路由到 Pod。该端口将是服务的端口:5432。

kubectl 暴露

创建服务的另一种方法是通过以下kubectl expose命令:

kubectl expose deployment/postgres

此命令将默认为ClusterIP类型服务并公开.spec.containers.ports部署 yaml 中字段中定义的端口。

更多信息:

https://kubernetes.io/docs/concepts/services-networking/service/

而且,这是将 PostgreSQL 部署到 Kubernetes 集群的正确方法吗?

这取决于几个变量。您是否计划部署 Postgres 集群?如果是这样,您可能需要考虑使用StatefulSet

StatefulSets 对于需要以下一项或多项的应用程序很有价值。

  • 稳定、唯一的网络标识符。
  • 稳定、持久的存储。
  • 有序、优雅的部署和扩展。
  • 有序、优雅的删除和终止。
  • 有序的自动滚动更新。

https://kubernetes.io/docs/concepts/workloads/controllers/statefulset/#using-statefulsets

您是否有熟悉 Postgres 的人来配置和维护它?如果没有,我还建议您考虑在集群之外部署托管 Postgres 服务器(例如 RDS)。您仍然可以在集群中部署您的 Django 应用程序并通过ExternalName服务连接到您的数据库。

我推荐这样做的原因是,在 Kubernetes 集群中管理有状态的应用程序可能具有挑战性。我不熟悉 Postgres,但这里有一个关于在 Kubernetes 上运行 Postgres 的警示故事:https ://gravitational.com/blog/running-postgresql-on-kubernetes/

除此之外,我遇到的一些经验影响了我从集群中删除有状态工作负载的决定:

卡住的卷

如果您使用的是 AWS EBS 卷,则卷可能会“卡在”节点上,并且如果您的数据库 pod 重新安排到新节点,则无法分离和重新连接到新节点。

迁移到新集群

如果您需要将工作负载移至新集群,您将不得不应对将状态移至新集群的额外挑战,而不会丢失任何数据。如果您将有状态应用程序移出集群,那么您可以将整个集群视为牛,然后将其拆除并迁移到新集群变得容易得多。

更多信息:

关于使用 StatefulSets 部署 Postgres 的 K8s 博客文章:https ://kubernetes.io/blog/2017/02/postgresql-clusters-kubernetes-statefulsets/


推荐阅读