一、Jenkins基礎配置
1.配置中文
主界面–>系統管理–>插件管理–>可選插件
安裝插件locale plugin
系統管理–>系統設置–>Locale
填入:zh_CN
保存應用
2.插件管理
插件管理在 系統管理 -> 管理插件 裏面。
我們需要先完成的插件的安裝才能配置和管理我們Job,有以下幾種插件是我們需要的:
- Svn plugin(Svn 源碼管理插件)
- antPlugin(ant 打包插件)
- Publish Over SSH(遠程訪問的SSH插件)
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-NKF6HTfl-1578832055211)(https://i.loli.net/2020/01/10/wGJr7RdiSyoce6h.png)]
3.全局工具配置
全局工具配置在 系統管理 -> Global Tool Configuration
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-0tSmlZ7G-1578832055212)(https://i.loli.net/2020/01/10/5v6zB1qbUQPilCc.png)]
- JDK配置
- Git配置
- Maven配置
- Ant配置
Name :ant_1.9.6
ANT_HOME: /home/data/apache-ant-1.9.6
- Gradle配置
4.系統配置
Jenkins Location
郵件配置圖
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-9oqJgXcp-1578832055212)(https://i.loli.net/2020/01/10/sVMklCj3euwg5f7.png)]
SSH配置
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-voRl7lmk-1578832055213)(https://i.loli.net/2020/01/10/qngVMPmL2uykp1Q.png)]
配置完成後點擊TestConfiguration進行測試,是否連通。
如果是服務器集羣的話,就再增加一個 SSH Server。
二、新建任務
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-f2CFtFGX-1578832055213)(https://i.loli.net/2020/01/10/ZwMkHCBlbGJ4RLK.png)]
1.添加任務描述
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-YDEJpEUE-1578832055213)(https://i.loli.net/2020/01/10/uEe68y7xKjHOmo9.png)]
2.源碼管理
選擇Subversion綁定svn
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-HxCCU476-1578832055214)(https://i.loli.net/2020/01/10/DjWTJpLPMg4F7N5.png)]
Check-out Strategy各個選項詳細
Check-out Strategy | 第一次build | 第n次build(除第一次) |
Use 'svn update' as much as possible | 將workspace下的所有文件清空,然後從svn上check out一份完整的項目到workspace下 | update前不會revert |
Always check out a fresh copy | 刪除workspace下的所有文件,然後重新check out一份完整的項目到workspace下。 | |
Emulate clean checkout by first deleting unversioned/ignored files, then 'svn update' | update前先刪除unversioned/ignored文件 | |
Use 'svn update' as much as possible, with 'svn revert' before updat | update前先revert |
3.構建觸發器
可選擇定時構建,輪詢構建等多種方式。
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-e8s56SEy-1578832055216)(https://i.loli.net/2020/01/10/6PVQEMlrZJUkwoD.png)]
4.構建環境
4.1配置Ant
不指定時默認使用build.xml,我這裏新寫了一個add_build.xml配置後執行。
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-yXipTxH6-1578832055217)(https://i.loli.net/2020/01/10/NbRv5eSrpmaMjhk.png)]
add_build.xml:
<?xml version="1.0" encoding="UTF-8"?>
<project name="policy_vhl_110" basedir="." default="package">
<property environment="env" />
<property name="ant.home" value="${env.ANT_HOME}" />
<property name="java.home" value="${env.JAVA_HOME}" />
<property name="src.dir" value="${basedir}/src/path" />
<property name="src.lib" value="${basedir}/src/templib" />
<property name="src.dir_1" value="${basedir}/src/main/java" />
<property name="src.dir_2" value="${basedir}/src/main/resources" />
<property name="src.dir_3" value="${basedir}/src/interface" />
<property name="web.dir" value="${basedir}/WebRoot" />
<property name="build.classes" value="${web.dir}/WEB-INF/classes" />
<property name="dist.dir" value="${basedir}/policy_vhl_jar" />
<property name="conf.dir" value="${web.dir}/WEB-INF/classes/conf" />
<property name="temp_build.dir" value="${basedir}/build" />
<property name="conf.dir_1" value="${web.dir}/WEB-INF/"/>
<!-- 依賴路徑,用於編譯 -->
<path id="classpath">
<!--<fileset dir="${basedir}/build">
<include name="**/*.jar" />
</fileset> -->
<fileset dir="${web.dir}/WEB-INF/lib">
<include name="**/*.jar" />
</fileset>
</path>
<!-- 排除java源文件的模式集 -->
<patternset id="no.java">
<exclude name="**/*.java" />
</patternset>
<!-- 排除conf下配置文件 -->
<patternset id="properties">
<exclude name="**/applicationDeployment.properties" />
<exclude name="**/pcisv6DataSource.properties" />
<exclude name="**/*.java" />
</patternset>
<echo>******刪除pcis目錄下包</echo>
<delete dir="${src.dir}" />
<delete dir="${src.lib}" />
<delete dir="${build.classes}" />
<delete dir="${basedir}/conf" />
<echo level="info">清理完畢</echo>
<!-- 初始化,建立目錄,將多個src目錄複製到同一src目錄,編譯-->
<target name="init" description="初始化,建立目錄,複製文件">
<echo>**** init dir copy ****</echo>
<mkdir dir="${build.classes}" />
<mkdir dir="${dist.dir}" />
<mkdir dir="${src.dir}" />
<copy todir="${src.dir}">
<fileset dir="${src.dir_1}"/>
<fileset dir="${src.dir_2}"/>
<fileset dir="${src.dir_3}"/>
</copy>
<copy todir="${build.classes}">
<fileset dir="${src.dir_1}">
<patternset refid="no.java" />
<patternset refid="properties" />
</fileset>
<fileset dir="${src.dir_2}">
<patternset refid="properties" />
</fileset>
<fileset dir="${src.dir_3}">
<patternset refid="properties" />
</fileset>
</copy>
</target>
<!-- 編譯 -->
<target name="compile" depends="init">
<echo>**** compile to classes dir ****</echo>
<javac srcdir="${src.dir}" destdir="${build.classes}" target="1.6" source="1.6" debug="true" debuglevel="lines,vars,source" fork="true" executable="/home/data/jdk1.6.0_45/bin/javac" memoryMaximumSize="1024m" nowarn="on" includeantruntime="true">
<compilerarg line="-encoding UTF-8" />
<classpath refid="classpath" />
</javac>
</target>
<path id="lib_classpath">
<fileset dir="${basedir}/">
<include name="svnPacket.jar"/>
</fileset>
</path>
<target name="package" depends="compile">
<echo>開始.......</echo>
<!-- <java classname="com.glory.svn.SVNKitUtil" classpathref="lib_classpath">
</java>-->
<echo>結束.......</echo>
</target>
</project>
4.2執行shell
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-9wqdycsk-1578832055217)(https://i.loli.net/2020/01/10/euO3CgoGwy6lxvM.png)]
因爲項目目前的打包方式是增量包,所以在這裏使用java寫了一個腳本,作用是將想發佈的內容以版本號爲標的,將兩個版本號範圍內提交的內容提取到一個文件內(svn_version.txt),再使用打包工具將文件內的列表進行打包。
其中主要使用的是svnkit的jar包獲取svn對應版本號內提交的內容,將路徑進行轉換成class路徑輸出到目標文件內。
具體代碼如下:
private static String line = System.getProperty("line.separator", "/n");
private static SVNRepository repository ;
private static Properties properties = new Properties();
static {
try {
InputStream is = new BufferedInputStream(new FileInputStream("svnconfig.properties"));
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(is, "UTF-8"));
properties.load(bufferedReader);
} catch (IOException e) {
e.printStackTrace();
}
}
public static void setupLibrary() {
DAVRepositoryFactory.setup();
SVNRepositoryFactoryImpl.setup();
FSRepositoryFactory.setup();
String uName;
try {
uName = (String)properties.get("SVN_URL");
repository = SVNRepositoryFactory.create(SVNURL.parseURIEncoded(uName));
} catch (SVNException e) {
e.printStackTrace();
}
uName = (String)properties.get("SVN_USERNAME");
String passwd = (String)properties.get("SVN_PASSWORD");
ISVNAuthenticationManager authManager = SVNWCUtil.createDefaultAuthenticationManager(uName, passwd.toCharArray());
repository.setAuthenticationManager(authManager);
// try {
// System.out.println("Repository Root:" + repository.getRepositoryRoot(true));
// System.out.println("Repository UUID:" + repository.getRepositoryUUID(true));
// } catch (SVNException e) {
// e.printStackTrace();
// }
}
public static void filterCommitHistoryTest() throws Exception {
long startRevision = 100L;
String versionStr = "100";
InputStream inputStream = null;
try {
File vFile = new File("svn_version.txt");
inputStream = new FileInputStream(vFile);
byte[] byets = new byte[(int)vFile.length()];
inputStream.read(byets);
versionStr = new String(byets,"utf-8");
} catch (IOException e) {
e.printStackTrace();
}finally {
if(null != inputStream) inputStream.close();
}
if(null != versionStr && !"".equals(versionStr)){
String[] versions = versionStr.split(",");
long endRevision = -1L;
final List<String> history = new ArrayList();
final List<Long> versionList = new ArrayList();
final Set<String> delPathSet = new HashSet();
for(String version : versions){
startRevision = Long.parseLong(version);
repository.log(new String[]{""}, startRevision, endRevision, true, true, new ISVNLogEntryHandler() {
public void handleLogEntry(SVNLogEntry svnlogentry) throws SVNException {
versionList.add(svnlogentry.getRevision());
Map<String, SVNLogEntryPath> mapLog = svnlogentry.getChangedPaths();
Set<String> keySet = mapLog.keySet();
Iterator var5 = keySet.iterator();
while(var5.hasNext()) {
String logkey = (String)var5.next();
char cType = ((SVNLogEntryPath)mapLog.get(logkey)).getType();
if ('D' == cType) {
delPathSet.add(logkey);
}
}
history.addAll((Collection)svnlogentry.getChangedPaths().keySet());
}
});
}
Set<String> fileNameSet = new HashSet();
StringBuilder sBuilder = new StringBuilder();
Iterator hisIter = history.iterator();
while(hisIter.hasNext()) {
String path = (String)hisIter.next();
if (!delPathSet.contains(path)) {
String className;
if (path.contains("WebRoot")) {
className = path.substring(path.indexOf("WebRoot"));
fileNameSet.add(className);
}
if (path.contains("src")) {
className = path.substring(path.indexOf("src"));
className = className.replace("src/main/java", "WebRoot/WEB-INF/classes");
className = className.replace("src/interface/com", "WebRoot/WEB-INF/classes/com");//只針對車承保
className = className.replace("src/com", "WebRoot/WEB-INF/classes/com");
className = className.replace("src/main/resources", "WebRoot/WEB-INF/classes");
className = className.replace("src", "WebRoot/WEB-INF/classes");
className = className.replace(".java", ".class");
fileNameSet.add(className);
}
}
}
int i = 0;
Iterator fileIter = fileNameSet.iterator();
while(fileIter.hasNext()) {
String namePath = (String)fileIter.next();
++i;
sBuilder.append(namePath);
if (i != fileNameSet.size()) {
sBuilder.append(line);
}
}
OutputStream outputStream = null;
try {
File file = new File("file_list.txt");
if (!file.exists()) {
try {
file.createNewFile();
} catch (IOException e) {
e.printStackTrace();
}
}
outputStream = new FileOutputStream(file);
outputStream.write(sBuilder.toString().getBytes());
outputStream.flush();
} catch (Exception e) {
e.printStackTrace();
}finally {
if(null != outputStream) outputStream.close();
}
}
}
public static void main(String[] args) throws Exception {
System.out.println("打包工程start");
setupLibrary();
filterCommitHistoryTest();
System.out.println("打包工程end");
}
命令:
echo =====gen file list begin=====
cd /var/lib/jenkins/workspace/policy_vhl_110/
java -jar svnPacket.jar
echo =====gen file list end=====
echo =====make jar======
jar cvf policy_vhl_jar/policy_vhl.jar @file_list.txt
echo ====make jar over=====
簡述下流程
- 首先代碼提交開發版本庫
- 由開發版本庫將內容合併至DEV版本庫
- 提交svn_version.txt文件,裏面記錄着想發佈到DEV環境的SVN version編號。例如:svn列表由上到下爲1、2、3、4代碼無交叉,svn_version記錄着2,3 ,則雖然1、2、3、4代碼已經發布了DEV環境的代碼基線,並且其代碼已經構建,但是隻會將2,3中提交的代碼進行打包。
- 根據file_list.txt記錄的具體class路徑進行打包,獲得指定版本編號範圍內的代碼。
- 將jar發佈至遠程服務,解壓重啓。
5.構建後操作
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-rnk9qtFe-1578832055218)(https://i.loli.net/2020/01/10/ZaXtE1pOjm9cg2b.png)]
指定環境變量,將jar發送到遠程服務器目標路徑下,解壓jar包後調用jenkins.sh腳本進行重啓。(容器爲weblogic)
echo =====jar begin=====
export JAVA_HOME=/usr/java/jrockit-jdk1.6.0_29-R28.1.5-4.0.1
export PATH=$JAVA_HOME/bin:/usr/local/bin:$PATH:$MAVEN_HOME/bin
export CLASSPATH=.:$JAVA_HOME/lib/tools.jar:$JAVA_HOME/lib/dt.jar
cd /usr/bin
ln -s -f /usr/java/jrockit-jdk1.6.0_29-R28.1.5-4.0.1/bin/jar jar
cd /home/source/7002/policy_vhl
jar -xvf policy_vhl.jar
echo =====jar end=====
cd /home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/
./jenkins.sh &
腳本主要是進行重啓,最後將jar包按照時間戳進行重命名。
#!/bin/bash
#jenkins 重啓腳本
#刪除lok文件
find /home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/ -name "*.lok" -print -exec rm -rf {} \;
#清除服務器緩存
cd /home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/servers/AdminServer/tmp/_WL_user
rm -rf pcisv7
#查找並強制殺死進程
ps -ef|egrep 7002|gawk '{print $2}'|while read pid
do
kill -9 $pid
done
#以當前時間命名後臺日誌,並顯示
str=$"/n"
MYDATE=`date +%Y%m%d%H%M%S`
echo "$MYDATE"
#清除歷史日誌,防止佔內存過多
cd /home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/logs
rm -rf *.log
cd /home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/bin
nohup ./startWebLogic.sh>/home/oracle/Oracle/Middleware/user_projects/domains/hhuat7002/logs/$MYDATE.log 2>&1 &
# 重命名jar包
mv /home/source/7002/policy_vhl/policy_vhl.jar policy_vhl.$MYDATE.jar
6.立即構建
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-0p7do9Ye-1578832055219)
(https://i.loli.net/2020/01/10/QzjkSHuMGT3ah8L.png)]
三、問題處理
ant編譯時亂碼問題:
編譯時遇到 “非法字符: \65279”的報錯
[javac] /var/lib/jenkins/workspace/policy_vhl_110/src/path/interface/com/isoftstone/pcis/policy/foreignInterface/service/impl/ElectricityPinServiceImpl.java:1: 非法字符: \65279
解決:https://blog.csdn.net/netwalk/article/details/52005546
軟件包 javax.servlet 不存在
軟件包 javax.servlet 不存在
[javac] import javax.servlet.ServletException;
解決辦法:
從tomcat lib目錄下拷貝一個servlet-api.jar的包到“JDK\jre\lib\ext”目錄下
凡是出現找不到包的情況,都可以將找到的包放到JDK\jre\lib\ext下,然後再編譯就能夠通過。
四、擴展資料
代碼及相關資料地址:https://github.com/cmevolve/xieexiaodaima/tree/master/DevOps/Jenkins%E9%85%8D%E7%BD%AE
1.Ant 構建相關連接
https://blog.csdn.net/Al_assad/article/details/76285841
https://blog.csdn.net/mevicky/article/details/72828554
https://blog.csdn.net/xxdddail/article/details/21166161
https://blog.csdn.net/yang3wei/article/details/7393399
https://www.cnblogs.com/fnlingnzb-learner/p/6279189.html
https://www.yiibai.com/ant/apache-ant-javac-task.html
2.Svnkit 組件使用:
https://www.cnblogs.com/douJiangYouTiao888/p/6138660.html
3. Jenkins+Ant
https://blog.csdn.net/xiaxiaozhang/article/details/74155300
jekins svn任務配置:https://blog.csdn.net/russ44/article/details/52261781