1、pom.xml
<!--svn上传文件-->
<dependency>
<groupId>org.tmatesoft.svnkit</groupId>
<artifactId>svnkit</artifactId>
<version>1.10.1</version>
</dependency>
2、SVN连接以及校验 //1、SVN仓库的地址(配置文件,有designFileUrl、packageFileUrl、frontFileUrl) String urlType = svnUploadEntity.getUrlType(); String svnUrl = CommonUtil.getSysPara(urlType, "frontFileUrl") ; //如果是程序源码包上传,需要增加一层目录,表示服务名 if(urlType.equals("packageFileUrl")){ svnUrl= svnUrl+ "/"+ svnUploadEntity.getServerName(); } log.info("上传SVN文件路径:"+svnUrl );
//2.登录SVN的用户名(需要获取)
String username = svnUploadEntity.getUsername();
//3.登录SVN的密码
String passwd = getSvnPassword(username);
//4、本地仓库的路径(需要获取)
String workspace = svnUploadEntity.getWorkspace();
//5、要上传的文件信息(需要获取)
String upfile = svnUploadEntity.getUpfile();
//6、提交的日志信息(需要获取)
String commitMessage ="提交发包文件:"+ svnUploadEntity.getCommitMessage();
//是否覆盖SVN上的文件(默认为true)
Boolean isOverwrite = true;
if(StringUtils.isEs(passwd)){
log.info("没有登录权限svn密码为空");
map.put("code", "0");
map.put("message", "没有svn登录权限svn密码为空!");
return map;
}
//第二步:创建SVNUtil对象
SVNUitl svnDeal = new SVNUitl(svnUrl,username, passwd);
//是否有登录权限
boolean flag = svnDeal.login();
if(flag){
//7、判断SVN上是否存在该目录不存在创建目录
SVNURL svnurl = SVNURL.parseURIDecoded(svnUrl);
if(!svnDeal.isURLExist(svnurl)){
SVNURL [] svnUrls = {svnurl};
svnDeal.createDir(svnUrls);
}
//8、获取所有要上传的文件信息
String [] fileArray = upfile.split(",");
//9、遍历数组判断要上传的文件
for(int i=0;i<fileArray.length;i++){
//每个文件信息
String filePath = fileArray[i];
String filename = "";
//获取上传的文件名称
if (filePath.indexOf("/") != -1) {
filename = filePath.substring(filePath.lastIndexOf("/"));
} else {
filename = filePath;
}
//10、进行文件上传
svnDeal.upload(svnUrl, workspace, filePath, filename,isOverwrite,commitMessage);
}
map.put("code", "1");
map.put("message", "文件上传svn成功!");
}else{
log.info("没有登录权限");
map.put("code", "0");
map.put("message", "没有svn登录权限!");
}
2、工具类 public class SVNUitl { // svn版本库根目录 private String svnRoot; // svn账号 private String userName; // svn密码 private String password; // 版本库服务 private SVNRepository repository; // 身份认证 private ISVNAuthenticationManager authManager; // 客户端管理 private SVNClientManager clientManager;
public SVNUitl() {
}
public SVNUitl(String svnRoot, String userName, String password) {
this.svnRoot = svnRoot;
this.userName = userName;
this.password = password;
}
/**
* 不同的协议初始化版本库
*/
private static void setupLibrary() {
// 对于使用http://和https://
DAVRepositoryFactory.setup();
//对于使用svn:/ /和svn+xxx:/ /
SVNRepositoryFactoryImpl.setup();
//对于使用file://
FSRepositoryFactory.setup();
}
/**
* 登录验证
*
* [@return](https://my.oschina.net/u/556800)
*/
public boolean login() {
setupLibrary();
try {
//创建库连接
repository = SVNRepositoryFactory.create(SVNURL.parseURIEncoded(this.svnRoot));
//身份验证
authManager = SVNWCUtil
.createDefaultAuthenticationManager(this.userName, this.password.toCharArray());
//创建身份验证管理器
repository.setAuthenticationManager(authManager);
//创建客户端管理对象
DefaultSVNOptions options = SVNWCUtil.createDefaultOptions(true);
clientManager = SVNClientManager.newInstance(options, authManager);
return true;
} catch (SVNException svne) {
log.info("身份验证失败:", svne);
return false;
}
}
/**
* 关闭版本库
*/
public void closeRepo() {
if (null != this.repository) {
this.repository.closeSession();
log.info("关闭版本库");
}
}
/**
* 将目录或者文件添加到版本库下
*
* [@param](https://my.oschina.net/u/2303379) wcPath
* [@throws](https://my.oschina.net/throws) SVNException
*/
private void addEntry(File wcPath) throws SVNException {
try {
clientManager.getWCClient().doAdd(new File[]{wcPath}, true,
false, false, SVNDepth.INFINITY, false, false, true);
} catch (SVNException e) {
log.info("SVN添加文件到版本控制失败:", e);
}
}
/**
* 提交到SVN库中
*
* [@param](https://my.oschina.net/u/2303379) wcPath
* @param keepLocks
* @param commitMessage
* @return
* @throws SVNException
*/
private SVNCommitInfo commit(File wcPath, boolean keepLocks, String commitMessage) throws SVNException {
try {
return clientManager.getCommitClient().doCommit(
new File[]{wcPath}, keepLocks, commitMessage, null,
null, false, false, SVNDepth.INFINITY);
} catch (SVNException e) {
log.info("SVN提交失败:", e);
}
return null;
}
/**
* 判断当前的路径是否是一个工作空间
*
* @param path
* @return
* @throws SVNException
*/
private boolean isWorkingCopy(File path) throws SVNException {
if (!path.exists()) {
return false;
}
try {
if (null == SVNWCUtil.getWorkingCopyRoot(path, false)) {
return false;
}
} catch (SVNException e) {
log.info("当前的path是否是一个工作空间:", e);
}
return true;
}
/**
* 确定URL在SVN上是否存在
*
* @param url
* @return
* @throws SVNException
*/
public boolean isURLExist(SVNURL url) throws SVNException {
try {
SVNRepository svnRepository = SVNRepositoryFactory.create(url);
svnRepository.setAuthenticationManager(authManager);
SVNNodeKind nodeKind = svnRepository.checkPath("", -1);
return nodeKind == SVNNodeKind.NONE ? false : true;
} catch (SVNException e) {
log.info("确定URL在SVN上是否存在:", e);
}
return false;
}
/**
* 在当前目录下创建一个新的目录
*/
public boolean createDir(SVNURL[] url) throws SVNException {
try {
clientManager.getCommitClient().doMkDir(url, "创建新的目录");
} catch (SVNException e) {
log.info("在SVN上创建目录失败:", e);
}
return false;
}
/**
* 检查不在版本库中的文件添加到版本库中
*
* @param wc
* @throws SVNException
*/
private void checkVersiondDirectory(File wc) throws SVNException {
if (!SVNWCUtil.isVersionedDirectory(wc)) {
this.addEntry(wc);
}
if (wc.isDirectory()) {
for (File sub : wc.listFiles()) {
if (sub.isDirectory() && sub.getName().equals(".svn")) {
continue;
}
checkVersiondDirectory(sub);
}
}
}
/**
* 删除单个文件
*
* @param sPath
* @return
*/
private boolean deleteFile(String sPath) {
boolean flag = false;
File file = new File(sPath);
// 路径为文件且不为空则进行删除
if (file.isFile() && file.exists()) {
file.delete();
flag = true;
}
return flag;
}
/**
* 删除目录(文件夹)以及目录下的文件
*
* @param sPath
* @return
*/
private boolean deleteDirectory(String sPath) {
//如果sPath不以文件分隔符结尾,自动添加文件分隔符
if (!sPath.endsWith(File.separator)) {
sPath = sPath + File.separator;
}
File dirFile = new File(sPath);
//如果dir对应的文件不存在,或者不是一个目录,则退出
if (!dirFile.exists() || !dirFile.isDirectory()) {
return false;
}
boolean flag = true;
//删除文件夹下的所有文件(包括子目录)
File[] files = dirFile.listFiles();
for (int i = 0; i < files.length; i++) {
//删除子文件
if (files[i].isFile()) {
flag = deleteFile(files[i].getAbsolutePath());
if (!flag) break;
} //删除子目录
else {
flag = deleteDirectory(files[i].getAbsolutePath());
if (!flag) break;
}
}
if (!flag) return false;
//删除当前目录
if (dirFile.delete()) {
return true;
} else {
return false;
}
}
/**
* 循环删除.svn目录
*
* @param spath
*/
private void deletePointSVN(String spath) {
File wc = new File(spath);
for (File sub : wc.listFiles()) {
if (sub.isDirectory() && sub.getName().equals(".svn")) {
this.deleteDirectory(sub.getAbsolutePath());
continue;
}
if (sub.isDirectory()) {
deletePointSVN(sub.getAbsolutePath());
}
}
}
/**
* 上传文件到对应的SVN库中
*
* @param svnUrl
* @param workspace
* @param filepath
* @param filename
* @param isOverwrite
* @param commitMessage
* @throws SVNException
*/
public void upload(String svnUrl, String workspace, String filepath, String filename, Boolean isOverwrite, String commitMessage) throws SVNException {
try {
String svnfilePath = svnUrl + "/" + filename;
//开始前删除以前的.svn文件目录
deletePointSVN(workspace);
boolean flag = this.isURLExist(SVNURL.parseURIDecoded(svnfilePath));
if (flag) {
if (isOverwrite) {
this.uploadFile(svnUrl, workspace, filepath, filename, commitMessage);
}
} else {
this.uploadFile(svnUrl, workspace, filepath, filename, commitMessage);
}
//结束后删除当前的.svn文件目录
deletePointSVN(workspace);
log.info("上传成功!");
} catch (Exception e) {
log.info("程序异常", e);
}
}
/**
* 更新SVN工作区
*
* @param wcPath
* @param updateToRevision
* @param depth
* @return
* @throws SVNException
*/
private long update(File wcPath, SVNRevision updateToRevision, SVNDepth depth) throws SVNException {
SVNUpdateClient updateClient = clientManager.getUpdateClient();
updateClient.setIgnoreExternals(false);
try {
return updateClient.doUpdate(wcPath, updateToRevision, depth, false, false);
} catch (SVNException e) {
log.info("更新SVN工作区失败:", e);
}
return -1;
}
/**
* SVN仓库文件检出
*
* @param url
* @param revision
* @param destPath
* @param depth
* @return
* @throws SVNException
*/
private long checkout(SVNURL url, SVNRevision revision, File destPath, SVNDepth depth) throws SVNException {
SVNUpdateClient updateClient = clientManager.getUpdateClient();
updateClient.setIgnoreExternals(false);
try {
return updateClient.doCheckout(url, destPath, revision, revision, depth, false);
} catch (SVNException e) {
log.info("检出SVN仓库失败:", e);
}
return -1;
}
private long checkouts(SVNURL url, SVNRevision revision, File destPath, SVNDepth depth) throws SVNException {
SVNUpdateClient updateClient = clientManager.getUpdateClient();
updateClient.setIgnoreExternals(false);
try {
// return updateClient.doCheckout(url, destPath, revision, revision,depth, false); return updateClient.doExport(url, destPath, revision, revision, "", true, false); } catch (SVNException e) { log.info("检出SVN仓库失败:", e); } return -1; }
public void checkWorkCopy(String svnUrl, String workspace, String filepath, String filename) throws SVNException {
SVNURL repositoryURL = null;
try {
repositoryURL = SVNURL.parseURIEncoded(svnUrl);
} catch (SVNException e) {
log.info("解析svnUrl失败", e);
}
String fPath = "";
if (filepath.indexOf("/") != -1) {
fPath = filepath.substring(0, filepath.lastIndexOf("/"));
}
File wc = new File(workspace + "/" + fPath);
File wc_project = new File(workspace + "/" + fPath);
SVNURL projectURL = null;
try {
projectURL = repositoryURL.appendPath(filename, false);
} catch (SVNException e) {
log.info("解析svnUrl文件失败:", e);
}
if (!this.isWorkingCopy(wc)) {
if (!this.isURLExist(projectURL)) {
this.checkout(repositoryURL, SVNRevision.HEAD, wc, SVNDepth.EMPTY);
} else {
this.checkout(projectURL, SVNRevision.HEAD, wc_project, SVNDepth.INFINITY);
}
} else {
this.update(wc, SVNRevision.HEAD, SVNDepth.INFINITY);
}
}
public void checkWorkCopys(String svnUrl, String workspace, String filepath, String filename) throws SVNException {
SVNURL repositoryURL = null;
try {
repositoryURL = SVNURL.parseURIEncoded(svnUrl);
} catch (SVNException e) {
log.info("解析svnUrl失败", e);
}
String fPath = "";
if (filepath.indexOf("/") != -1) {
fPath = filepath.substring(0, filepath.lastIndexOf("/"));
}
// workspace="E:\images"; log.info("解析到的workspace地址为:", workspace); File wc = new File(workspace); File wc_project = new File(workspace); log.info("文件地址是:", workspace); if (StringUtils.isnEs(fPath)) { wc = new File(workspace + "/" + fPath); wc_project = new File(workspace + "/" + fPath); } if (!wc.exists()) { //建目录 wc.mkdirs(); } log.info("解析到的地址为:", wc.getPath()); SVNURL projectURL = null; try { projectURL = repositoryURL.appendPath(filename, false); } catch (SVNException e) { log.info("解析svnUrl文件失败:", e); }
if (!this.isWorkingCopy(wc)) {
if (!this.isURLExist(projectURL)) {
this.checkouts(repositoryURL, SVNRevision.HEAD, wc, SVNDepth.EMPTY);
} else {
this.checkouts(projectURL, SVNRevision.HEAD, wc_project, SVNDepth.INFINITY);
}
} else {
this.update(wc, SVNRevision.HEAD, SVNDepth.INFINITY);
}
}
/**
* 上传文件
*
* @param svnUrl
* @param workspace
* @param filepath
* @param filename
* @param commitMessage
* @throws SVNException
*/
private void uploadFile(String svnUrl, String workspace, String filepath, String filename, String commitMessage) throws SVNException {
this.checkWorkCopy(svnUrl, workspace, filepath, filename);
File file = new File(workspace + "/" + filepath);
this.checkVersiondDirectory(file);
this.commit(file, false, commitMessage);
}
}