Popular Posts
javax.net.ssl.SSLHandshakeException: Connection closed by peer in Android 5.0 Lollipop Recently, there is a error occurs when access website via ssl connection like below although it worked fine several days ago. // Enable SSL... Enable SSL connection for Jsoup import org.jsoup.Connection; import org.jsoup.Jsoup; import javax.net.ssl.*; import java.io.IOException; import java.security.KeyManagement... Copy/Delete/Permission directory using System; using System.IO; using System.Security.AccessControl; namespace Bruce.Lib {     public class DirHelper     {         /// <...
Stats
Difference source code programmably from svn
import org.tmatesoft.svn.core.SVNException;
import org.tmatesoft.svn.core.SVNNodeKind;
import org.tmatesoft.svn.core.SVNProperties;
import org.tmatesoft.svn.core.SVNURL;
import org.tmatesoft.svn.core.auth.ISVNAuthenticationManager;
import org.tmatesoft.svn.core.internal.io.dav.DAVRepositoryFactory;
import org.tmatesoft.svn.core.internal.io.fs.FSRepositoryFactory;
import org.tmatesoft.svn.core.internal.io.svn.SVNRepositoryFactoryImpl;
import org.tmatesoft.svn.core.io.SVNRepository;
import org.tmatesoft.svn.core.io.SVNRepositoryFactory;
import org.tmatesoft.svn.core.wc.*;
import org.tmatesoft.svn.core.wc2.SvnOperationFactory;
import java.io.ByteArrayOutputStream;
import java.io.File;
/**
* Diff & export
* Created by nanashi07 on 2016/6/29.
*/
public class DiffWithSvnKit {
public static void main(String[] args) throws SVNException {
final String fromUrl = "https://svn.your_server.com/path_to_compare_from";
final long fromRevision = 1000;
final String targetUrl = "https://svn.your_server.com/path_to_compare_to";
final long targetRevision = 2000;
final String outputFolder = "/folder_to_export";
final String account = "account";
final String password = "password";
DAVRepositoryFactory.setup();
SVNRepositoryFactoryImpl.setup();
FSRepositoryFactory.setup();
SVNURL fromSvnUrl = SVNURL.parseURIEncoded(fromUrl);
SVNRevision fromSvnRevision = SVNRevision.create(fromRevision);
SVNURL targetSvnUrl = SVNURL.parseURIEncoded(targetUrl);
SVNRevision targetSvnRevision = SVNRevision.create(targetRevision);
final File baseFolder = new File(outputFolder);
final SvnOperationFactory svnOperationFactory = new SvnOperationFactory();
final SVNRepository repository = SVNRepositoryFactory.create(targetSvnUrl);
final StringBuilder builder = new StringBuilder();
ISVNAuthenticationManager authManager = SVNWCUtil.createDefaultAuthenticationManager(account, password.toCharArray());
svnOperationFactory.setAuthenticationManager(authManager);
repository.setAuthenticationManager(authManager);
SVNDiffClient diffClient = new SVNDiffClient(authManager, null);
try {
diffClient.doDiffStatus(fromSvnUrl, fromSvnRevision, targetSvnUrl, targetSvnRevision, org.tmatesoft.svn.core.SVNDepth.UNKNOWN, true, new ISVNDiffStatusHandler() {
@Override
public void handleDiffStatus(SVNDiffStatus diffStatus) throws SVNException {
builder.append(String.format("%s, %s%n", diffStatus.getModificationType(), diffStatus.getPath()));
if (diffStatus.getKind() == SVNNodeKind.FILE) {
SVNProperties p = new SVNProperties();
ByteArrayOutputStream output = new ByteArrayOutputStream();
repository.getFile(diffStatus.getPath(), targetRevision, p, output);
byte[] data = output.toByteArray();
File copy = new File(baseFolder, diffStatus.getPath());
if (!copy.getParentFile().exists()) copy.getParentFile().mkdirs();
Files.write(copy, data);
}
}
});
Files.write(new File(baseFolder, "diff.txt"), builder);
} catch (Throwable ex) {
ex.printStackTrace();
}
}
}
Invoke Gson#toJson() on anonymous class

Create a anonymous object and try to serialize instance via gson. The code is below

public class SerializeJson {
static class ResultMessage {
int code;
String content;
public ResultMessage() {
}
public ResultMessage(int code, String content) {
this.code = code;
this.content = content;
}
}
public static void main(String[] args) {
ResultMessage m1 = new ResultMessage(111, "hello");
ResultMessage m2 = new ResultMessage() {{
code = 2323;
content = "hello";
}};
System.out.printf("m1.code : %s%n", m1.code);
System.out.printf("m1.content : %s%n", m1.content);
System.out.printf("m2.code : %s%n", m2.code);
System.out.printf("m2.content : %s%n", m2.content);
System.out.println(m1.getClass());
System.out.println(m2.getClass());
System.out.println("m1: " + new Gson().toJson(m1));
System.out.println("m2: " + new Gson().toJson(m2));
}
}

