1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44 package org.eclipse.jgit.api;
45
46 import java.io.IOException;
47 import java.text.MessageFormat;
48 import java.util.Arrays;
49
50 import org.eclipse.jgit.api.errors.DetachedHeadException;
51 import org.eclipse.jgit.api.errors.GitAPIException;
52 import org.eclipse.jgit.api.errors.InvalidRefNameException;
53 import org.eclipse.jgit.api.errors.JGitInternalException;
54 import org.eclipse.jgit.api.errors.NoHeadException;
55 import org.eclipse.jgit.api.errors.RefAlreadyExistsException;
56 import org.eclipse.jgit.api.errors.RefNotFoundException;
57 import org.eclipse.jgit.internal.JGitText;
58 import org.eclipse.jgit.lib.ConfigConstants;
59 import org.eclipse.jgit.lib.Constants;
60 import org.eclipse.jgit.lib.ObjectId;
61 import org.eclipse.jgit.lib.Ref;
62 import org.eclipse.jgit.lib.RefRename;
63 import org.eclipse.jgit.lib.RefUpdate.Result;
64 import org.eclipse.jgit.lib.Repository;
65 import org.eclipse.jgit.lib.StoredConfig;
66
67
68
69
70
71
72
73
74 public class RenameBranchCommand extends GitCommand<Ref> {
75 private String oldName;
76
77 private String newName;
78
79
80
81
82 protected RenameBranchCommand(Repository repo) {
83 super(repo);
84 }
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99 @Override
100 public Ref call() throws GitAPIException, RefNotFoundException, InvalidRefNameException,
101 RefAlreadyExistsException, DetachedHeadException {
102 checkCallable();
103
104 if (newName == null)
105 throw new InvalidRefNameException(MessageFormat.format(JGitText
106 .get().branchNameInvalid, "<null>"));
107
108 try {
109 String fullOldName;
110 String fullNewName;
111 if (repo.findRef(newName) != null)
112 throw new RefAlreadyExistsException(MessageFormat.format(
113 JGitText.get().refAlreadyExists1, newName));
114 if (oldName != null) {
115 Ref ref = repo.findRef(oldName);
116 if (ref == null)
117 throw new RefNotFoundException(MessageFormat.format(
118 JGitText.get().refNotResolved, oldName));
119 if (ref.getName().startsWith(Constants.R_TAGS))
120 throw new RefNotFoundException(MessageFormat.format(
121 JGitText.get().renameBranchFailedBecauseTag,
122 oldName));
123 fullOldName = ref.getName();
124 } else {
125 fullOldName = repo.getFullBranch();
126 if (fullOldName == null) {
127 throw new NoHeadException(
128 JGitText.get().invalidRepositoryStateNoHead);
129 }
130 if (ObjectId.isId(fullOldName))
131 throw new DetachedHeadException();
132 }
133
134 if (fullOldName.startsWith(Constants.R_REMOTES))
135 fullNewName = Constants.R_REMOTES + newName;
136 else {
137 fullNewName = Constants.R_HEADS + newName;
138 }
139
140 if (!Repository.isValidRefName(fullNewName))
141 throw new InvalidRefNameException(MessageFormat.format(JGitText
142 .get().branchNameInvalid, fullNewName));
143
144 RefRename rename = repo.renameRef(fullOldName, fullNewName);
145 Result renameResult = rename.rename();
146
147 setCallable(false);
148
149 if (Result.RENAMED != renameResult)
150 throw new JGitInternalException(MessageFormat.format(JGitText
151 .get().renameBranchUnexpectedResult, renameResult
152 .name()));
153
154 if (fullNewName.startsWith(Constants.R_HEADS)) {
155 String shortOldName = fullOldName.substring(Constants.R_HEADS
156 .length());
157 final StoredConfig repoConfig = repo.getConfig();
158
159 for (String name : repoConfig.getNames(
160 ConfigConstants.CONFIG_BRANCH_SECTION, shortOldName)) {
161 String[] values = repoConfig.getStringList(
162 ConfigConstants.CONFIG_BRANCH_SECTION,
163 shortOldName, name);
164 if (values.length == 0)
165 continue;
166
167
168 String[] existing = repoConfig.getStringList(
169 ConfigConstants.CONFIG_BRANCH_SECTION, newName,
170 name);
171 if (existing.length > 0) {
172 String[] newValues = new String[values.length
173 + existing.length];
174 System.arraycopy(existing, 0, newValues, 0,
175 existing.length);
176 System.arraycopy(values, 0, newValues, existing.length,
177 values.length);
178 values = newValues;
179 }
180
181 repoConfig.setStringList(
182 ConfigConstants.CONFIG_BRANCH_SECTION, newName,
183 name, Arrays.asList(values));
184 }
185 repoConfig.unsetSection(ConfigConstants.CONFIG_BRANCH_SECTION,
186 shortOldName);
187 repoConfig.save();
188 }
189
190 Ref resultRef = repo.findRef(newName);
191 if (resultRef == null)
192 throw new JGitInternalException(
193 JGitText.get().renameBranchFailedUnknownReason);
194 return resultRef;
195 } catch (IOException ioe) {
196 throw new JGitInternalException(ioe.getMessage(), ioe);
197 }
198 }
199
200
201
202
203
204
205 public RenameBranchCommand setNewName(String newName) {
206 checkCallable();
207 this.newName = newName;
208 return this;
209 }
210
211
212
213
214
215
216
217 public RenameBranchCommand setOldName(String oldName) {
218 checkCallable();
219 this.oldName = oldName;
220 return this;
221 }
222 }