我仍在与其他几个人一起在开发集群中尝试Istio。我们有一个示例虚拟服务,部署和destinationrule,对指定uri的请求将转到与该部署关联的pod。一切正常。
如果存在特定的标头和值,我尝试将其更改为备用部署。如果未设置标头,或者不存在指定的标头值,则它将转到原始部署,否则转到备用部署。我最终打算让它检查指定标头的几个不同值,每个值去不同的部署。
我创建了一个部署和目标规则,这些规则是原始副本的副本,具有一致的变体。我试图使用此备用路由修改虚拟服务。到目前为止,它无法正常工作。我通过跟踪与每个部署关联的容器的容器日志来确定请求转到哪个部署。当我发送带有指定标头和值的请求时,它确实转到了备用部署。但是,当我发送的请求没有指定的标头或没有匹配的值时,它也将转到备用部署。实际上,我根本无法达到主要部署。
请注意,我知道执行此操作的另一种方法是为“默认”路由提供一个虚拟服务,为每个备用路由提供一个附加虚拟服务,并指定不同的标头值。我基本上看到了类似的东西。但是,要获得在单个VirtualService中设置起来应该更简单的东西,这似乎有很多重复。
以下是虚拟服务的当前状态,其中有一些省略:
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
annotations: {}
name: fooms-vs-ingress
namespace: com-example
spec:
gateways:
- ingress-gateway
hosts:
- '*'
http:
- match:
- uri:
prefix: /msapi/foo
- headers:
ctx-debug-route-fooms:
exact: myuid-1
route:
- destination:
host: fooms.com-example.svc.cluster.local
port:
number: 80
subset: myuid-1
- route:
- destination:
host: fooms.com-example.svc.cluster.local
port:
number: 80
subset: blue
我可以显示部署和目的地规则,但是我不知道这是否有帮助。
更新:
自从我写这篇文章以来,我发现为了在路由匹配中创建两个条件AND,必须在单个匹配规则中同时拥有两个条件。我仍然习惯于YAML的工作方式。我将在此处提供虚拟服务的更新版本,以及网关,目标规则和大部分部署。部署中有很多东西可能无济于事。
当我从Postman向服务发送请求时,无论是否带有路由标头,我都会收到503。在进行这些更改以检查路由头之前,它已将请求正确路由到“蓝色”实例(我将两个Pod的日志都尾随了)。当我第一次尝试进行这些更改时,我无意中定义了两个匹配块,一个带有uri条件,一个带有标头匹配条件。当我这样做时,所有请求都转到了备用吊舱。
以下是可能相关的对象的省略版本,其中删除了一些临时属性。
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
annotations: {}
name: fooms-vs-ingress
namespace: com-example
spec:
gateways:
- comp-ingress-gateway
hosts:
- '*'
http:
- match:
- headers:
compctx-debug-route-fooms:
exact: myuid-1
name: match-myuid-1
uri:
prefix: /msapi/foo
route:
- destination:
host: fooms.com-example.svc.cluster.local
port:
number: 80
subset: myuid-1
- name: default
route:
- destination:
host: fooms.com-example.svc.cluster.local
port:
number: 80
subset: blue
apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
annotations: {}
name: comp-ingress-gateway
namespace: com-example
spec:
selector:
istio: ingressgateway
servers:
- hosts:
- '*'
port:
name: http
number: 80
protocol: HTTP
- hosts:
- '*'
port:
name: https
number: 443
protocol: HTTPS
tls:
mode: SIMPLE
privateKey: /etc/istio/ingressgateway-certs/tls.key
serverCertificate: /etc/istio/ingressgateway-certs/tls.crt
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
annotations:
deployment.kubernetes.io/revision: "1"
labels:
app: FooMS
role: blue
routeoffer: DEFAULT
seed: COMPv2.2.0
version: 2.2.0-myuid-1
name: fooms-myuid-1
namespace: com-example
spec:
replicas: 1
revisionHistoryLimit: 2
selector:
matchLabels:
app: FooMS
role: blue
strategy:
rollingUpdate:
maxSurge: 1
maxUnavailable: 1
type: RollingUpdate
template:
metadata:
annotations:
sidecar.istio.io/inject: "true"
creationTimestamp: null
labels:
app: FooMS
role: blue
routeoffer: DEFAULT
seed: COMPv2.2.0
version: 2.2.0-myuid-1
spec:
containers:
- env:
- name: SERVICE_NAME
value: fooms
- name: NODE_NAME
valueFrom:
fieldRef:
apiVersion: v1
fieldPath: spec.nodeName
envFrom:
- configMapRef:
name: global-config
- secretRef:
name: global-secrets
image: dockercentral.it....
imagePullPolicy: Always
name: fooms
ports:
- containerPort: 8080
name: http
protocol: TCP
- image: ...
imagePullPolicy: IfNotPresent
name: info
dnsPolicy: ClusterFirst
restartPolicy: Always
schedulerName: default-scheduler
securityContext: {}
serviceAccount: default
serviceAccountName: default
terminationGracePeriodSeconds: 30
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
annotations: {}
name: fooms-destination-myuid-1
namespace: com-example
spec:
host: fooms.com-example.svc.cluster.local
subsets:
- labels:
version: 2.2.0-myuid-1
name: myuid-1
trafficPolicy:
tls:
mode: ISTIO_MUTUAL
答案 0 :(得分:0)
由于我没有该命令kubectl get pods,ep,svc -o wide
的所有信息,所以我不确定这是目标规则错误,因为我不了解有关pod,ep,svc的所有信息,并且目标规则适用于同一部署只有一个副本。
可能是存在destination rule只有一个子集的问题
根据您的virtual service,我认为您的目标规则应该是这样
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: fooms-destination-myuid-1
namespace: com-example
spec:
host: fooms.com-example.svc.cluster.local
subsets:
- labels:
version: 2.2.0-myuid-1
name: myuid-1
subsets:
- labels:
role: blue
name: blue
trafficPolicy:
tls:
mode: ISTIO_MUTUAL
我举了一个例子,下面做了所有说明
Kubernetes版本 1.13.11-gke.14
Istio版本 1.4.1
kubectl label namespace default istio-injection=enabled
部署 1
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx1
spec:
selector:
matchLabels:
run: nginx1
replicas: 1
template:
metadata:
labels:
run: nginx1
app: frontend
spec:
containers:
- name: nginx1
image: nginx
ports:
- containerPort: 80
lifecycle:
postStart:
exec:
command: ["/bin/sh", "-c", "echo Hello nginx1 > /usr/share/nginx/html/index.html"]
部署 2
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx2
spec:
selector:
matchLabels:
run: nginx2
replicas: 1
template:
metadata:
labels:
run: nginx2
app: frontend
spec:
containers:
- name: nginx2
image: nginx
ports:
- containerPort: 80
lifecycle:
postStart:
exec:
command: ["/bin/sh", "-c", "echo Hello nginx2 > /usr/share/nginx/html/index.html"]
服务
apiVersion: v1
kind: Service
metadata:
name: nginx
labels:
app: frontend
spec:
ports:
- port: 80
protocol: TCP
selector:
app: frontend
网关
apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
name: comp-ingress-gateway
namespace: default
spec:
selector:
istio: ingressgateway
servers:
- hosts:
- '*'
port:
name: http
number: 80
protocol: HTTP
- hosts:
- '*'
port:
name: https
number: 443
protocol: HTTPS
tls:
mode: SIMPLE
privateKey: /etc/istio/ingressgateway-certs/tls.key
serverCertificate: /etc/istio/ingressgateway-certs/tls.crt
虚拟服务
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: nginxvirt
spec:
gateways:
- comp-ingress-gateway #outside cluster
- mesh #inside cluster
hosts:
- nginx.default.svc.cluster.local #inside cluster
- nginx.com #outside cluster
http:
- name: match-myuid
match:
- uri:
prefix: /msapi
headers:
compctx:
exact: myuid
rewrite:
uri: /
route:
- destination:
host: nginx.default.svc.cluster.local
port:
number: 80
subset: v1
- name: default
route:
- destination:
host: nginx.default.svc.cluster.local
port:
number: 80
subset: v2
目的地规则
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: nginxdest
spec:
host: nginx.default.svc.cluster.local
subsets:
- name: v1
labels:
run: nginx1
- name: v2
labels:
run: nginx2
trafficPolicy:
tls:
mode: ISTIO_MUTUAL
用于外部测试的Pod
apiVersion: v1
kind: Pod
metadata:
name: ubu1
spec:
containers:
- name: ubu1
image: ubuntu
command: ["/bin/sh"]
args: ["-c", "sleep 3000"]
卷曲的结果:
外部:
curl -H "host: nginx.com" -H "compctx: myuid" ingress_gateway_ip/msapi
Hello nginx1
curl -H "host: nginx.com" -H "compctx: myuid" ingress_gateway_ip/msapi
Hello nginx1
curl -H "host: nginx.com" -H "compctx: myuid" ingress_gateway_ip/msapi
Hello nginx1
curl -H "host: nginx.com" ingress_gateway_ip
Hello nginx2
curl -H "host: nginx.com" ingress_gateway_ip
Hello nginx2
curl -H "host: nginx.com" ingress_gateway_ip
Hello nginx2
内部:
kubectl exec -ti ubu1 -- /bin/bash
root@ubu1:/# curl -H "compctx: myuid " nginx/msapi
Hello nginx1
root@ubu1:/# curl -H "compctx: myuid " nginx/msapi
Hello nginx1
root@ubu1:/# curl -H "compctx: myuid " nginx/msapi
Hello nginx1