Result of execution. null result when serialize a anonymous instance

m1.code : 111
m1.content : hello
m2.code : 2323
m2.content : hello
class com.prhythm.test.generic.http.SerializeJson$ResultMessage
class com.prhythm.test.generic.http.SerializeJson$1
m1: {"code":111,"content":"hello"}
m2: null
view raw output hosted with ❤ by GitHub
Commit file via SVNkit

SVNKit version:

<dependency>
<groupId>org.tmatesoft.svnkit</groupId>
<artifactId>svnkit</artifactId>
<version>1.8.12</version>
</dependency>
view raw pom.xml hosted with ❤ by GitHub

SvnCommitter.java

package com.prhythm.batch.source.control;
import org.tmatesoft.svn.core.*;
import org.tmatesoft.svn.core.auth.ISVNAuthenticationManager;
import org.tmatesoft.svn.core.internal.io.dav.DAVRepositoryFactory;
import org.tmatesoft.svn.core.internal.io.fs.FSRepositoryFactory;
import org.tmatesoft.svn.core.internal.io.svn.SVNRepositoryFactoryImpl;
import org.tmatesoft.svn.core.io.ISVNEditor;
import org.tmatesoft.svn.core.io.SVNRepository;
import org.tmatesoft.svn.core.io.SVNRepositoryFactory;
import org.tmatesoft.svn.core.io.diff.SVNDeltaGenerator;
import org.tmatesoft.svn.core.wc.SVNWCUtil;
import java.io.*;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
/**
* Created by nanashi07 on 2016/6/22.
*/
@SuppressWarnings("Duplicates")
public class SvnCommitter implements ICommitable {
public static void main(String[] args) throws Throwable {
String url1 = "https://svn.your_server.com";
String userName = "account";
String userPassword = "password";
DAVRepositoryFactory.setup();
SVNRepositoryFactoryImpl.setup();
FSRepositoryFactory.setup();
new SvnCommitter().commit(
url1,
userName,
userPassword,
"Commit updates",
"trunk/other",
new File("xom/src")
);
}
/**
* 最新版本
*/
private int revision = -1;
@Override
public void commit(String repositoryUrl, String account, String password, String commitMessage, String pathToCommit, File... fileOrDirectory) throws Throwable {
// 解析網址
SVNURL url = SVNURL.parseURIEncoded(repositoryUrl);
// 取得資源庫
SVNRepository repository = SVNRepositoryFactory.create(url);
// 身份驗證
ISVNAuthenticationManager authManager = SVNWCUtil.createDefaultAuthenticationManager(account, password.toCharArray());
repository.setAuthenticationManager(authManager);
// 檢查路徑是否存在
if (pathToCommit == null) pathToCommit = "";
SVNNodeKind nodeKind = repository.checkPath(pathToCommit, revision);
if (nodeKind == SVNNodeKind.NONE) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.UNKNOWN, "No entry at URL ''{0}''", url);
throw new SVNException(err);
} else if (nodeKind == SVNNodeKind.FILE) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.UNKNOWN, "Entry at URL ''{0}'' is a file while directory was expected", url);
throw new SVNException(err);
}
Map<String, SVNNodeKind> kinds = new HashMap<String, SVNNodeKind>();
for (File file : fileOrDirectory) {
kinds.putAll(collect(repository, pathToCommit, file));
}
ISVNEditor editor = repository.getCommitEditor(commitMessage, null);
try {
editor.openRoot(revision);
SVNDeltaGenerator svnDeltaGenerator = new SVNDeltaGenerator();
for (String segment : (pathToCommit.charAt(0) == '/' ? pathToCommit.substring(1) : pathToCommit).split("[/]")) {
System.out.printf("開啟資料夾 %s%n", segment);
editor.openDir(segment, revision);
}
boolean result = false;
for (File file : fileOrDirectory) {
result = sendDelta(kinds, editor, svnDeltaGenerator, pathToCommit, file);
}
for (String segment : (pathToCommit.charAt(0) == '/' ? pathToCommit.substring(1) : pathToCommit).split("[/]")) {
System.out.printf("關閉資料夾 %s%n", segment);
editor.closeDir();
}
if (!result) {
editor.abortEdit();
System.out.println("無變更");
} else {
SVNCommitInfo svnCommitInfo = editor.closeEdit();
System.out.println(svnCommitInfo);
}
} catch (Throwable e) {
editor.abortEdit();
e.printStackTrace();
}
}
/**
* 收集版本資訊
*
* @param repository 版本庫
* @param path 路徑
* @param fileOrDir 檔案
* @return
* @throws SVNException
*/
private Map<String, SVNNodeKind> collect(final SVNRepository repository, String path, File fileOrDir) throws SVNException, FileNotFoundException {
Map<String, SVNNodeKind> values = new HashMap<String, SVNNodeKind>();
final String targetPath = path.endsWith("/") ? path + fileOrDir.getName() : path + "/" + fileOrDir.getName();
final SVNNodeKind kind = repository.checkPath(targetPath, revision);
System.out.println(String.format("%s: %s", targetPath, kind));
// 取得相關資料
boolean ignore = false;
if (kind == SVNNodeKind.FILE) {
SVNProperties p = new SVNProperties();
ByteArrayOutputStream output = new ByteArrayOutputStream();
repository.getFile(targetPath, revision, p, output);
byte[] data = output.toByteArray();
// 檔案未變更
ignore = Arrays.equals(data, toByteArray(new FileInputStream(fileOrDir)));
}
// 比對版本,檔案相同時不處理
if (!ignore) values.put(targetPath, kind);
if (fileOrDir.isDirectory()) {
File[] files = fileOrDir.listFiles();
if (files != null) {
for (File file : files) {
values.putAll(collect(repository, targetPath, file));
}
}
}
return values;
}
/**
* 處理提交的內容。
*
* @param kindMap 版本資訊
* @param editor
* @param deltaGenerator
* @param path 處理路徑
* @param fileOrDir 檔案
* @return
* @throws SVNException
* @throws FileNotFoundException
*/
private boolean sendDelta(Map<String, SVNNodeKind> kindMap, ISVNEditor editor, SVNDeltaGenerator deltaGenerator, String path, File fileOrDir) throws SVNException, FileNotFoundException {
boolean result = false;
String targetPath = path.endsWith("/") ? path + fileOrDir.getName() : path + "/" + fileOrDir.getName();
SVNNodeKind info = kindMap.get(targetPath);
if (info == SVNNodeKind.NONE) {
// 新增
if (fileOrDir.isDirectory()) {
System.out.printf("加入資料夾 %s%n", fileOrDir.getName());
editor.addDir(fileOrDir.getName(), null, revision);
File[] subFiles = fileOrDir.listFiles();
if (subFiles != null) {
for (File subFile : subFiles) {
result = result || sendDelta(kindMap, editor, deltaGenerator, targetPath, subFile);
}
}
editor.closeDir();
result = true;
} else if (fileOrDir.isFile()) {
System.out.printf("加入檔案 %s%n", fileOrDir.getName());
editor.addFile(fileOrDir.getName(), null, revision);
editor.applyTextDelta(fileOrDir.getName(), null);
String checksum = deltaGenerator.sendDelta(fileOrDir.getName(), new FileInputStream(fileOrDir), editor, true);
editor.closeFile(fileOrDir.getName(), checksum);
result = true;
}
} else if (info == SVNNodeKind.DIR || info == SVNNodeKind.FILE) {
// 修改
if (fileOrDir.isDirectory()) {
if (info != SVNNodeKind.DIR)
throw new RuntimeException(String.format("無法提交資料夾 %s 至檔案格式", fileOrDir));
System.out.printf("開啟資料夾 %s%n", fileOrDir);
editor.openDir(fileOrDir.getName(), revision);
File[] subFiles = fileOrDir.listFiles();
if (subFiles != null) {
for (File subFile : subFiles) {
result = result || sendDelta(kindMap, editor, deltaGenerator, targetPath, subFile);
}
}
editor.closeDir();
} else if (fileOrDir.isFile()) {
if (info != SVNNodeKind.FILE)
throw new RuntimeException(String.format("無法提交檔案 %s 至資料夾格式", fileOrDir));
System.out.printf("變更檔案 %s%n", fileOrDir.getName());
editor.openFile(fileOrDir.getName(), revision);
editor.applyTextDelta(fileOrDir.getName(), null);
String checksum = deltaGenerator.sendDelta(fileOrDir.getName(), new FileInputStream(fileOrDir), editor, true);
editor.closeFile(fileOrDir.getName(), checksum);
result = true;
}
}
return result;
}
private byte[] toByteArray(InputStream input) {
if (input == null) throw new IllegalArgumentException("Input can't be null");
ByteArrayOutputStream output = null;
try {
output = new ByteArrayOutputStream();
byte[] buffer = new byte[128];
int len;
while ((len = input.read(buffer)) > 0) {
output.write(buffer, 0, len);
}
return output.toByteArray();
} catch (Throwable e) {
throw new RuntimeException(e.getMessage(), e);
} finally {
if (output != null) try {
output.close();
} catch (IOException e) {
e.printStackTrace();
}
try {
input.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
List changed files between commits
List all changed files between commits of git.
git diff --name-only SHA1 SHA2
or
git diff --name-only HEAD~10 HEAD~5