天天看点

关于maven插件的一点事(三)实践

  • 关联阅读:
    • 关于maven插件的一点事(一)生命周期
    • 关于maven插件的一点事(二)插件
    • 关于maven插件的一点事(三)实践

需求

需求:一个web项目,需要对其中某些jar包以及web代码进行加密,为了节省资源以及方便起见,不影响本地开发,只对用于测试和部署的war进行操作。

已知:加密程序是jar程序(但是还调用了 dll和so),只能加密jar/war包里的代码,加密时要设置jar/war原始依赖(包括servlet.jar),原操作是手工解war里的jar出来单个加密,再放回war包中。作为一个程序员,肯定是不能接受的,于是帮忙将其加入打包环节中。

思路

一种思路是对需要加密的jar先加密好,即war打包时下载下来的jar已经是处理好的了,这样子就很简单,只需要在package出jar之后进行一次处理,但是这样子,开发环节可能会有问题,不过也好处理,只需要在war包时处理版本的问题即可,即对引用的jar在打war时将依赖引用为加密的jar包。

一种思路是在打war包时,才对jar包进行处理。最终采用的是这个方案,虽然可能会影响自动打包的速度,但是主要是考虑到如下:

一是,对某些需要加密的jar我没有打包权限,需要让另外的人去另外打包,并且每次打包发布到私服的时候要另外发布加密的包。

二是,有一部分公共jar,每个war项目的秘钥并不同,如果在jar包和war用的秘钥不同,可能有问题。打war包时才对jar处理,这样的话可以保证这两者时一致的。

操作

  • 首先要让打包环节可以调用加密程序并且可以动态传入一些参数进行加密,这个环节要走通,否则后面就无法操作了。
    • Maven不知道能否调用系统的

      java -jar

      ,但是我想到我之前使用ant是可以的,而ant可以直接用Maven调用,于是打算使用ant。
    • 测试发现,加密程序可以使用加密参数文件和参数,于是把原先加密参数文件中一些可能需要动态变换参数抽出来。如,依赖路径、输入和输出。其他和加密有关的则作为一个

      common-encrypt.txt

      来传入。
  • 依赖处理,由于加密程序需要指明依赖。于是第一次想到,用固定的lib,但是可能会有缺失;后面觉得还是用pom定义的依赖。找了下,插件

    maven-dependency-plugin

    copy-dependencies

    能满足目标。于是使用。
  • 之后想到,要对某些dependency进行加密, 这些加密之后要替换掉原先的dependency,而加密程序需要的是原版的dependency以及不需要到打包里的servlet.api,于是索性用两次copy-dependencies产生两个依赖文件夹。一个是未处理的,一个是之后需要弄进打包里的。
  • 但是原先打war包在package是自动的,好像不能控制依赖,于是找了一下,能不能自己控制哪些需要打到war包里面,找到

    maven-assembly-plugin

    , 该插件可以自己定制打包,于是使用。之后我再用ant对定制后的产生的war包(部分依赖已加密)进行一次加密,即完成了目标。
  • 组合并调试上面提到的步骤,即实现了自动化加密。以后需要增加加密的依赖包,只需要在 encrypt.xml把jar包名字加入即可。当然,增加了这些步骤之后,自动化打包的速度理所当然有所下降。
  • 相关的文件(除加密)在下面

执行加密程序的ant任务

<?xml version="1.0" ?>
<project name="encrypt" default="encryptJar">
    <property name="jarPath" value="/usr/share/AxProtector/AxProtector.jar" />
    <property name="inputFileDir" value="${basedir}/scripts" />
    <property name="dependencyDir" value="${basedir}/target/dependencylibs" />
    <property name="targetLibDir" value="${basedir}/target/libs" />
	<property name="jar1Name" value="xxxxx-core" />
	<target name="encryptWar">
		<echo message=".........encrpyt encryptWar......." />
		<java fork="true" jar="${jarPath}">
			<arg value="-o:${basedir}/target/xxxxx-encrypted.war"></arg>
			<arg value="-jcp:${dependencyDir}" ></arg>
			<arg value="@${inputFileDir}/common-encrypt-info.xml"></arg>
			<arg value="${basedir}/target/xxxxx-assembly.war"></arg>
        </java>
	</target>
    <target name="encryptJar">
		<echo message=".........encrpyt ${jar1Name}......." />
        <java fork="true" jar="${jarPath}">
			<arg value="-o:${targetLibDir}/${jar1Name}-encrypted.jar"></arg>
			<arg value="-jcp:${dependencyDir}" ></arg>
			<arg value="@${inputFileDir}/common-encrypt-info.xml"></arg>
			<arg value="${dependencyDir}/${jar1Name}.jar"></arg>
        </java>
        <delete>
        	<file file="${targetLibDir}/${jar1Name}.jar"></file>
        </delete>
     </target>
