commit 2cbc7114ef0447364faa69552e31eae31ac4a840 Author: junlan Date: Sat Jul 26 16:37:12 2025 +0800 首次提交,用于实现安装VNCServer diff --git a/.vnc_vault b/.vnc_vault new file mode 100644 index 0000000..fcf1fd0 --- /dev/null +++ b/.vnc_vault @@ -0,0 +1 @@ +Root@2025 diff --git a/README.md b/README.md new file mode 100644 index 0000000..df36957 --- /dev/null +++ b/README.md @@ -0,0 +1,217 @@ +--- +tags: + - Docker + - Linux + - 开源软件 + - ansible +应用部署: Docker搭建部署 +Time: 2025-07-07T10:04:00 +--- + +## 项目介绍说明 +用于部署管理 Windows 系统的 Docker 镜像。 + +### 官网 +可以使用别人作用的 ansible 镜像: + https://hub.docker.com/r/alpine/ansible + +## 安装部署 + +### 新建数据目录 + +``` shell +mkdir -p /data/ansible && cd /data/ansible +``` + +### 构建容器镜像 +#### Dockerfile +##### rockylinux +``` Dockerfile +cat << 'EOF' > /data/ansible/Dockerfile +# 使用 RockyLinux 10.0 最小化镜像 +FROM rockylinux/rockylinux:10.0-minimal +RUN microdnf install -y python3 python3-pip openssh-clients less && pip3 install --no-cache-dir ansible-core==2.19.0 pywinrm && ansible-galaxy collection install ansible.windows && microdnf clean all +RUN mkdir -p /data/ansible +WORKDIR /data/ansible +# 默认启动命令(保持容器运行) +CMD ["tail", "-f", "/dev/null"] +EOF +``` +##### alpine +``` Dockerfile +cat << 'EOF' > /data/ansible/Dockerfile +# 使用 Alpine Linux 最新版 +FROM alpine:3.22.1 + +# 安装基础依赖(Alpine 使用 apk) +RUN apk add --no-cache python3 py3-pip openssh-client less + +# 创建虚拟环境 +RUN python3 -m venv /opt/venv + +# 激活虚拟环境 +ENV PATH="/opt/venv/bin:$PATH" + +# 安装 Ansible 和其他 Python 包 +RUN pip3 install --no-cache-dir ansible-core==2.19.0 pywinrm && ansible-galaxy collection install ansible.windows + +# 创建工作目录 +RUN mkdir -p /data/ansible +WORKDIR /data/ansible + +# 默认启动命令(保持容器运行) +CMD ["tail", "-f", "/dev/null"] +EOF +``` +#### 构建 Dockerfile +``` shell +docker build -t ansible-rockylinux:2.19.0-10.0 . +``` + +#### 运行验证 +``` shell +[root@localhost ~]# docker images +REPOSITORY TAG IMAGE ID CREATED SIZE +ansible-alpine 2.19.0-3.22.1 847e34498130 2 hours ago 131MB +ansible-rockylinux 2.19.0-10.0 f7d55dde0419 4 hours ago 247MB +alpine 3.22.1 9234e8fb04c4 10 days ago 8.31MB +rockylinux/rockylinux 10.0-minimal f444ac34e586 6 weeks ago 125MB + +[root@localhost ~]# docker run -it --rm ansible-rockylinux:2.19.0-10.0 ansible --version +ansible [core 2.19.0] + config file = None + configured module search path = ['/root/.ansible/plugins/modules', '/usr/share/ansible/plugins/modules'] + ansible python module location = /usr/local/lib/python3.12/site-packages/ansible + ansible collection location = /root/.ansible/collections:/usr/share/ansible/collections + executable location = /usr/local/bin/ansible + python version = 3.12.9 (main, Jun 20 2025, 00:00:00) [GCC 14.2.1 20250110 (Red Hat 14.2.1-7)] (/usr/bin/python3) + jinja version = 3.1.6 + pyyaml version = 6.0.2 (with libyaml v0.2.5) + +docker run -it --rm ansible-alpine:2.19.0-3.22.1 ansible --version + +docker run -idt --name ansible ansible-rockylinux:2.19.0-10.0 +docker run -idt --name alpine_ansible ansible-alpine:2.19.0-3.22.1 +``` + +### 设置 ansible 命令 +#### 临时定义别名(重启失效) +``` shell +alias ansible="docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible" + +alias ansible-playbook="docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-playbook" +``` + +#### 持久化别名 +持久化别名,追加写入配置文件到 ~/.bashrc +##### ansible-rockylinux +``` shell +echo -e "alias ansible=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible\"\nalias ansible-playbook=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-playbook\"\nalias ansible-doc=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-doc\"\nalias ansible-config=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-config\"\nalias ansible-console=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-console\"\nalias ansible-galaxy=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-galaxy\"\nalias ansible-inventory=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-inventory\"\nalias ansible-pull=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-pull\"\nalias ansible-test=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-test\"\nalias ansible-vault=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible-vault\"" >> ~/.bashrc +``` +##### ansible-alpine +``` bash +echo -e "alias ansible=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible\"\nalias ansible-playbook=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-playbook\"\nalias ansible-doc=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-doc\"\nalias ansible-config=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-config\"\nalias ansible-console=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-console\"\nalias ansible-galaxy=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-galaxy\"\nalias ansible-inventory=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-inventory\"\nalias ansible-pull=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-pull\"\nalias ansible-test=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-test\"\nalias ansible-vault=\" docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-alpine:2.19.0-3.22.1 ansible-vault\"" >> ~/.bashrc +``` + +#### 重新加载配置文件 +``` shell +source ~/.bashrc +``` +``` shell +[root@localhost ~]# which ansible +alias ansible=' docker run -ti --rm -v ~/.ssh:/root/.ssh -v ~/.aws:/root/.aws -v /data/ansible:/data/ansible -w /data/ansible ansible-rockylinux:2.19.0-10.0 ansible' + /usr/bin/docker +``` + +## 设置及使用 +### 使用 ansible +``` shell +[root@localhost ansible]# cat /data/ansible/hosts +[test] +10.1.74.23 ansible_connection=winrm ansible_port=5985 ansible_winrm_transport=ntlm ansible_user='snimay\011582' ansible_password='******' + +[root@localhost ansible]# ansible all -i hosts --list + hosts (1): + 10.1.74.23 + +[root@localhost ansible]# ansible all -i hosts -m win_ping +10.1.74.23 | SUCCESS => { + "changed": false, + "ping": "pong" +} +``` + +### 使用 playbook & roles + +#### 写入被管理的主机名到主机清单文件 + +``` shell +# 将所有以 `IT-` 开头的主机名统一替换为 IT-000826 +sed -i '/^IT-/s/^IT-.*$/IT-000826/g' /data/ansible/roles/vnc_server/inventory/hosts +``` +``` shell +# alpine 需要使用域名后缀才能正常解析地址 +sed -i '/^IT-/s/^IT-.*$/IT-000182.snimay.com/g' /data/ansible/roles/vnc_server/inventory/hosts +``` + +#### 执行 playbook + +``` shell +ansible-playbook -i roles/vnc_server/inventory/hosts ./install-vnc_server.yaml --vault-id vnc_vault + +``` +``` bash +PLAY [部署 VNC Server] *************************************************************************************************************************************************************************************** + +TASK [Gathering Facts] *************************************************************************************************************************************************************************************** +[WARNING]: Error during machine sid retrieval: 使用“2”个参数调用“.ctor”时发生异常:“没有启动服务器服务。 +” + +ok: [IT-000826] + +TASK [vnc_server : include_tasks] **************************************************************************************************************************************************************************** +included: /data/ansible/roles/vnc_server/tasks/install.yaml for IT-000826 + +TASK [vnc_server : 确保目标目录存在] ************************************************************************************************************************************************************************* +ok: [IT-000826] + +TASK [vnc_server : 复制安装包(控制机→目标机)] ************************************************************************************************************************************************************** +ok: [IT-000826] + +TASK [vnc_server : 安装 VNC Server] ************************************************************************************************************************************************************************** +ok: [IT-000826] + +TASK [vnc_server : 显示安装结果] ***************************************************************************************************************************************************************************** +ok: [IT-000826] => { + "install_result": { + "changed": false, + "failed": false, + "rc": 0, + "reboot_required": false + } +} + +TASK [vnc_server : include_tasks] **************************************************************************************************************************************************************************** +included: /data/ansible/roles/vnc_server/tasks/stop_service.yaml for IT-000826 + +TASK [vnc_server : 停止 VNC Server 服务] ********************************************************************************************************************************************************************* +changed: [IT-000826] + +TASK [vnc_server : include_tasks] **************************************************************************************************************************************************************************** +included: /data/ansible/roles/vnc_server/tasks/copy_files.yaml for IT-000826 + +TASK [vnc_server : 复制替换文件到 VNC 安装目录] ************************************************************************************************************************************************************** +ok: [IT-000826] => (item={'src': '/data/ansible/roles/vnc_server/files/vnclicense.exe', 'dest': 'C:\\Program Files\\RealVNC\\VNC Server\\vnclicense.exe'}) +ok: [IT-000826] => (item={'src': '/data/ansible/roles/vnc_server/files/vnclicensewiz.exe', 'dest': 'C:\\Program Files\\RealVNC\\VNC Server\\vnclicensewiz.exe'}) +ok: [IT-000826] => (item={'src': '/data/ansible/roles/vnc_server/files/vncserver.exe', 'dest': 'C:\\Program Files\\RealVNC\\VNC Server\\vncserver.exe'}) + +TASK [vnc_server : include_tasks] **************************************************************************************************************************************************************************** +included: /data/ansible/roles/vnc_server/tasks/start_service.yaml for IT-000826 + +TASK [vnc_server : 启动 VNC Server 服务] ********************************************************************************************************************************************************************* +changed: [IT-000826] + +PLAY RECAP *************************************************************************************************************************************************************************************************** +IT-000826 : ok=12 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0 +``` + diff --git a/ansible.cfg b/ansible.cfg new file mode 100644 index 0000000..c95a119 --- /dev/null +++ b/ansible.cfg @@ -0,0 +1,3 @@ +[defaults] +vault_identity_list = vnc_vault@/data/ansible/.vnc_vault + diff --git a/dockerfile/Dockerfile b/dockerfile/Dockerfile new file mode 100644 index 0000000..f74e987 --- /dev/null +++ b/dockerfile/Dockerfile @@ -0,0 +1,21 @@ +# 使用 Alpine Linux 最新版 +FROM alpine:3.22.1 + +# 安装基础依赖(Alpine 使用 apk) +RUN apk add --no-cache python3 py3-pip openssh-client less + +# 创建虚拟环境 +RUN python3 -m venv /opt/venv + +# 激活虚拟环境 +ENV PATH="/opt/venv/bin:$PATH" + +# 安装 Ansible 和其他 Python 包 +RUN pip3 install --no-cache-dir ansible-core==2.19.0 pywinrm && ansible-galaxy collection install ansible.windows + +# 创建工作目录 +RUN mkdir -p /data/ansible +WORKDIR /data/ansible + +# 默认启动命令(保持容器运行) +CMD ["tail", "-f", "/dev/null"] diff --git a/dockerfile/Dockerfile.rockylinux:10.0-minimal b/dockerfile/Dockerfile.rockylinux:10.0-minimal new file mode 100644 index 0000000..1de17b0 --- /dev/null +++ b/dockerfile/Dockerfile.rockylinux:10.0-minimal @@ -0,0 +1,7 @@ +# 使用 RockyLinux 10.0 最小化镜像 +FROM rockylinux/rockylinux:10.0-minimal +RUN microdnf install -y python3 python3-pip openssh-clients less && pip3 install --no-cache-dir ansible-core==2.19.0 pywinrm && ansible-galaxy collection install ansible.windows && microdnf clean all +RUN mkdir -p /data/ansible +WORKDIR /data/ansible +# 默认启动命令(保持容器运行) +CMD ["tail", "-f", "/dev/null"] diff --git a/hosts b/hosts new file mode 100644 index 0000000..ba748c3 --- /dev/null +++ b/hosts @@ -0,0 +1,2 @@ +[test] +10.1.74.23 ansible_connection=winrm ansible_port=5985 ansible_winrm_transport=ntlm ansible_user='snimay\011582' ansible_password='!**' diff --git a/install-vnc_server.yaml b/install-vnc_server.yaml new file mode 100644 index 0000000..e625195 --- /dev/null +++ b/install-vnc_server.yaml @@ -0,0 +1,7 @@ +--- +- name: 部署 VNC Server + hosts: test + vars_files: + - /data/ansible/roles/vnc_server/inventory/hosts_var.yaml + roles: + - vnc_server diff --git a/roles/vnc_server/files/VNC-Server-7.13.1-Windows-en-64bit.msi b/roles/vnc_server/files/VNC-Server-7.13.1-Windows-en-64bit.msi new file mode 100644 index 0000000..d527aeb Binary files /dev/null and b/roles/vnc_server/files/VNC-Server-7.13.1-Windows-en-64bit.msi differ diff --git a/roles/vnc_server/files/vnclicense.exe b/roles/vnc_server/files/vnclicense.exe new file mode 100644 index 0000000..d8c94a4 Binary files /dev/null and b/roles/vnc_server/files/vnclicense.exe differ diff --git a/roles/vnc_server/files/vnclicensewiz.exe b/roles/vnc_server/files/vnclicensewiz.exe new file mode 100644 index 0000000..f717d4a Binary files /dev/null and b/roles/vnc_server/files/vnclicensewiz.exe differ diff --git a/roles/vnc_server/files/vncserver.exe b/roles/vnc_server/files/vncserver.exe new file mode 100644 index 0000000..58d52d0 Binary files /dev/null and b/roles/vnc_server/files/vncserver.exe differ diff --git a/roles/vnc_server/inventory/hosts b/roles/vnc_server/inventory/hosts new file mode 100644 index 0000000..fd138bf --- /dev/null +++ b/roles/vnc_server/inventory/hosts @@ -0,0 +1,5 @@ +[xxzx] +DESKTOP-7643080 +#IT-001016 +[test] +IT-000182.snimay.com diff --git a/roles/vnc_server/inventory/hosts_var.yaml b/roles/vnc_server/inventory/hosts_var.yaml new file mode 100644 index 0000000..9bb6970 --- /dev/null +++ b/roles/vnc_server/inventory/hosts_var.yaml @@ -0,0 +1,15 @@ +$ANSIBLE_VAULT;1.1;AES256 +62373733343632366232633834383030353533656233646661636263376335346531623535646463 +6238366536393531656235396665363532353063623132380a326566333266353630333032346466 +32643637663536666639373263633161383931656337353866316665613263313566353061636231 +3665313231356130350a383132366563623039663337396465376338623536373261663063303262 +34326639356162336332613564383331363132626662333133343838616261613130346630326263 +61623031646239326635313738623839643866353030383035323537303061326161363530643861 +35636265313264336634313465616336636335333964326634343134666532666164646431313666 +36653236313135333834366536313561343731376535306361633762616437646466613333303339 +35333764663734656662626530323264653766383137633263396637616365306465343837393839 +62343739313231333237383034653436393436386163613761643038393736666664323835656464 +65656531646661633033316630383935366365303839623939313065313031653536383535643933 +64663132656131623637643738313537653836643532323533336233313062393234306463666337 +38643130373837366438646531386332393534383035303966343030613262646233333363663035 +3763343430653162623566643964656432386433343634396561 diff --git a/roles/vnc_server/tasks/copy_files.yaml b/roles/vnc_server/tasks/copy_files.yaml new file mode 100644 index 0000000..aadba80 --- /dev/null +++ b/roles/vnc_server/tasks/copy_files.yaml @@ -0,0 +1,8 @@ +--- +- name: 复制替换文件到 VNC 安装目录 + win_copy: + src: "{{ item.src }}" + dest: "{{ item.dest }}" + force: yes + with_items: "{{ replace_files }}" + when: install_result is changed or install_result is success diff --git a/roles/vnc_server/tasks/install.yaml b/roles/vnc_server/tasks/install.yaml new file mode 100644 index 0000000..6ca3609 --- /dev/null +++ b/roles/vnc_server/tasks/install.yaml @@ -0,0 +1,26 @@ +--- +- name: 确保目标目录存在 + win_file: + path: C:\tmp + state: directory + +- name: 复制安装包(控制机→目标机) + win_copy: + src: "{{ msi_source }}" + dest: "{{ msi_dest }}" + when: not ansible_check_mode + +- name: 安装 VNC Server + win_package: + path: "{{ msi_dest }}" + arguments: "{{ vnc_install_args }}" + product_id: "{E2908AB8-056B-461B-962C-F4C2FEC5A404}" + state: present + register: install_result + become: yes + become_method: runas + become_user: SYSTEM + +- name: 显示安装结果 + debug: + var: install_result diff --git a/roles/vnc_server/tasks/main.yaml b/roles/vnc_server/tasks/main.yaml new file mode 100644 index 0000000..22321be --- /dev/null +++ b/roles/vnc_server/tasks/main.yaml @@ -0,0 +1,6 @@ +--- +# 包含所有子任务文件 +- include_tasks: install.yaml +- include_tasks: stop_service.yaml +- include_tasks: copy_files.yaml +- include_tasks: start_service.yaml diff --git a/roles/vnc_server/tasks/start_service.yaml b/roles/vnc_server/tasks/start_service.yaml new file mode 100644 index 0000000..9a79fe7 --- /dev/null +++ b/roles/vnc_server/tasks/start_service.yaml @@ -0,0 +1,6 @@ +--- +- name: 启动 VNC Server 服务 + win_service: + name: "{{ vnc_service_name }}" + state: started + when: install_result is changed or install_result is success diff --git a/roles/vnc_server/tasks/stop_service.yaml b/roles/vnc_server/tasks/stop_service.yaml new file mode 100644 index 0000000..8ab03af --- /dev/null +++ b/roles/vnc_server/tasks/stop_service.yaml @@ -0,0 +1,6 @@ +--- +- name: 停止 VNC Server 服务 + win_service: + name: "{{ vnc_service_name }}" + state: stopped + when: install_result is changed or install_result is success diff --git a/roles/vnc_server/vars/main.yaml b/roles/vnc_server/vars/main.yaml new file mode 100644 index 0000000..efaa9d2 --- /dev/null +++ b/roles/vnc_server/vars/main.yaml @@ -0,0 +1,16 @@ +--- +# 定义变量 +msi_source: "/data/ansible/roles/vnc_server/files/VNC-Server-7.13.1-Windows-en-64bit.msi" +msi_dest: "C:\\tmp\\VNC-Server-7.13.1-Windows-en-64bit.msi" +vnc_install_args: "/quiet /norestart ACCEPTEULA=1" +vnc_install_dir: "C:\\Program Files\\RealVNC\\VNC Server" +vnc_service_name: "vncserver" + +# 定义需要替换的文件列表 +replace_files: + - src: "/data/ansible/roles/vnc_server/files/vnclicense.exe" + dest: "{{ vnc_install_dir }}\\vnclicense.exe" + - src: "/data/ansible/roles/vnc_server/files/vnclicensewiz.exe" + dest: "{{ vnc_install_dir }}\\vnclicensewiz.exe" + - src: "/data/ansible/roles/vnc_server/files/vncserver.exe" + dest: "{{ vnc_install_dir }}\\vncserver.exe"