diff --git a/org.eclipse.jgit.test/tst/org/eclipse/jgit/gitrepo/RepoCommandTest.java b/org.eclipse.jgit.test/tst/org/eclipse/jgit/gitrepo/RepoCommandTest.java index c170ac1b3..1f6861b35 100644 --- a/org.eclipse.jgit.test/tst/org/eclipse/jgit/gitrepo/RepoCommandTest.java +++ b/org.eclipse.jgit.test/tst/org/eclipse/jgit/gitrepo/RepoCommandTest.java @@ -577,13 +577,69 @@ public void testRepoManifestCopyFile() throws Exception { // The original file should exist File hello = new File(localDb.getWorkTree(), "foo/hello.txt"); assertTrue("The original file should exist", hello.exists()); + assertFalse("The original file should not be executable", + hello.canExecute()); assertContents(hello.toPath(), "master world"); // The dest file should also exist hello = new File(localDb.getWorkTree(), "Hello"); assertTrue("The destination file should exist", hello.exists()); + assertFalse("The destination file should not be executable", + hello.canExecute()); assertContents(hello.toPath(), "master world"); } + @Test + public void testRepoManifestCopyFile_executable() throws Exception { + try (Git git = new Git(defaultDb)) { + git.checkout().setName("master").call(); + File f = JGitTestUtil.writeTrashFile(defaultDb, "hello.sh", + "content of the executable file"); + f.setExecutable(true); + git.add().addFilepattern("hello.sh").call(); + git.commit().setMessage("Add binary file").call(); + } + + Repository localDb = createWorkRepository(); + StringBuilder xmlContent = new StringBuilder(); + xmlContent.append("\n") + .append("") + .append("") + .append("") + .append("") + .append("") + .append("").append(""); + JGitTestUtil.writeTrashFile(localDb, "manifest.xml", + xmlContent.toString()); + RepoCommand command = new RepoCommand(localDb); + command.setPath( + localDb.getWorkTree().getAbsolutePath() + "/manifest.xml") + .setURI(rootUri).call(); + + // The original file should exist and be an executable + File hello = new File(localDb.getWorkTree(), "foo/hello.sh"); + assertTrue("The original file should exist", hello.exists()); + assertTrue("The original file must be executable", hello.canExecute()); + try (BufferedReader reader = Files.newBufferedReader(hello.toPath(), + UTF_8)) { + String content = reader.readLine(); + assertEquals("The original file should have expected content", + "content of the executable file", content); + } + + // The destination file should also exist and be an executable + hello = new File(localDb.getWorkTree(), "copy-hello.sh"); + assertTrue("The destination file should exist", hello.exists()); + assertTrue("The destination file must be executable", + hello.canExecute()); + try (BufferedReader reader = Files.newBufferedReader(hello.toPath(), + UTF_8)) { + String content = reader.readLine(); + assertEquals("The destination file should have expected content", + "content of the executable file", content); + } + } + @Test public void testBareRepo() throws Exception { Repository remoteDb = createBareRepository(); @@ -767,6 +823,68 @@ public void testCopyFileBare() throws Exception { } } + @Test + public void testCopyFileBare_executable() throws Exception { + try (Git git = new Git(defaultDb)) { + git.checkout().setName(BRANCH).call(); + File f = JGitTestUtil.writeTrashFile(defaultDb, "hello.sh", + "content of the executable file"); + f.setExecutable(true); + git.add().addFilepattern("hello.sh").call(); + git.commit().setMessage("Add binary file").call(); + } + + Repository remoteDb = createBareRepository(); + Repository tempDb = createWorkRepository(); + + StringBuilder xmlContent = new StringBuilder(); + xmlContent.append("\n") + .append("") + .append("") + .append("") + .append("") + .append("") + .append("") + .append("") + .append("").append(""); + JGitTestUtil.writeTrashFile(tempDb, "manifest.xml", + xmlContent.toString()); + RepoCommand command = new RepoCommand(remoteDb); + command.setPath( + tempDb.getWorkTree().getAbsolutePath() + "/manifest.xml") + .setURI(rootUri).call(); + // Clone it + File directory = createTempDirectory("testCopyFileBare"); + try (Repository localDb = Git.cloneRepository().setDirectory(directory) + .setURI(remoteDb.getDirectory().toURI().toString()).call() + .getRepository()) { + // The Hello file should exist + File hello = new File(localDb.getWorkTree(), "Hello"); + assertTrue("The Hello file should exist", hello.exists()); + // The foo/Hello file should be skipped. + File foohello = new File(localDb.getWorkTree(), "foo/Hello"); + assertFalse("The foo/Hello file should be skipped", + foohello.exists()); + // The content of Hello file should be expected + try (BufferedReader reader = Files.newBufferedReader(hello.toPath(), + UTF_8)) { + String content = reader.readLine(); + assertEquals("The Hello file should have expected content", + "branch world", content); + } + + // The executable file must be there and preserve the executable bit + File helloSh = new File(localDb.getWorkTree(), "copy-hello.sh"); + assertTrue("Destination file should exist", helloSh.exists()); + assertContents(helloSh.toPath(), "content of the executable file"); + assertTrue("Destination file should be executable", + helloSh.canExecute()); + + } + } + @Test public void testReplaceManifestBare() throws Exception { Repository remoteDb = createBareRepository(); diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoCommand.java b/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoCommand.java index e01101095..e9d86dfa8 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoCommand.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoCommand.java @@ -663,12 +663,13 @@ public RevCommit call() throws GitAPIException { builder.add(dcEntry); for (CopyFile copyfile : proj.getCopyFiles()) { - byte[] src = callback.readFile( + RemoteFile rf = callback.readFileWithMode( url, proj.getRevision(), copyfile.src); - objectId = inserter.insert(Constants.OBJ_BLOB, src); + objectId = inserter.insert(Constants.OBJ_BLOB, + rf.getContents()); dcEntry = new DirCacheEntry(copyfile.dest); dcEntry.setObjectId(objectId); - dcEntry.setFileMode(FileMode.REGULAR_FILE); + dcEntry.setFileMode(rf.getFileMode()); builder.add(dcEntry); } for (LinkFile linkfile : proj.getLinkFiles()) { diff --git a/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoProject.java b/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoProject.java index 7ba83c7cb..d79dfa8b2 100644 --- a/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoProject.java +++ b/org.eclipse.jgit/src/org/eclipse/jgit/gitrepo/RepoProject.java @@ -136,6 +136,7 @@ public void copy() throws IOException { FileChannel channel = input.getChannel(); output.getChannel().transferFrom(channel, 0, channel.size()); } + destFile.setExecutable(srcFile.canExecute()); } }