</project>   
           

pom文件

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>
	<artifactId>xxxxx</artifactId>
	<packaging>war</packaging>
	<parent>
		<groupId>com.xxx.xxxxx</groupId>
		<artifactId>xxxxx-root</artifactId>
		<version>3.0-SNAPSHOT</version>
		<relativePath>../../pom.xml</relativePath>
	</parent>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<uat.time>${maven.build.timestamp}</uat.time>
	</properties>

	<dependencies>
		......省略
	</dependencies>

	<build>

		<finalName>${artifactId}</finalName>
		<resources>
			<resource>
				<directory>${project.basedir}/src/main/resources</directory>
				<filtering>true</filtering>
			</resource>
		</resources>
		<plugins>
			<plugin>
				<artifactId>maven-compiler-plugin</artifactId>
				<version>3.3</version>
				<configuration>
					<source>1.8</source>
					<target>1.8</target>
					<encoding>UTF-8</encoding>
				</configuration>
			</plugin>
			        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>copy-dependencies</id>
                    <phase>prepare-package</phase>
                    <goals>
                        <goal>copy-dependencies</goal>
                    </goals>
                    <configuration>
                        <outputDirectory>
                            ${project.build.directory}/libs
                        </outputDirectory>
                        <excludeArtifactIds>junit*,servlet*</excludeArtifactIds>
                        <excludeScope>provided</excludeScope>
                        <!-- 表示复制的jar文件去掉版本信息 -->  
                		<stripVersion>true</stripVersion> 
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-dependency-plugin</artifactId>
            <executions>
                <execution>
                    <id>copy-dependencies2</id>
                    <phase>prepare-package</phase>
                    <goals>
                        <goal>copy-dependencies</goal>
                    </goals>
                    <configuration>
                        <outputDirectory>
                            ${project.build.directory}/dependencylibs
                        </outputDirectory>
                        <!-- 表示复制的jar文件去掉版本信息 -->  
                		<stripVersion>true</stripVersion> 
                    </configuration>
                </execution>
            </executions>
        </plugin>
        <!-- 处理jar包和war包加密 -->
        <plugin>
          <artifactId>maven-antrun-plugin</artifactId>
          <version>1.8</version>
          <executions>
            <execution>
            	<id>ant-encryptJar</id>
              <phase>prepare-package</phase>
              <configuration>
                <target >
          				<ant antfile="encrypt.xml" target="encryptJar" inheritAll="false">
          				</ant>
                </target>
              </configuration>
              <goals>
                <goal>run</goal>
              </goals>
            </execution>
            <execution>
            	<id>ant-encryptWar</id>
              <phase>install</phase>
              <configuration>
                <target >
          				<ant antfile="encrypt.xml" target="encryptWar" inheritAll="false">
          				</ant>
                </target>
              </configuration>
              <goals>
                <goal>run</goal>
              </goals>
            </execution>
          </executions>
      </plugin>
        
      		<plugin>  
    			<artifactId>maven-assembly-plugin</artifactId>  
    			<configuration>  
       				<descriptor>scripts/assembly.xml</descriptor>  
   				</configuration>  
    			<executions>  
        			<execution>  
            			<id>make-assembly</id>  
            			<phase>package</phase>  
            			<goals>  
                			<goal>single</goal>  
            			</goals>  
       			 	</execution>  
				  </executions>  
			</plugin>
		</plugins>
	</build>
</project>
           

定义组装的文件

<assembly>  
  <id>assembly</id>  
  <formats>  
    <format>war</format>  
  </formats>  
  <includeBaseDirectory>false</includeBaseDirectory>  
  <dependencySets>  
  <!-- 将项目依赖的JAR包输出到 WEB-INF/lib -->  
   <dependencySet>  
   		<excludes>
   			<exclude>*</exclude>
   		</excludes>
      <outputDirectory>WEB-INF/lib</outputDirectory>  
      <useProjectArtifact>true</useProjectArtifact>  
    </dependencySet>      
  </dependencySets>  
  <fileSets>  
    <fileSet>  
      <directory>${project.build.outputDirectory}</directory>  
      <outputDirectory>WEB-INF/classes</outputDirectory>  
    </fileSet>
    <fileSet>  
      <directory>${project.basedir}/target/libs</directory>  
      <outputDirectory>WEB-INF/lib</outputDirectory>  
    </fileSet>    
    <!-- 将 webapp 下的文件输出到 WAR 包 -->  
    <fileSet>  
      <directory>${project.basedir}/src/main/webapp</directory>  
      <outputDirectory>/</outputDirectory>  
    </fileSet>
  </fileSets>    
</assembly>