1. 首先確認Jenkins上安裝了Git plugin, 以及Subversion plugin
Manage Jenkins -> Plugin Manager -> Available
2. 配置git命令路徑
Manage Jenkins -> Global Tool Configuration, 順便把JDK, ANT, Maven也配置了
3. 在Jenkins安裝的服務器上, 創建一對rsa key, 並配置
ssh-keygen -t rsa -C "jenkins" # 一路回車, 默認路徑和文件名, 不要密碼 cd ~/.ssh mv id_rsa id_rsa_tho mv id_rsa.pub id_rsa_tho.pub
4. 在gitlab的項目下, 點擊右側配置菜單 -> Deploy Keys, 用剛才創建的 id_rsa_tho.pub 的內容, 創建一個key, 名稱為 Readonly Key for Jenkins, 如果有多個項目都需要這個私鑰, 則在每個項目的deploy keys下enable這個key即可. 可以用下面的方式驗證是否生效
# 以下步驟, 只是為了驗證key是否有效, 實際項目中不需要這么設置 vi config # 寫入以下內容 Host 192.168.1.109 RSAAuthentication yes IdentityFile ~/.ssh/id_rsa_tho User milton # 必須要修改讀取權限否則ssh連接時會報錯 chmod 600 config # 運行git命令檢查一下是否有效, 如果有錯, 根據提示處理 git ls-remote -h git@192.168.1.109:cc/tho.git HEAD
5. 檢驗: 在Jenkins中, 新建一個freestyle的項目, 點擊項目 -> Source Code Management, 選擇 Git, 填入gitlab中給的項目地址 git@192.168.1.109:cc/tho.git 在下面add new credential, Username:git, Private Key Enter Directly, 輸入剛才創建的 id_rsa_tho 的內容, 注意這個是私鑰.
6. 如果切換鼠標焦點后, 項目地址欄下方沒有錯誤提示, 就說明Jenkins檢查沒錯
以下是通過Pipeline Script進行部署的說明
同樣需要Git Plugin插件, 還需要另外安裝Pipeline, SSH Agent, 因為Publish Over SSH插件尚未支持Pipeline, 所以只能通過ssh agent自己寫命令來處理, 我在項目中的script如下
node { // Mark the code checkout 'stage'.... stage 'Checkout' sh "mkdir -p tho" dir('thor') { git branch: 'master', credentialsId: '29254e2e-256c-47e0-8a9a-756f16e6705a', url: 'git@192.168.10.239:cc/tho.git' } sh "mkdir -p tho-commons" dir('tho-commons') { git branch: 'master', credentialsId: '29254e2e-256c-47e0-8a9a-756f16e6705a', url: 'git@192.168.10.239:cc/tho-commons.git' } sh "mkdir -p thor-commons-lib" dir('tho-commons-lib') { git branch: 'master', credentialsId: '29254e2e-256c-47e0-8a9a-756f16e6705a', url: 'git@192.168.10.239:cc/tho-commons-lib.git' } sh "mkdir -p thor-commons-api" dir('tho-commons-api') { git branch: 'master', credentialsId: '29254e2e-256c-47e0-8a9a-756f16e6705a', url: 'git@192.168.10.239:cc/tho-commons-api.git' } sh "mkdir -p tho-commons-impl" dir('tho-commons-impl') { git branch: 'master', credentialsId: '29254e2e-256c-47e0-8a9a-756f16e6705a', url: 'git@192.168.10.239:yhc/tho-commons-impl.git' } env.JAVA_HOME="${tool 'jdk1.8.0_45'}" sh '$JAVA_HOME/bin/java -version' def mvnHome = tool 'M3.3' stage 'Build' dir('tho-commons') { sh "${mvnHome}/bin/mvn -s /home/tomcat/files/settings.xml clean install -Dmaven.test.skip=true -Ptho_dev -e" } sshagent(['d5058e06-4873-4f82-850b-1d5da1b80dc8']) { sh 'ssh -p 22 tomcat@15.28.12.16 \'df -h\'' sh 'scp tho-commons-impl/target/tho-commons.war tomcat@15.28.12.16:/home/tomcat/ant_build/' } }
非標准端口的git地址, 可以用
sh "mkdir -p tho-commons" dir('tho-commons') { git branch: 'master', credentialsId: '201e0d5b-27b5-46dc-9a1a-920859fd6952', url: 'ssh://git@1.2.3.4:6022/cc/tho-commons.git' }
這個腳本完成了導出代碼, 編譯, 部署, 執行的工作. 里面需要的前提條件:
1. git里面的credentialID對應credential里添加過的私鑰, 其公鑰配置在gitlab的deploy keys里.
2. sshagent里面的credentialID對應在Credential里面添加過私鑰, 其公鑰配置在15.28.12.16的tomcat用戶下
3. M3.3對應的Maven, jdk1.8.0_45對應的JDK1.8, ss
4. Maven用到的settings.xml文件
配置使用密鑰文件登錄
使用密鑰文件代替普通的簡單密碼認證也會極大的提高安全性:
[dir@username ~]$ ssh-keygen -t rsa -b 2048 Generating public/private rsa key pair. Enter file in which to save the key (/root/.ssh/id_rsa): //默認路徑,回車 Enter passphrase (empty for no passphrase): //輸入你的密鑰短語,登錄時使用 Enter same passphrase again: Your identification has been saved in /root/.ssh/id_rsa. Your public key has been saved in /root/.ssh/id_rsa.pub. The key fingerprint is: 3e:fd:fc:e5:d3:22:86:8e:2c:4b:a7:3d:92:18:9f:64 root@ibpak.tp-link.net The key's randomart image is: +--[ RSA 2048]----+ | | … | o++o..oo..o| +-----------------+
將公鑰重命名為authorized_key:
$ mv ~/.ssh/id_rsa.pub ~/.ssh/authorized_keys $ chmod 600 ~/.ssh/authorized_keys
下載私鑰文件 id_rsa 到本地(為了更加容易識別,可重命名為id_rsa_hostname_username),保存到安全的地方。以后 username 用戶登錄這台主機就必須使用這個私鑰,配合密碼短語來登錄(不再使用 username 用戶自身的密碼)
另外還要修改/etc/ssh/sshd_config文件
打開注釋
RSAAuthentication yes
PubkeyAuthentication yes
AuthorizedKeysFile .ssh/authorized_keys
我們要求 username 用戶(可以切換到其他用戶,特別是root)必須使用ssh密鑰文件登錄,而其他普通用戶可以直接密碼登錄。因此還需在sshd_config文件最后加入:
Match User itsection
PasswordAuthentication no
重啟sshd服務后生效
常出現的問題:
1. 源主機和目標主機上, 對應用戶下的.ssh目錄和私鑰/公鑰文件權限不正確, 都應當為600 or 700, 不是這個權限的系統會忽略. 具體的錯誤, 可以通過客戶端的 ssh -v 方式, 以及服務端的 /var/log/secure 日志查看原因.
2. 雖然可以直接把ssh的private key 配到jenkins, 但是還是需要手工在ssh命令行下, 將private key配到 .ssh目錄下, 然后手工 ssh 登錄一次, 因為第一次登錄會彈出接受RSA key的提示, 回答yes后, 用jenkins登就沒問題了
Update 2019-06-27: 在Jenkins 2.176.1上測試, 以上說法有誤. 不需要將key配置到.ssh, 只需要在命令行下ssh用密碼登錄一次即可. 目的也是為了接收RSA key
RSA key fingerprint is xx:b7:d5:c0:1d:d4:d4:f3:ee:8a:5d:xx:ee:xx:xx:xx. Are you sure you want to continue connecting (yes/no)? yes Warning: Permanently added '[192.168.10.11]:39922' (RSA) to the list of known hosts.
否則在jenkins中會出現這個錯誤提示
debug1: checking without port identifier debug1: read_passphrase: can't open /dev/tty: No such device or address Host key verification failed.