web-dev-qa-db-ja.com

2つのKubernetesサービスを相互に通信させる方法は?

現在、K8sRedisサービスに接続するK8sサービスでK8sAPIポッドを使用しており、独自のK8sポッドを使用しています。問題は、NodePortを使用しているため、両方が一般に公開されていることです。 APIを一般に公開したいだけです。問題は、Redisサービスを公開しないと、APIがそれを認識できないことです。 1つを公開せずに2つのサービスを接続する方法はありますか?

これは私のAPIサービスyamlです:

apiVersion: v1
kind: Service
metadata:
   name: app-api-svc
spec:
   selector:
     app: app-api
     tier: api
   ports:
     - protocol: TCP
       port: 5000
       nodePort: 30400
   type: NodePort

そしてこれは私のRedisサービスyamlです:

apiVersion: v1
kind: Service
metadata:
   name: app-api-redis-svc
spec:
   selector:
     app: app-api-redis
     tier: celery_broker
   ports:
     - protocol: TCP
       port: 6379
       nodePort: 30537
   type: NodePort
9
Will Parzybok

まず、RedisサービスをClusterIPサービスとして構成します。プライベートになり、他のサービスでのみ表示されます。これは、オプションtypeを使用して行を削除することで実行できます。

apiVersion: v1
kind: Service
metadata:
   name: app-api-redis-svc
spec:
   selector:
     app: app-api-redis
     tier: celery_broker
   ports:
     - protocol: TCP
       port: 6379
       targetPort: [the port exposed by the Redis pod]

最後に、Redisに到達するようにAPIを構成する場合、アドレスはapp-api-redis-svc:6379である必要があります

そしてそれがすべてです。私はこのように相互に通信する多くのサービスを持っています。これがうまくいかない場合は、コメントで知らせてください。

9
Mario S

私はすべての答えと私自身の研究から最善を尽くし、あなたが役立つと思う短いガイドを作るつもりです:

1.接続をテストします

別のポッドに接続します。例:Ruby pod:

kubectl exec -it some-pod-name -- /bin/sh

問題のサービスにpingできることを確認します。

ping redis

ポートに接続できますか? (telnetはこれでは機能しませんでした)

nc -zv redis 6379

2.サービスセレクターが正しいことを確認します

サービス構成が次のようになっている場合:

kind: Service
apiVersion: v1
metadata:
  name: redis
  labels:
    app: redis
    role: master
    tier: backend
spec:
  ports:
  - port: 6379
    targetPort: 6379
  selector:
    app: redis
    role: master
    tier: backend

それらのセレクターがポッドにも設定されていることを確認しますか?

get pods --selector=app=redis,role=master,tier=backend

次のコマンドを実行して、サービスがポッドに関連付けられていることを確認します。

$> describe service redis
Name:           redis
Namespace:      default
Labels:         app=redis
            role=master
            tier=backend
Annotations:        <none>
Selector:       app=redis,role=master,tier=backend
Type:           ClusterIP
IP:         10.47.250.121
Port:           <unset> 6379/TCP
Endpoints:      10.44.0.16:6379
Session Affinity:   None
Events:         <none>

Endpoints:フィールドをチェックして、空白でないことを確認します

詳細については、次のURLをご覧ください。 https://kubernetes.io/docs/tasks/debug-application-cluster/debug-service/#my-service-is-missing-endpoints

5
newUserNameHere

Redisについてはよくわかりませんが、同様のアプリケーションがあります。 Java Webアプリケーションをポッドとして実行し、nodePortを介して外の世界に公開しています。mongodbコンテナーをポッドとして実行しています。

Webappデプロイメント仕様では、サービス名をパラメーターとして渡して、名前を介してmongodbサービスにマップします。以下の仕様を貼り付けました。それに応じて変更できます。Redisにも同様のマッピングパラメータがあり、私の場合は「mongoservice」であるサービス名を使用する必要があります。

    apiVersion: extensions/v1beta1
    kind: Deployment
    metadata:
      name: empappdepl
      labels:
        name: empapp
    spec:
      replicas: 1
      template:
        metadata:
          labels:
            name: empapp
        spec:
          containers:
            -
              resources:
                limits:
                  cpu: 0.2
              image: registryip:5000/employee:1
              imagePullPolicy: IfNotPresent
              name: wsemp
              ports:
                - containerPort: 8080
                  name: wsemp
              command: ["Java","-Dspring.data.mongodb.uri=mongodb://mongoservice/microservices", "-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]
          imagePullSecrets:
           - name: myregistrykey
---
apiVersion: v1
kind: Service
metadata:
  labels:
    name: empwhatever
  name: empservice
spec:
  ports:
   - port: 8080
     targetPort: 8080
     protocol: TCP
     name: http
     nodePort: 30062
  type: NodePort
  selector:
    name: empapp
    ---
    apiVersion: extensions/v1beta1
    kind: Deployment
    metadata:
      name: mongodbdepl
      labels:
        name: mongodb
    spec:
      replicas: 1
      template:
        metadata:
          labels:
            name: mongodb
        spec:
          containers:
          - resources:
              limits:
                cpu: 0.3
            image: mongo
            imagePullPolicy: IfNotPresent
            name: mongodb
            ports:
                  - containerPort: 27017
    ---
    apiVersion: v1
    kind: Service
    metadata:
      labels:
        name: mongowhatever
      name: mongoservice
    spec:
      ports:
       - port: 27017
         targetPort: 27017
         protocol: TCP
      selector:
        name: mongodb

MongodbサービスをNodePortとして公開する必要がないことに注意してください。

1
Vikram

Kubernetesは、サービスがサービス名を使用して他のサービスと通信できるようにすることで、サービス間の通信を可能にします。

シナリオでは、redisサービスは http://app-api-redis-svc.default:6379 の他のサービスからアクセスできる必要があります。ここでのデフォルトは、サービスが実行されている名前空間です。

これにより、ターゲットコンテナポートで実行されているredisポッドにリクエストが内部的にルーティングされます

Kubernetesが提供するさまざまなサービス検出オプションのモードについては、これをチェックアウトしてください リンク

それが役に立てば幸い