1
2
3
4
5
6
7
8
9
10 package org.eclipse.jgit.archive;
11
12 import static java.nio.charset.StandardCharsets.UTF_8;
13
14 import java.io.IOException;
15 import java.io.OutputStream;
16 import java.text.MessageFormat;
17 import java.util.Arrays;
18 import java.util.Collections;
19 import java.util.List;
20 import java.util.Map;
21
22 import org.apache.commons.compress.archivers.ArchiveOutputStream;
23 import org.apache.commons.compress.archivers.tar.TarArchiveEntry;
24 import org.apache.commons.compress.archivers.tar.TarArchiveOutputStream;
25 import org.apache.commons.compress.archivers.tar.TarConstants;
26 import org.eclipse.jgit.api.ArchiveCommand;
27 import org.eclipse.jgit.archive.internal.ArchiveText;
28 import org.eclipse.jgit.lib.FileMode;
29 import org.eclipse.jgit.lib.ObjectId;
30 import org.eclipse.jgit.lib.ObjectLoader;
31 import org.eclipse.jgit.revwalk.RevCommit;
32
33
34
35
36
37 public final class TarFormat extends BaseFormat implements
38 ArchiveCommand.Format<ArchiveOutputStream> {
39 private static final List<String> SUFFIXES = Collections
40 .unmodifiableList(Arrays.asList(".tar"));
41
42
43 @Override
44 public ArchiveOutputStream createArchiveOutputStream(OutputStream s)
45 throws IOException {
46 return createArchiveOutputStream(s,
47 Collections.<String, Object> emptyMap());
48 }
49
50
51 @Override
52 public ArchiveOutputStream createArchiveOutputStream(OutputStream s,
53 Map<String, Object> o) throws IOException {
54 TarArchiveOutputStream out = new TarArchiveOutputStream(s,
55 UTF_8.name());
56 out.setLongFileMode(TarArchiveOutputStream.LONGFILE_POSIX);
57 out.setBigNumberMode(TarArchiveOutputStream.BIGNUMBER_POSIX);
58 return applyFormatOptions(out, o);
59 }
60
61
62 @Override
63 public void putEntry(ArchiveOutputStream out,
64 ObjectId tree, String path, FileMode mode, ObjectLoader loader)
65 throws IOException {
66 if (mode == FileMode.SYMLINK) {
67 final TarArchiveEntry entry = new TarArchiveEntry(
68 path, TarConstants.LF_SYMLINK);
69 entry.setLinkName(new String(loader.getCachedBytes(100), UTF_8));
70 out.putArchiveEntry(entry);
71 out.closeArchiveEntry();
72 return;
73 }
74
75
76
77 if (path.endsWith("/") && mode != FileMode.TREE)
78 throw new IllegalArgumentException(MessageFormat.format(
79 ArchiveText.get().pathDoesNotMatchMode, path, mode));
80 if (!path.endsWith("/") && mode == FileMode.TREE)
81 path = path + "/";
82
83 final TarArchiveEntry entry = new TarArchiveEntry(path);
84
85 if (tree instanceof RevCommit) {
86 long t = ((RevCommit) tree).getCommitTime() * 1000L;
87 entry.setModTime(t);
88 }
89
90 if (mode == FileMode.TREE) {
91 out.putArchiveEntry(entry);
92 out.closeArchiveEntry();
93 return;
94 }
95
96 if (mode == FileMode.REGULAR_FILE) {
97
98 } else if (mode == FileMode.EXECUTABLE_FILE) {
99 entry.setMode(mode.getBits());
100 } else {
101
102 throw new IllegalArgumentException(MessageFormat.format(
103 ArchiveText.get().unsupportedMode, mode));
104 }
105 entry.setSize(loader.getSize());
106 out.putArchiveEntry(entry);
107 loader.copyTo(out);
108 out.closeArchiveEntry();
109 }
110
111
112 @Override
113 public Iterable<String> suffixes() {
114 return SUFFIXES;
115 }
116
117
118 @Override
119 public boolean equals(Object other) {
120 return (other instanceof TarFormat);
121 }
122
123
124 @Override
125 public int hashCode() {
126 return getClass().hashCode();
127 }
128 }