From 20a8bb8edccd189ce8a40cabd78a2643d2c34c68 Mon Sep 17 00:00:00 2001 From: James Moger <james.moger@gitblit.com> Date: Wed, 25 Apr 2012 17:30:11 -0400 Subject: [PATCH] Allow manipulating display name and email address from web ui --- src/com/gitblit/utils/JGitUtils.java | 209 ++++++++++++++++++++++++++++++++++++---------------- 1 files changed, 144 insertions(+), 65 deletions(-) diff --git a/src/com/gitblit/utils/JGitUtils.java b/src/com/gitblit/utils/JGitUtils.java index 5d6011a..72e948c 100644 --- a/src/com/gitblit/utils/JGitUtils.java +++ b/src/com/gitblit/utils/JGitUtils.java @@ -36,8 +36,6 @@ import org.eclipse.jgit.api.CloneCommand; import org.eclipse.jgit.api.FetchCommand; import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.ResetCommand; -import org.eclipse.jgit.api.ResetCommand.ResetType; import org.eclipse.jgit.diff.DiffEntry; import org.eclipse.jgit.diff.DiffEntry.ChangeType; import org.eclipse.jgit.diff.DiffFormatter; @@ -253,27 +251,6 @@ } /** - * Reset HEAD to the latest remote tracking commit. - * - * @param repository - * @param remoteRef - * the remote tracking reference (e.g. origin/master) - * @return Ref - * @throws Exception - */ - public static Ref resetHEAD(Repository repository, String remoteRef) throws Exception { - if (!remoteRef.startsWith(Constants.R_REMOTES)) { - remoteRef = Constants.R_REMOTES + remoteRef; - } - Git git = new Git(repository); - ResetCommand reset = git.reset(); - reset.setMode(ResetType.SOFT); - reset.setRef(remoteRef); - Ref result = reset.call(); - return result; - } - - /** * Creates a bare repository. * * @param repositoriesFolder @@ -289,21 +266,21 @@ * Returns a list of repository names in the specified folder. * * @param repositoriesFolder - * @param exportAll - * if true, all repositories are listed. If false only the - * repositories with a "git-daemon-export-ok" file are included + * @param onlyBare + * if true, only bare repositories repositories are listed. If + * false all repositories are included. * @param searchSubfolders * recurse into subfolders to find grouped repositories * @return list of repository names */ - public static List<String> getRepositoryList(File repositoriesFolder, boolean exportAll, + public static List<String> getRepositoryList(File repositoriesFolder, boolean onlyBare, boolean searchSubfolders) { List<String> list = new ArrayList<String>(); if (repositoriesFolder == null || !repositoriesFolder.exists()) { return list; } list.addAll(getRepositoryList(repositoriesFolder.getAbsolutePath(), repositoriesFolder, - exportAll, searchSubfolders)); + onlyBare, searchSubfolders)); StringUtils.sortRepositorynames(list); return list; } @@ -315,33 +292,30 @@ * basePath is stripped from the repository name as repositories * are relative to this path * @param searchFolder - * @param exportAll - * if true all repositories are listed. If false only the - * repositories with a "git-daemon-export-ok" file are included + * @param onlyBare + * if true only bare repositories will be listed. if false all + * repositories are included. * @param searchSubfolders * recurse into subfolders to find grouped repositories * @return */ private static List<String> getRepositoryList(String basePath, File searchFolder, - boolean exportAll, boolean searchSubfolders) { + boolean onlyBare, boolean searchSubfolders) { + File baseFile = new File(basePath); List<String> list = new ArrayList<String>(); for (File file : searchFolder.listFiles()) { if (file.isDirectory()) { File gitDir = FileKey.resolve(new File(searchFolder, file.getName()), FS.DETECTED); if (gitDir != null) { - boolean exportRepository = exportAll - || new File(gitDir, "git-daemon-export-ok").exists(); - - if (!exportRepository) { + if (onlyBare && gitDir.getName().equals(".git")) { continue; } // determine repository name relative to base path - String repository = StringUtils.getRelativePath(basePath, - file.getAbsolutePath()); + String repository = FileUtils.getRelativePath(baseFile, file); list.add(repository); - } else if (searchSubfolders) { + } else if (searchSubfolders && file.canRead()) { // look for repositories in subfolders - list.addAll(getRepositoryList(basePath, file, exportAll, searchSubfolders)); + list.addAll(getRepositoryList(basePath, file, onlyBare, searchSubfolders)); } } } @@ -426,11 +400,9 @@ * last modified date of the repository folder is returned. * * @param repository - * @param branch - * if unspecified, all branches are checked. * @return */ - public static Date getLastChange(Repository repository, String branch) { + public static Date getLastChange(Repository repository) { if (!hasCommits(repository)) { // null repository if (repository == null) { @@ -439,26 +411,21 @@ // fresh repository return new Date(repository.getDirectory().lastModified()); } - if (StringUtils.isEmpty(branch)) { - List<RefModel> branchModels = getLocalBranches(repository, true, -1); - if (branchModels.size() > 0) { - // find most recent branch update - Date lastChange = new Date(0); - for (RefModel branchModel : branchModels) { - if (branchModel.getDate().after(lastChange)) { - lastChange = branchModel.getDate(); - } - } - return lastChange; - } else { - // try to find head - branch = Constants.HEAD; - } - } - // lookup specified branch - RevCommit commit = getCommit(repository, branch); - return getCommitDate(commit); + List<RefModel> branchModels = getLocalBranches(repository, true, -1); + if (branchModels.size() > 0) { + // find most recent branch update + Date lastChange = new Date(0); + for (RefModel branchModel : branchModels) { + if (branchModel.getDate().after(lastChange)) { + lastChange = branchModel.getDate(); + } + } + return lastChange; + } + + // default to the repository folder modification date + return new Date(repository.getDirectory().lastModified()); } /** @@ -731,6 +698,10 @@ list.add(new PathChangeModel(diff.getOldPath(), diff.getOldPath(), 0, diff .getNewMode().getBits(), commit.getId().getName(), diff .getChangeType())); + } else if (diff.getChangeType().equals(ChangeType.RENAME)) { + list.add(new PathChangeModel(diff.getOldPath(), diff.getNewPath(), 0, diff + .getNewMode().getBits(), commit.getId().getName(), diff + .getChangeType())); } else { list.add(new PathChangeModel(diff.getNewPath(), diff.getNewPath(), 0, diff .getNewMode().getBits(), commit.getId().getName(), diff @@ -965,6 +936,9 @@ } else { branchObject = repository.resolve(objectId); } + if (branchObject == null) { + return list; + } RevWalk rw = new RevWalk(repository); rw.markStart(rw.parseCommit(branchObject)); @@ -1175,6 +1149,98 @@ } /** + * Returns the target of the symbolic HEAD reference for a repository. + * Normally returns a branch reference name, but when HEAD is detached, + * the commit is matched against the known tags. The most recent matching + * tag ref name will be returned if it references the HEAD commit. If + * no match is found, the SHA1 is returned. + * + * @param repository + * @return the ref name or the SHA1 for a detached HEAD + */ + public static String getHEADRef(Repository repository) { + String target = null; + try { + target = repository.getFullBranch(); + if (!target.startsWith(Constants.R_HEADS)) { + // refers to an actual commit, probably a tag + // find latest tag that matches the commit, if any + List<RefModel> tagModels = getTags(repository, true, -1); + if (tagModels.size() > 0) { + RefModel tag = null; + Date lastDate = new Date(0); + for (RefModel tagModel : tagModels) { + if (tagModel.getReferencedObjectId().getName().equals(target) && + tagModel.getDate().after(lastDate)) { + tag = tagModel; + lastDate = tag.getDate(); + } + } + target = tag.getName(); + } + } + } catch (Throwable t) { + error(t, repository, "{0} failed to get symbolic HEAD target"); + } + return target; + } + + /** + * Sets the symbolic ref HEAD to the specified target ref. The + * HEAD will be detached if the target ref is not a branch. + * + * @param repository + * @param targetRef + * @return true if successful + */ + public static boolean setHEADtoRef(Repository repository, String targetRef) { + try { + // detach HEAD if target ref is not a branch + boolean detach = !targetRef.startsWith(Constants.R_HEADS); + RefUpdate.Result result; + RefUpdate head = repository.updateRef(Constants.HEAD, detach); + if (detach) { // Tag + RevCommit commit = getCommit(repository, targetRef); + head.setNewObjectId(commit.getId()); + result = head.forceUpdate(); + } else { + result = head.link(targetRef); + } + switch (result) { + case NEW: + case FORCED: + case NO_CHANGE: + case FAST_FORWARD: + return true; + default: + LOGGER.error(MessageFormat.format("{0} HEAD update to {1} returned result {2}", + repository.getDirectory().getAbsolutePath(), targetRef, result)); + } + } catch (Throwable t) { + error(t, repository, "{0} failed to set HEAD to {1}", targetRef); + } + return false; + } + + /** + * Get the full branch and tag ref names for any potential HEAD targets. + * + * @param repository + * @return a list of ref names + */ + public static List<String> getAvailableHeadTargets(Repository repository) { + List<String> targets = new ArrayList<String>(); + for (RefModel branchModel : JGitUtils.getLocalBranches(repository, true, -1)) { + targets.add(branchModel.getName()); + } + + for (RefModel tagModel : JGitUtils.getTags(repository, true, -1)) { + targets.add(tagModel.getName()); + } + return targets; + } + + /** * Returns all refs grouped by their associated object id. * * @param repository @@ -1368,10 +1434,23 @@ List<RefModel> noteBranches = getNoteBranches(repository, true, -1); for (RefModel notesRef : noteBranches) { RevTree notesTree = JGitUtils.getCommit(repository, notesRef.getName()).getTree(); + // flat notes list + String notePath = commit.getName(); + String text = getStringContent(repository, notesTree, notePath); + if (!StringUtils.isEmpty(text)) { + List<RevCommit> history = getRevLog(repository, notesRef.getName(), notePath, 0, -1); + RefModel noteRef = new RefModel(notesRef.displayName, null, history.get(history + .size() - 1)); + GitNote gitNote = new GitNote(noteRef, text); + list.add(gitNote); + continue; + } + + // folder structure StringBuilder sb = new StringBuilder(commit.getName()); sb.insert(2, '/'); - String notePath = sb.toString(); - String text = getStringContent(repository, notesTree, notePath); + notePath = sb.toString(); + text = getStringContent(repository, notesTree, notePath); if (!StringUtils.isEmpty(text)) { List<RevCommit> history = getRevLog(repository, notesRef.getName(), notePath, 0, -1); RefModel noteRef = new RefModel(notesRef.displayName, null, history.get(history @@ -1408,7 +1487,7 @@ // Create a tree object to reference from a commit TreeFormatter tree = new TreeFormatter(); - tree.append("NEWBRANCH", FileMode.REGULAR_FILE, blobId); + tree.append(".branch", FileMode.REGULAR_FILE, blobId); ObjectId treeId = odi.insert(tree); // Create a commit object -- Gitblit v1.9.1