7.17. 虚拟机网络

7.17.1. 为默认 pod 网络配置虚拟机

您可以通过将其网络接口配置为使用 masquerade 绑定模式,将虚拟机连接到默认的内部 pod 网络。

注意

KubeMacPool 组件为指定命名空间中的虚拟机 NIC 提供 MAC 地址池服务。默认情况下不启用它。通过将 KubeMacPool 标签应用到该命名空间来启用命名空间中的 MAC 地址池

7.17.1.1. 从命令行配置伪装模式

您可以使用伪装模式将虚拟机的外发流量隐藏在 pod IP 地址后。伪装模式使用网络地址转换 (NAT) 来通过 Linux 网桥将虚拟机连接至 pod 网络后端。

启用伪装模式,并通过编辑虚拟机配置文件让流量进入虚拟机。

先决条件

  • 虚拟机必须配置为使用 DHCP 来获取 IPv4 地址。以下示例配置为使用 DHCP。

流程

  1. 编辑虚拟机配置文件的 interfaces 规格:

    kind: VirtualMachine
    spec:
      domain:
        devices:
          interfaces:
            - name: default
              masquerade: {} 1
              ports:
                - port: 80 2
      networks:
      - name: default
        pod: {}
    1
    使用伪装模式进行连接。
    2
    可选:列出您要从虚拟机公开的端口,每个都由 port 字段指定。port 值必须是 0 到 65536 之间的数字。如果没有使用 port 数组,则有效范围内的所有端口都开放给传入流量。在本例中,端口 80 上允许传入的流量。
    注意

    端口 49152 和 49153 保留供 libvirt 平台使用,这些端口的所有其他传入流量将被丢弃。

  2. 创建虚拟机:

    $ oc create -f <vm-name>.yaml

7.17.1.2. 从虚拟机创建服务

首先通过创建 Service 对象来公开虚拟机,从正在运行的虚拟机创建服务。

ClusterIP 服务类型会在集群内部公开虚拟机。NodePortLoadBalancer 服务类型在集群外为外部公开虚拟机。

此流程演示了如何创建、连接和公开一个 type: ClusterIP Service 对象作为虚拟机支持的服务。

注意

如果没有指定 服务类型ClusterIP 是默认的服务类型

流程

  1. 编辑虚拟机 YAML,如下所示:

    apiVersion: kubevirt.io/v1alpha3
    kind: VirtualMachine
    metadata:
      name: vm-ephemeral
      namespace: example-namespace
    spec:
      running: false
      template:
        metadata:
          labels:
            special: key 1
        spec:
          domain:
            devices:
              disks:
                - name: containerdisk
                  disk:
                    bus: virtio
                - name: cloudinitdisk
                  disk:
                    bus: virtio
              interfaces:
              - masquerade: {}
                name: default
            resources:
              requests:
                memory: 1024M
          networks:
            - name: default
              pod: {}
          volumes:
            - name: containerdisk
              containerDisk:
                image: kubevirt/fedora-cloud-container-disk-demo
            - name: cloudinitdisk
              cloudInitNoCloud:
                userData: |
                  #!/bin/bash
                  echo "fedora" | passwd fedora --stdin
    1
    spec.template.metadata.labels 部分添加标签 special: key
    注意

    虚拟机上的标签会传递到 pod。VirtualMachine 配置上的标签(例如,special: key)必须与 Service YAML selector 属性中的标签匹配,您在此流程中创建该属性。

  2. 保存虚拟机 YAML 以应用您的更改。
  3. 编辑 Service YAML 以配置创建和公开 Service 对象所需的设置:

    apiVersion: v1
    kind: Service
    metadata:
      name: vmservice 1
      namespace: example-namespace 2
    spec:
      ports:
      - port: 27017
        protocol: TCP
        targetPort: 22 3
      selector:
        special: key 4
      type: ClusterIP 5
    1
    指定您要创建和公开的服务的名称
    2
    Service YAML 的 metadata 部分中指定与您在虚拟机 YAML 中指定的 namespace 对应的 namespace
    3
    添加 targetPort: 22,在 SSH 端口 22 中公开服务。
    4
    Service YAML 的 spec 部分,将 special: key 添加到 selector 属性中,该属性与您在虚拟机 YAML 配置文件中添加的 labels 对应。
    5
    Service YAML 的 spec 部分,为 ClusterIP 服务添加 type: ClusterIP要在集群外部创建和公开其他类型的服务,如 NodePortLoadBalancer,根据情况将 type: ClusterIP 替换为 type: NodePorttype: LoadBalancer
  4. 保存 Service YAML 以存储服务配置。
  5. 创建 ClusterIP 服务:

    $ oc create -f <service_name>.yaml
  6. 启动虚拟机。如果虚拟机已在运行,重启它。
  7. 查询 Service 对象以验证它是否可用,并使用 ClusterIP 类型进行配置。

    验证

    • 运行 oc get service 命令,指定您在虚拟机和 Service YAML 文件中引用的 namespace

      $ oc get service -n example-namespace

      输出示例

      NAME        TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)     AGE
      vmservice   ClusterIP   172.30.3.149   <none>        27017/TCP   2m

      • 如输出所示,vmservice 正在运行。
      • 如您在 Service YAML 中指定,TYPE 显示为 ClusterIP
  8. 建立到您要用来支持您的服务的虚拟机的连接。从集群内的一个对象(如另一个虚拟机)连接。

    1. 编辑虚拟机 YAML,如下所示:

      apiVersion: kubevirt.io/v1alpha3
      kind: VirtualMachine
      metadata:
        name: vm-connect
        namespace: example-namespace
      spec:
        running: false
        template:
          spec:
            domain:
              devices:
                disks:
                  - name: containerdisk
                    disk:
                      bus: virtio
                  - name: cloudinitdisk
                    disk:
                      bus: virtio
                interfaces:
                - masquerade: {}
                  name: default
              resources:
                requests:
                  memory: 1024M
            networks:
              - name: default
                pod: {}
            volumes:
              - name: containerdisk
                containerDisk:
                  image: kubevirt/fedora-cloud-container-disk-demo
              - name: cloudinitdisk
                cloudInitNoCloud:
                  userData: |
                    #!/bin/bash
                    echo "fedora" | passwd fedora --stdin
    2. 运行 oc create 命令来创建第二个虚拟机,其中 file.yaml 是虚拟机 YAML 的名称:

      $ oc create -f <file.yaml>
    3. 启动虚拟机。
    4. 运行以下 virtctl 命令连接到虚拟机:

      $ virtctl -n example-namespace console <new-vm-name>
      注意

      对于服务类型 LoadBalancer,使用 vinagre 客户端使用公共 IP 和端口连接您的虚拟机。在使用服务类型 LoadBalancer 时,外部端口会被动态分配。

    5. 运行 ssh 命令验证连接,其中 172.30.3.149 是服务的 ClusterIP,fedora 是虚拟机的用户名:

      $ ssh fedora@172.30.3.149 -p 27017

      验证

      • 您收到用于支持要公开服务的虚拟机的命令行提示符。现在,您有一个被一个运行的虚拟机支持的服务。