仮想化通信

日本仮想化技術株式会社の公式エンジニアブログ

KubeVirtでWindows VMにリモートデスクトップ(RDP)アクセスする

KubeVirtはアプリケーションを仮想マシンで動作させるため、LinuxだけでなくWindowsなども動かすことができます。

近年のWindowsはコマンドベースによるアクセスも色々とできるようになってはいますが、まだまだWindowsはGUIで操作する方が多いと思います。そこで、KubeVirtで起動した仮想マシンで動くWindowsにRDPプロトコルを使ってリモートアクセスする方法をまとめてみたいと思います。

基本的には前の投稿でも説明したように、Kubernetesのサービスを利用して実現します。

tech.virtualtech.jp

RDPプロトコルのポートはTCPおよびUDPプロトコルの3389番ポートを使って通信を行いますが、今回の場合はKubernetes ServiceでNodePortを割り当ててアクセスしてみます。

KubeVirtでVMを管理するには、次の流れでそれぞれを作成します。

  • ストレージボリュームを作成
  • VMIを作成
  • VMIの上でVMが動く
  • VMになんらかの方法で任意のOSを導入

VMIのIはInfrastructureのことのようです。 コンテナーの中でLibvirtとQEMU、KubeVirtの少々のプロセスが動く環境のことを指します。

そのVMIの作成時に、次のようなYAMLファイルを作成してデプロイしたとします。

apiVersion: kubevirt.io/v1alpha3
kind: VirtualMachine
metadata:
  creationTimestamp: 2018-07-04T15:03:08Z
  generation: 1
  labels:
    kubevirt.io/os: windows
  name: win2016
spec:
  running: true
  template:
    metadata:
      creationTimestamp: null
      labels:
        kubevirt.io/domain: win2016
    spec:
      domain:
        cpu:
          cores: 2
        devices:
          disks:
          - disk:
              bus: virtio
            name: disk0
          - cdrom:
              bus: sata
              readonly: true
            name: cloudinitdisk
        machine:
          type: q35
        resources:
          requests:
            memory: 8192M
      volumes:
      - name: disk0
        persistentVolumeClaim:
          claimName: win2016
      - cloudInitNoCloud:
          userData: |
            #ps1_sysnative
            $HostName = hostname
            [ADSI]$UpdateUser = "WinNT://$HostName/Administrator,User"
            $UpdateUser.SetPassword( "Mywin2k16#" )
            $UpdateUser.SetInfo()
        name: cloudinitdisk

この場合にこのVMIに対してServiceを割り当てるには、次のようなYAMLファイルを作成します。ラベルとセレクターで同じラベルを設定すれば良いというわけです。下記の例では kubevirt.io/domain: win2016 がラベルですね。

---
apiVersion: v1
kind: Service
metadata:
  name: win2016-nodeport
  labels:
    kubevirt.io/domain: win2016
spec:
  type: NodePort
  ports:
  - port: 3389
    targetPort: 3389
    nodePort: 30389
  selector:
    kubevirt.io/domain: win2016

nodePort: 30389の部分は未指定の場合はNodePortの範囲から自動設定されますが、今回の場合は特定のポートを記述することにしました。クラスターで使用中のポートはkubectl get svcなどで確認できますから、使用中ではないポートを指定します。

NodePortで利用するレンジは事前にファイヤーウォール設定で許可しておく必要があります。例えばfirewall-cmdを使う場合は次のような感じです。おそらくKubernetesの環境をセットアップする際になんらかの方法でポート開放しているはずです。

$ sudo firewall-cmd --permanent --add-port=30000-32767/tcp
$ sudo firewall-cmd --reload

リモートデスクトップの設定

あとはWindows側でリモートデスクトップの許可をするだけです。デフォルトの設定では無効化されていると思います。

Windows Server 2016以降の場合はサーバーマネージャーを起動し、左ペインで「ローカルサーバー」を選び、右ペインの一覧の中からリモートデスクトップの設定を確認します。「無効」となっている項目をクリックすると、従来のバージョンのWindowsのような「システムのプロパティ」が開かれますので、リモートデスクトップの項目を「このコンピューターへのリモート接続を許可する」にします。その下の「ネットワークレベル認証で〜(推奨)」の設定はオンにしておいた方がいいでしょう。

f:id:virtualtech:20210511172423p:plain:w360

リモートデスクトップクライアントの設定

Windowsマシンであれば、リモートデスクトップクライアントはデフォルトで用意されています。 Macの場合は、AppStoreなどからリモートデスクトップクライアントがダウンロードできます。

Microsoft純正のリモートデスクトップクライアントを使う場合は「PC name」という項目に「ノードのIPアドレス:NodePort」を指定します。例えば「192.168.0.100:30389」のような感じです。あとの項目はいつものように必要な設定を仕込んでいきます。

f:id:virtualtech:20210511174108p:plain

サードパーティのリモートデスクトップクライアント、例えばParallels Clientの場合、IPアドレスとポートを別に設定できるものも存在します。私的にはこちらの方が好きです。

f:id:virtualtech:20210511172608p:plain

KubeVirtはVNCコンソールで操作はできますが、デフォルトの設定のままだとマウスの矢印に大きなずれがあるので使いずらい問題があります。対象がWindowsであれば、これまで説明した設定を行うことでRDPプロトコルを使ったWindows VMへのリモートアクセスが可能になります。

f:id:virtualtech:20210511173921p:plain

VNCコンソールによるアクセス時に起きていた、マウスの矢印のずれがなくなるほか、文字列などのコピーペーストやリモートソースへのローカルソースのマウントなどができるようになって便利になります。