部署到 Kubernetes (GKE) 时无法访问 SFTP 服务器
SFTP server is not accessible when deployed to Kubernetes (GKE)
使用 NodePort 服务和 Kubernetes Ingress 公开时无法访问 SFTP 服务器。但是,如果使用 LoadBalancer 类型的服务公开相同的部署,则它工作正常。
下面是 GKE using atmoz/sftp Dockerfile 中 SFTP 的部署文件。
kind: Deployment
apiVersion: extensions/v1beta1
metadata:
name: sftp
labels:
environment: production
app: sftp
spec:
replicas: 1
minReadySeconds: 10
template:
metadata:
labels:
environment: production
app: sftp
annotations:
container.apparmor.security.beta.kubernetes.io/sftp: runtime/default
spec:
containers:
- name: sftp
image: atmoz/sftp:alpine
imagePullPolicy: Always
args: ["user:pass:1001:100:upload"]
ports:
- containerPort: 22
securityContext:
capabilities:
add: ["SYS_ADMIN"]
resources: {}
如果我使用 LoadBalancer 类型的 Kubernetes 服务正常公开此部署,如下所示:
apiVersion: v1
kind: Service
metadata:
labels:
environment: production
name: sftp-service
spec:
type: LoadBalancer
ports:
- name: sftp-port
port: 22
protocol: TCP
targetPort: 22
selector:
app: sftp
上面的服务获得了一个外部 IP,我可以简单地在命令 sftp xxx.xx.xx.xxx
命令中使用它来使用 pass
密码进行访问。
但是,我尝试使用 GKE Ingress 公开相同的部署,但它不起作用。以下是入口清单:
# First I create a NodePort service to expose the deployment internally
---
apiVersion: v1
kind: Service
metadata:
labels:
environment: production
name: sftp-service
spec:
type: NodePort
ports:
- name: sftp-port
port: 22
protocol: TCP
targetPort: 22
nodePort: 30063
selector:
app: sftp
# Ingress service has SFTP service as it's default backend
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: basic-ingress-2
spec:
backend:
serviceName: sftp-service
servicePort: 22
rules:
- http:
paths:
# "http-service-sample" is a service exposing a simple hello-word app deployment
- path: /sample
backend:
serviceName: http-service-sample
servicePort: 80
将外部 IP 分配给 Ingress 后(我知道完全设置需要几分钟)并且 xxx.xx.xx.xxx/sample
开始工作但 sftp -P 80 xxx.xx.xx.xxx
不工作。
以下是我从服务器得到的错误:
ssh_exchange_identification: Connection closed by remote host
Connection closed
我在上面的设置中做错了什么?为什么 LoadBalancer 服务能够允许访问 SFTP 服务,而 Ingress 失败?
目前不完全支持在 Kubernetes Ingress 中路由除 HTTP/HTTPS 协议之外的任何其他流量(参见 docs)。
您可以尝试按照此处所述进行一些解决方法:
使用 NodePort 服务和 Kubernetes Ingress 公开时无法访问 SFTP 服务器。但是,如果使用 LoadBalancer 类型的服务公开相同的部署,则它工作正常。
下面是 GKE using atmoz/sftp Dockerfile 中 SFTP 的部署文件。
kind: Deployment
apiVersion: extensions/v1beta1
metadata:
name: sftp
labels:
environment: production
app: sftp
spec:
replicas: 1
minReadySeconds: 10
template:
metadata:
labels:
environment: production
app: sftp
annotations:
container.apparmor.security.beta.kubernetes.io/sftp: runtime/default
spec:
containers:
- name: sftp
image: atmoz/sftp:alpine
imagePullPolicy: Always
args: ["user:pass:1001:100:upload"]
ports:
- containerPort: 22
securityContext:
capabilities:
add: ["SYS_ADMIN"]
resources: {}
如果我使用 LoadBalancer 类型的 Kubernetes 服务正常公开此部署,如下所示:
apiVersion: v1
kind: Service
metadata:
labels:
environment: production
name: sftp-service
spec:
type: LoadBalancer
ports:
- name: sftp-port
port: 22
protocol: TCP
targetPort: 22
selector:
app: sftp
上面的服务获得了一个外部 IP,我可以简单地在命令 sftp xxx.xx.xx.xxx
命令中使用它来使用 pass
密码进行访问。
但是,我尝试使用 GKE Ingress 公开相同的部署,但它不起作用。以下是入口清单:
# First I create a NodePort service to expose the deployment internally
---
apiVersion: v1
kind: Service
metadata:
labels:
environment: production
name: sftp-service
spec:
type: NodePort
ports:
- name: sftp-port
port: 22
protocol: TCP
targetPort: 22
nodePort: 30063
selector:
app: sftp
# Ingress service has SFTP service as it's default backend
---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: basic-ingress-2
spec:
backend:
serviceName: sftp-service
servicePort: 22
rules:
- http:
paths:
# "http-service-sample" is a service exposing a simple hello-word app deployment
- path: /sample
backend:
serviceName: http-service-sample
servicePort: 80
将外部 IP 分配给 Ingress 后(我知道完全设置需要几分钟)并且 xxx.xx.xx.xxx/sample
开始工作但 sftp -P 80 xxx.xx.xx.xxx
不工作。
以下是我从服务器得到的错误:
ssh_exchange_identification: Connection closed by remote host
Connection closed
我在上面的设置中做错了什么?为什么 LoadBalancer 服务能够允许访问 SFTP 服务,而 Ingress 失败?
目前不完全支持在 Kubernetes Ingress 中路由除 HTTP/HTTPS 协议之外的任何其他流量(参见 docs)。
您可以尝试按照此处所述进行一些解决方法: