From 264ba908941414ea5e750524b2472f7ad0670563 Mon Sep 17 00:00:00 2001 From: James Moger Date: Thu, 2 May 2013 21:37:58 -0400 Subject: [PATCH] Improved the repository url panel and show git daemon url, appropriately This will probably be refined some more to merge the http/https and git urls into a single url panel. --- .../gitblit/wicket/GitBlitWebApp.properties | 7 +- .../com/gitblit/wicket/pages/BasePage.java | 42 +++++++ .../wicket/pages/EmptyRepositoryPage.java | 12 +- .../com/gitblit/wicket/pages/ProjectPage.html | 2 +- .../com/gitblit/wicket/pages/SummaryPage.html | 10 +- .../com/gitblit/wicket/pages/SummaryPage.java | 34 ++++-- .../panels/DetailedRepositoryUrlPanel.html | 42 +++++++ .../panels/DetailedRepositoryUrlPanel.java | 115 ++++++++++++++++++ .../wicket/panels/ProjectRepositoryPanel.html | 2 +- .../wicket/panels/ProjectRepositoryPanel.java | 6 +- src/main/resources/gitblit.css | 24 ++++ 11 files changed, 279 insertions(+), 17 deletions(-) create mode 100644 src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.html create mode 100644 src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.java diff --git a/src/main/java/com/gitblit/wicket/GitBlitWebApp.properties b/src/main/java/com/gitblit/wicket/GitBlitWebApp.properties index f2d4a36c..aa5a415a 100644 --- a/src/main/java/com/gitblit/wicket/GitBlitWebApp.properties +++ b/src/main/java/com/gitblit/wicket/GitBlitWebApp.properties @@ -445,7 +445,10 @@ gb.isSparkleshared = repository is Sparkleshared gb.owners = owners gb.sessionEnded = Session has been closed gb.closeBrowser = Please close the browser to properly end the session. -gb.doesNotExistInTree = {0} does not exist in tree {1} +gb.doesNotExistInTree = {0} does not exist in tree {1} gb.enableIncrementalPushTags = enable incremental push tags gb.useIncrementalPushTagsDescription = on push, automatically tag each branch tip with an incremental revision number -gb.incrementalPushTagMessage = Auto-tagged [{0}] branch on push \ No newline at end of file +gb.incrementalPushTagMessage = Auto-tagged [{0}] branch on push +gb.externalPermissions = {0} access permissions for {1} are externally maintained +gb.viewAccess = You do not have Gitblit read or write access +gb.yourProtocolPermissionIs = Your {0} access permission for {1} is {2} \ No newline at end of file diff --git a/src/main/java/com/gitblit/wicket/pages/BasePage.java b/src/main/java/com/gitblit/wicket/pages/BasePage.java index bb7d8c9e..b2dcce3f 100644 --- a/src/main/java/com/gitblit/wicket/pages/BasePage.java +++ b/src/main/java/com/gitblit/wicket/pages/BasePage.java @@ -32,6 +32,7 @@ import java.util.regex.Pattern; import javax.servlet.http.HttpServletRequest; import org.apache.wicket.Application; +import org.apache.wicket.Component; import org.apache.wicket.MarkupContainer; import org.apache.wicket.PageParameters; import org.apache.wicket.RedirectToUrlException; @@ -44,6 +45,7 @@ import org.apache.wicket.markup.html.link.ExternalLink; import org.apache.wicket.markup.html.panel.FeedbackPanel; import org.apache.wicket.markup.html.panel.Fragment; import org.apache.wicket.protocol.http.RequestUtils; +import org.apache.wicket.protocol.http.WebRequest; import org.apache.wicket.protocol.http.servlet.ServletWebRequest; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -63,6 +65,7 @@ import com.gitblit.utils.StringUtils; import com.gitblit.utils.TimeUtils; import com.gitblit.wicket.GitBlitWebSession; import com.gitblit.wicket.WicketUtils; +import com.gitblit.wicket.panels.DetailedRepositoryUrlPanel; import com.gitblit.wicket.panels.LinkPanel; public abstract class BasePage extends SessionPage { @@ -270,6 +273,45 @@ public abstract class BasePage extends SessionPage { return sb.toString(); } + protected Component createGitDaemonUrlPanel(String wicketId, UserModel user, RepositoryModel repository) { + int gitDaemonPort = GitBlit.getInteger(Keys.git.daemonPort, 0); + if (gitDaemonPort > 0 && user.canClone(repository)) { + String servername = ((WebRequest) getRequest()).getHttpServletRequest().getServerName(); + String gitDaemonUrl; + if (gitDaemonPort == 9418) { + // standard port + gitDaemonUrl = MessageFormat.format("git://{0}/{1}", servername, repository.name); + } else { + // non-standard port + gitDaemonUrl = MessageFormat.format("git://{0}:{1,number,0}/{2}", servername, gitDaemonPort, repository.name); + } + + AccessPermission gitDaemonPermission = user.getRepositoryPermission(repository).permission;; + if (gitDaemonPermission.atLeast(AccessPermission.CLONE)) { + if (repository.accessRestriction.atLeast(AccessRestrictionType.CLONE)) { + // can not authenticate clone via anonymous git protocol + gitDaemonPermission = AccessPermission.NONE; + } else if (repository.accessRestriction.atLeast(AccessRestrictionType.PUSH)) { + // can not authenticate push via anonymous git protocol + gitDaemonPermission = AccessPermission.CLONE; + } else { + // normal user permission + } + } + + if (AccessPermission.NONE.equals(gitDaemonPermission)) { + // repository prohibits all anonymous access + return new Label(wicketId).setVisible(false); + } else { + // repository allows some form of anonymous access + return new DetailedRepositoryUrlPanel(wicketId, getLocalizer(), this, repository.name, gitDaemonUrl, gitDaemonPermission); + } + } else { + // git daemon is not running + return new Label(wicketId).setVisible(false); + } + } + protected List getProjectModels() { final UserModel user = GitBlitWebSession.get().getUser(); List projects = GitBlit.self().getProjectModels(user, true); diff --git a/src/main/java/com/gitblit/wicket/pages/EmptyRepositoryPage.java b/src/main/java/com/gitblit/wicket/pages/EmptyRepositoryPage.java index cccf8a69..a2264c44 100644 --- a/src/main/java/com/gitblit/wicket/pages/EmptyRepositoryPage.java +++ b/src/main/java/com/gitblit/wicket/pages/EmptyRepositoryPage.java @@ -22,6 +22,7 @@ import java.util.List; import org.apache.wicket.PageParameters; import org.apache.wicket.markup.html.basic.Label; +import com.gitblit.Constants.AccessPermission; import com.gitblit.GitBlit; import com.gitblit.Keys; import com.gitblit.models.RepositoryModel; @@ -30,7 +31,7 @@ import com.gitblit.utils.ArrayUtils; import com.gitblit.wicket.GitBlitWebSession; import com.gitblit.wicket.GitblitRedirectException; import com.gitblit.wicket.WicketUtils; -import com.gitblit.wicket.panels.RepositoryUrlPanel; +import com.gitblit.wicket.panels.DetailedRepositoryUrlPanel; public class EmptyRepositoryPage extends RootPage { @@ -59,11 +60,16 @@ public class EmptyRepositoryPage extends RootPage { repositoryUrls.add(getRepositoryUrl(repository)); } UserModel user = GitBlitWebSession.get().getUser(); - repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(repositoryName, user == null ? "" : user.username)); + if (user == null) { + user = UserModel.ANONYMOUS; + } + repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(repositoryName, UserModel.ANONYMOUS.equals(user) ? "" : user.username)); String primaryUrl = ArrayUtils.isEmpty(repositoryUrls) ? "" : repositoryUrls.get(0); + AccessPermission accessPermission = user.getRepositoryPermission(repository).permission; + add(new Label("repository", repositoryName)); - add(new RepositoryUrlPanel("pushurl", primaryUrl)); + add(new DetailedRepositoryUrlPanel("pushurl", getLocalizer(), this, repository.name, primaryUrl, accessPermission)); add(new Label("cloneSyntax", MessageFormat.format("git clone {0}", repositoryUrls.get(0)))); add(new Label("remoteSyntax", MessageFormat.format("git remote add gitblit {0}\ngit push gitblit master", primaryUrl))); } diff --git a/src/main/java/com/gitblit/wicket/pages/ProjectPage.html b/src/main/java/com/gitblit/wicket/pages/ProjectPage.html index 3e73ba52..6c161959 100644 --- a/src/main/java/com/gitblit/wicket/pages/ProjectPage.html +++ b/src/main/java/com/gitblit/wicket/pages/ProjectPage.html @@ -38,7 +38,7 @@
-
+
diff --git a/src/main/java/com/gitblit/wicket/pages/SummaryPage.html b/src/main/java/com/gitblit/wicket/pages/SummaryPage.html index 3e85df99..a751d1f0 100644 --- a/src/main/java/com/gitblit/wicket/pages/SummaryPage.html +++ b/src/main/java/com/gitblit/wicket/pages/SummaryPage.html @@ -19,7 +19,15 @@ [owner] [last change][repository last change] [stats][branch stats] [metrics] - [URL] [repository clone url]
+ [URL]  + +
[repository primary url]
+
[repository git daemon url]
+
+
+
+ +
diff --git a/src/main/java/com/gitblit/wicket/pages/SummaryPage.java b/src/main/java/com/gitblit/wicket/pages/SummaryPage.java index d68add0f..863974b3 100644 --- a/src/main/java/com/gitblit/wicket/pages/SummaryPage.java +++ b/src/main/java/com/gitblit/wicket/pages/SummaryPage.java @@ -42,6 +42,7 @@ import org.wicketstuff.googlecharts.LineStyle; import org.wicketstuff.googlecharts.MarkerType; import org.wicketstuff.googlecharts.ShapeMarker; +import com.gitblit.Constants.AccessPermission; import com.gitblit.Constants.AccessRestrictionType; import com.gitblit.GitBlit; import com.gitblit.Keys; @@ -56,9 +57,9 @@ import com.gitblit.utils.StringUtils; import com.gitblit.wicket.GitBlitWebSession; import com.gitblit.wicket.WicketUtils; import com.gitblit.wicket.panels.BranchesPanel; +import com.gitblit.wicket.panels.DetailedRepositoryUrlPanel; import com.gitblit.wicket.panels.LinkPanel; import com.gitblit.wicket.panels.LogPanel; -import com.gitblit.wicket.panels.RepositoryUrlPanel; import com.gitblit.wicket.panels.TagsPanel; public class SummaryPage extends RepositoryPage { @@ -73,8 +74,11 @@ public class SummaryPage extends RepositoryPage { int numberRefs = GitBlit.getInteger(Keys.web.summaryRefsCount, 5); Repository r = getRepository(); - RepositoryModel model = getRepositoryModel(); + final RepositoryModel model = getRepositoryModel(); UserModel user = GitBlitWebSession.get().getUser(); + if (user == null) { + user = UserModel.ANONYMOUS; + } List metrics = null; Metric metricsTotal = null; @@ -124,7 +128,9 @@ public class SummaryPage extends RepositoryPage { List repositoryUrls = new ArrayList(); - if (GitBlit.getBoolean(Keys.git.enableGitServlet, true)) { + AccessPermission accessPermission = null; + if (GitBlit.getBoolean(Keys.git.enableGitServlet, true)) { + accessPermission = user.getRepositoryPermission(model).permission; AccessRestrictionType accessRestriction = getRepositoryModel().accessRestriction; switch (accessRestriction) { case NONE: @@ -150,13 +156,27 @@ public class SummaryPage extends RepositoryPage { } else { add(WicketUtils.newClearPixel("accessRestrictionIcon").setVisible(false)); } - repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(repositoryName, user == null ? "" : user.username)); + repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(repositoryName, UserModel.ANONYMOUS.equals(user) ? "" : user.username)); String primaryUrl = ArrayUtils.isEmpty(repositoryUrls) ? "" : repositoryUrls.remove(0); - add(new RepositoryUrlPanel("repositoryCloneUrl", primaryUrl)); + add(new DetailedRepositoryUrlPanel("repositoryPrimaryUrl", getLocalizer(), this, model.name, primaryUrl, accessPermission)); + + Component gitDaemonUrlPanel = createGitDaemonUrlPanel("repositoryGitDaemonUrl", user, model); + if (!StringUtils.isEmpty(primaryUrl) && gitDaemonUrlPanel instanceof DetailedRepositoryUrlPanel) { + WicketUtils.setCssStyle(gitDaemonUrlPanel, "padding-top: 10px"); + } + add(gitDaemonUrlPanel); + + ListDataProvider urls = new ListDataProvider(repositoryUrls); + DataView otherUrlsView = new DataView("otherUrls", urls) { + private static final long serialVersionUID = 1L; - add(new Label("otherUrls", StringUtils.flattenStrings(repositoryUrls, "
")) - .setEscapeModelStrings(false)); + public void populateItem(final Item item) { + final String url = item.getModelObject(); + item.add(new DetailedRepositoryUrlPanel("otherUrl", getLocalizer(), this, model.name, url)); + } + }; + add(otherUrlsView); add(new LogPanel("commitsPanel", repositoryName, getRepositoryModel().HEAD, r, numberCommits, 0, getRepositoryModel().showRemoteBranches)); add(new TagsPanel("tagsPanel", repositoryName, r, numberRefs).hideIfEmpty()); diff --git a/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.html b/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.html new file mode 100644 index 00000000..e671435b --- /dev/null +++ b/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.html @@ -0,0 +1,42 @@ + + + + + + + + + + [protocol] + + [repository url] + + + [repository url permission] + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.java b/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.java new file mode 100644 index 00000000..afeee1d0 --- /dev/null +++ b/src/main/java/com/gitblit/wicket/panels/DetailedRepositoryUrlPanel.java @@ -0,0 +1,115 @@ +/* + * Copyright 2013 gitblit.com. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.gitblit.wicket.panels; + +import java.text.MessageFormat; + +import org.apache.wicket.Component; +import org.apache.wicket.Localizer; +import org.apache.wicket.markup.html.basic.Label; +import org.apache.wicket.markup.html.image.ContextImage; +import org.apache.wicket.markup.html.panel.Fragment; + +import com.gitblit.Constants.AccessPermission; +import com.gitblit.GitBlit; +import com.gitblit.Keys; +import com.gitblit.utils.StringUtils; +import com.gitblit.wicket.WicketUtils; + +public class DetailedRepositoryUrlPanel extends BasePanel { + + private static final long serialVersionUID = 1L; + public DetailedRepositoryUrlPanel(String wicketId, Localizer localizer, Component parent, String repository, String url) { + this(wicketId, localizer, parent, repository, url, null); + } + + public DetailedRepositoryUrlPanel(String wicketId, Localizer localizer, Component parent, String repository, String url, AccessPermission ap) { + super(wicketId); + + String protocol = url.substring(0, url.indexOf(':')); + String note; + String permission; + + if (ap == null) { + note = MessageFormat.format(localizer.getString("gb.externalPermissions", parent), protocol, repository); + permission = ""; + } else { + note = null; + permission = ap.toString(); + String key; + switch (ap) { + case OWNER: + case REWIND: + key = "gb.rewindPermission"; + break; + case DELETE: + key = "gb.deletePermission"; + break; + case CREATE: + key = "gb.createPermission"; + break; + case PUSH: + key = "gb.pushPermission"; + break; + case CLONE: + key = "gb.clonePermission"; + break; + default: + key = null; + note = localizer.getString("gb.viewAccess", parent); + break; + } + + if (note == null) { + String pattern = localizer.getString(key, parent); + String description = MessageFormat.format(pattern, permission); + String permissionPattern = localizer.getString("gb.yourProtocolPermissionIs", parent); + note = MessageFormat.format(permissionPattern, protocol.toUpperCase(), repository, description); + } + } + + if (!StringUtils.isEmpty(url) && ((ap == null) || ap.atLeast(AccessPermission.CLONE))) { + // valid repository url + Fragment fragment = new Fragment("urlPanel", "repositoryUrlPanel", this); + add(fragment); + fragment.add(WicketUtils.setHtmlTooltip(new Label("repositoryProtocol", protocol + "://"), note)); + fragment.add(new Label("repositoryUrl", url.substring(url.indexOf("://") + 3))); + fragment.add(WicketUtils.setHtmlTooltip(new Label("repositoryUrlPermission", permission), note)); + + if (StringUtils.isEmpty(url)) { + fragment.add(new Label("copyFunction").setVisible(false)); + } else if (GitBlit.getBoolean(Keys.web.allowFlashCopyToClipboard, true)) { + // clippy: flash-based copy & paste + Fragment copyFragment = new Fragment("copyFunction", "clippyPanel", this); + String baseUrl = WicketUtils.getGitblitURL(getRequest()); + ShockWaveComponent clippy = new ShockWaveComponent("clippy", baseUrl + "/clippy.swf"); + clippy.setValue("flashVars", "text=" + StringUtils.encodeURL(url)); + copyFragment.add(clippy); + fragment.add(copyFragment); + } else { + // javascript: manual copy & paste with modal browser prompt dialog + Fragment copyFragment = new Fragment("copyFunction", "jsPanel", this); + ContextImage img = WicketUtils.newImage("copyIcon", "clippy.png"); + img.add(new JavascriptTextPrompt("onclick", "Copy to Clipboard (Ctrl+C, Enter)", url)); + copyFragment.add(img); + fragment.add(copyFragment); + } + } else { + // no Git url, there may be a message + add(new Label("urlPanel", MessageFormat.format("{0}", note)).setEscapeModelStrings(false).setVisible(!StringUtils.isEmpty(note))); + } + } +} diff --git a/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.html b/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.html index 9b621d5a..e67e6416 100644 --- a/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.html +++ b/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.html @@ -72,7 +72,7 @@ [repository size] -
[repository clone url]
+
[repository primary url]
diff --git a/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.java b/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.java index f2b56e17..822a9b21 100644 --- a/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.java +++ b/src/main/java/com/gitblit/wicket/panels/ProjectRepositoryPanel.java @@ -29,6 +29,7 @@ import org.apache.wicket.markup.html.link.ExternalLink; import org.apache.wicket.markup.html.link.Link; import org.apache.wicket.markup.html.panel.Fragment; +import com.gitblit.Constants.AccessPermission; import com.gitblit.Constants.AccessRestrictionType; import com.gitblit.GitBlit; import com.gitblit.Keys; @@ -221,9 +222,10 @@ public class ProjectRepositoryPanel extends BasePanel { // add the Gitblit repository url repositoryUrls.add(BasePage.getRepositoryUrl(entry)); } - repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(entry.name, user == null ? "" : user.username)); + repositoryUrls.addAll(GitBlit.self().getOtherCloneUrls(entry.name, UserModel.ANONYMOUS.equals(user) ? "" : user.username)); + AccessPermission ap = user.getRepositoryPermission(entry).permission; String primaryUrl = ArrayUtils.isEmpty(repositoryUrls) ? "" : repositoryUrls.remove(0); - add(new RepositoryUrlPanel("repositoryCloneUrl", primaryUrl)); + add(new DetailedRepositoryUrlPanel("repositoryPrimaryUrl",localizer, parent, entry.name, primaryUrl, ap)); } } diff --git a/src/main/resources/gitblit.css b/src/main/resources/gitblit.css index 811b08a5..c93f6a69 100644 --- a/src/main/resources/gitblit.css +++ b/src/main/resources/gitblit.css @@ -179,6 +179,30 @@ navbar div>ul .menu-dropdown li a:hover,.nav .menu-dropdown li a:hover,.navbar d vertical-align: middle; } +span.repositoryUrlContainer { + color: black; + background-color: #eee; + padding: 4px; + border: 1px solid #ccc; + border-radius: 3px +} + +span.repositoryUrlEndCap { + padding: 4px; + font-weight: bold; + font-size: 0.85em; + font-family:menlo,consolas,monospace; +} + +span.repositoryUrl { + font-size: 1em; + padding: 4px; + color: blue; + background-color: #fff; + border-left: 1px solid #ccc; + border-right: 1px solid #ccc; +} + div.odd { } -- 2.39.5