## 介紹 [Vagrant](https://developer.hashicorp.com/vagrant) 可以迅速建立虛擬主機配置環境,不需要再像 Vitrual Box 將整個 OS 安裝一遍,只需要使用 [Vagrant boxes](https://developer.hashicorp.com/vagrant/docs/boxes) 就可以馬上獲得一個作業系統。在 [Vagrant Cloud](https://app.vagrantup.com/boxes/search) 上就能搜尋需要的 box 來使用,尤其官方特邊推薦 [Bento Boxes](https://app.vagrantup.com/bento) 中的 boxes,除了大部分為知名創作者外,大部分品質穩定且也都在 Github 上開源。 ## 安裝 直接到 [Vagrant 官網](https://developer.hashicorp.com/vagrant/downloads)下載相對應的版本即可。 本人使用 Windows 做示範,請使用 Windows 可執行的 Bash CMD 即可。 ## 示範 ### 1. 版本顯示 輸入: ``` $ vagrant version ``` 輸出: ``` Installed Version: 2.3.7 Latest Version: 2.3.7 You're running an up-to-date version of Vagrant! ``` ### 2. 初始化 box 輸入: ``` $ mkdir ~/Desktop/workspace $ cd ~/Desktop/workspace $ vagrant init bento/centos-7.9 ``` 輸出: ``` A `Vagrantfile` has been placed in this directory. You are now ready to `vagrant up` your first virtual environment! Please read the comments in the Vagrantfile as well as documentation on `vagrantup.com` for more information on using Vagrant. ``` 注意:若資料夾內已有 Vagrantfile 時則不能重複初始化新的 box。 ### 3. 啟動 box 輸入: ``` $ vagrant up ``` 輸出: ``` Bringing machine 'default' up with 'virtualbox' provider... ==> default: Box 'bento/centos-7.9' could not be found. Attempting to find and install... default: Box Provider: virtualbox default: Box Version: >= 0 ==> default: Loading metadata for box 'bento/centos-7.9' default: URL: https://vagrantcloud.com/bento/centos-7.9 ==> default: Adding box 'bento/centos-7.9' (v202303.13.0) for provider: virtualbox default: Downloading: https://vagrantcloud.com/bento/boxes/centos-7.9/versions/202303.13.0/providers/virtualbox.box default: ==> default: Successfully added box 'bento/centos-7.9' (v202303.13.0) for 'virtualbox'! ==> default: Importing base box 'bento/centos-7.9'... ==> default: Matching MAC address for NAT networking... ==> default: Checking if box 'bento/centos-7.9' version '202303.13.0' is up to date... ==> default: Setting the name of the VM: workspace_default_1689059864043_23910 ==> default: Fixed port collision for 22 => 2222. Now on port 2200. ==> default: Clearing any previously set network interfaces... ==> default: Preparing network interfaces based on configuration... default: Adapter 1: nat ==> default: Forwarding ports... default: 22 (guest) => 2200 (host) (adapter 1) ==> default: Booting VM... ==> default: Waiting for machine to boot. This may take a few minutes... default: SSH address: 127.0.0.1:2200 default: SSH username: vagrant default: SSH auth method: private key default: default: Vagrant insecure key detected. Vagrant will automatically replace default: this with a newly generated keypair for better security. default: default: Inserting generated public key within guest... default: Removing insecure key from the guest if it's present... default: Key inserted! Disconnecting and reconnecting using new SSH key... ==> default: Machine booted and ready! ==> default: Checking for guest additions in VM... default: The guest additions on this VM do not match the installed version of default: VirtualBox! In most cases this is fine, but in rare cases it can default: prevent things such as shared folders from working properly. If you see default: shared folder errors, please make sure the guest additions within the default: virtual machine match the version of VirtualBox you have installed on default: your host and reload your VM. default: default: Guest Additions Version: 7.0.6 default: VirtualBox Version: 6.1 ==> default: Mounting shared folders... default: /vagrant => C:/Users/Kurt/Desktop/workspace ``` 注意:因首次啟動需要下載整份 box,所以耗時會較久 ### 4. ssh box 輸入: ``` $ vagrant ssh ``` 輸出: ``` This system is built by the Bento project by Chef Software More information can be found at https://github.com/chef/bento [vagrant@localhost ~]$ ``` #### 此時我們已進入這個 box 之中,而我們這次使用的系統是 CentOS 7.9。 輸入: ``` $ cat /etc/*release* ``` 輸出: ``` CentOS Linux release 7.9.2009 (Core) Derived from Red Hat Enterprise Linux 7.9 (Source) NAME="CentOS Linux" VERSION="7 (Core)" ID="centos" ID_LIKE="rhel fedora" VERSION_ID="7" PRETTY_NAME="CentOS Linux 7 (Core)" ANSI_COLOR="0;31" CPE_NAME="cpe:/o:centos:centos:7" HOME_URL="https://www.centos.org/" BUG_REPORT_URL="https://bugs.centos.org/" CENTOS_MANTISBT_PROJECT="CentOS-7" CENTOS_MANTISBT_PROJECT_VERSION="7" REDHAT_SUPPORT_PRODUCT="centos" REDHAT_SUPPORT_PRODUCT_VERSION="7" CentOS Linux release 7.9.2009 (Core) CentOS Linux release 7.9.2009 (Core) cpe:/o:centos:centos:7 ``` 注意:通常默認的密碼為 `vagrant`,若無法登入上網查應該也有答案。 ### 5. 關閉 box 輸入: ``` $ vagrant halt ``` 輸出: ``` ==> default: Attempting graceful shutdown of VM... ``` ### 6. 命名此 box 因預設初始化 box 時通常命名為 default,當太多 box 在執行時會產生錯亂。 輸入: ``` $ vagrant status ``` 輸出: ``` Current machine states: default poweroff (virtualbox) The VM is powered off. To restart the VM, simply run `vagrant up` ``` 我們只需要在 Vagrantfile 中增加 define 的設定即可。 Vagrantfile: ``` Vagrant.configure("2") do |config| config.vm.box = "bento/centos-7.9" config.vm.define "Training_for_TS" end ``` 此時再將 box up 之後就能看到 box 已更名為 Training_for_TS。 輸入: ``` $ vagrant.exe up ``` 輸出: ``` Bringing machine 'Training_for_TS' up with 'virtualbox' provider... ==> Training_for_TS: Importing base box 'bento/centos-7.9'... ==> Training_for_TS: Matching MAC address for NAT networking... ==> Training_for_TS: Checking if box 'bento/centos-7.9' version '202303.13.0' is up to date... ==> Training_for_TS: Setting the name of the VM: workspace_Training_for_TS_1689061454221_81981 ==> Training_for_TS: Fixed port collision for 22 => 2222. Now on port 2200. ==> Training_for_TS: Clearing any previously set network interfaces... ==> Training_for_TS: Preparing network interfaces based on configuration... Training_for_TS: Adapter 1: nat ==> Training_for_TS: Forwarding ports... Training_for_TS: 22 (guest) => 2200 (host) (adapter 1) ==> Training_for_TS: Booting VM... ==> Training_for_TS: Waiting for machine to boot. This may take a few minutes... Training_for_TS: SSH address: 127.0.0.1:2200 Training_for_TS: SSH username: vagrant Training_for_TS: SSH auth method: private key Training_for_TS: Training_for_TS: Vagrant insecure key detected. Vagrant will automatically replace Training_for_TS: this with a newly generated keypair for better security. Training_for_TS: Training_for_TS: Inserting generated public key within guest... Training_for_TS: Removing insecure key from the guest if it's present... Training_for_TS: Key inserted! Disconnecting and reconnecting using new SSH key... ==> Training_for_TS: Machine booted and ready! ==> Training_for_TS: Checking for guest additions in VM... Training_for_TS: The guest additions on this VM do not match the installed version of Training_for_TS: VirtualBox! In most cases this is fine, but in rare cases it can Training_for_TS: prevent things such as shared folders from working properly. If you see Training_for_TS: shared folder errors, please make sure the guest additions within the Training_for_TS: virtual machine match the version of VirtualBox you have installed on Training_for_TS: your host and reload your VM. Training_for_TS: Training_for_TS: Guest Additions Version: 7.0.6 Training_for_TS: VirtualBox Version: 6.1 ==> Training_for_TS: Mounting shared folders... Training_for_TS: /vagrant => C:/Users/Kurt/Desktop/workspace ``` 輸入: ``` $ vagrant status ``` 輸出: ``` Current machine states: Training_for_TS running (virtualbox) The VM is running. To stop this VM, you can run `vagrant halt` to shut it down forcefully, or you can run `vagrant suspend` to simply suspend the virtual machine. In either case, to restart it again, simply run `vagrant up`. ``` ### 7. 打包 box 打包 box 的目的是為了讓其他人能用完全相同的開發環境,這樣才能確保所有人都是在相同的基礎上開發。 打包需要在 box 為關機狀態下才能進行。 輸入: ``` $ vagrant package ``` 輸出: ``` ==> Training_for_TS: Clearing any previously set forwarded ports... ==> Training_for_TS: Exporting VM... ==> Training_for_TS: Compressing package to: C:/Users/Kurt/Desktop/workspace/package.box ``` 打包完成後會出現一個新檔案 package.box,此時只需要將此 package.box 傳給其他組員,其他組員就能使用相同的環境開發。 ### 8. 新增 box 當拿到 box 或 box 的 url,我們可以使用指令加入到我們的環境中。 首先我們先確認我們環境中有那些 box。 輸入: ``` $ vagrant box list ``` 輸出: ``` bento/centos-7.9 (virtualbox, 202303.13.0) ``` 使用指令將 package.box 加到我們的 list 中。 輸入: ``` $ vagrant box add TS_team package.box ``` 輸出: ``` ==> box: Box file was not detected as metadata. Adding it directly... ==> box: Adding box 'TS_team' (v0) for provider: box: Unpacking necessary files from: file://C:/Users/Kurt/Desktop/workspace/package.box box: ==> box: Successfully added box 'TS_team' (v0) for 'virtualbox'! ``` #### 注意:package.box 的位置可以是一個檔案或 url。 此時我們確認 box list 中已增加了 TS_team 這個 box。 輸入: ``` $ vagrant box list ``` 輸出: ``` TS_team (virtualbox, 0) bento/centos-7.9 (virtualbox, 202303.13.0) ``` 最後我們只需要在新的資料夾內初始化這個 box,就能得到一模一樣的開發環境了。 輸入: ``` $ mkdir ~/Desktop/TS_team $ cd ~/Desktop/TS_team $ vagrant init TS_team $ vagrant status $ vagrant ssh ``` ## 結語 有時團隊在開發時可能會共用開發環境,但這其實可能並不是太好的做法,如果大家各自能拿到一模一樣的開發環境,並分別開發,最後再用各自的版本控制合在 Staging 上並測試,或許也是一個不錯的方案。 主要會想使用這個方法的契機為 TS Team 在 training 時發現各個工程師的環境不盡相同,有人使用 CentOS7,有人用 docker,也有人用 RHEL9,而此次剛好又是 DB 相關的 training,還需要各自再倒資料進 DB,耗費許多時間。若一開始準備好已倒好資料的環境給每個人使用,就可以減少前期在建置的這些時間。 原有使用 Virtual Box 的人也可以試著使用 Vagrant 看看,雖然 Vagrant 是建立在 Virtual Box 之上,但省下下載 iSO 和安裝的時間,可以利用這些時間做更多的事,也是更好的方案。