diff options
author | James Moger <james.moger@gitblit.com> | 2012-01-09 20:49:34 -0500 |
---|---|---|
committer | James Moger <james.moger@gitblit.com> | 2012-01-09 20:49:34 -0500 |
commit | 11924dc5db4bc44cb32e905700a8557124b1fd56 (patch) | |
tree | 610fbdf40ef312a5b2512864ae381838efa38e11 | |
parent | 6d874a0cb27092a1c7c3eae3dfe660ffcd8d48e6 (diff) | |
download | gitblit-11924dc5db4bc44cb32e905700a8557124b1fd56.tar.gz gitblit-11924dc5db4bc44cb32e905700a8557124b1fd56.zip |
Support for gh-pages branch serving as /pages/repo.git
-rw-r--r-- | docs/01_features.mkd | 1 | ||||
-rw-r--r-- | docs/04_releases.mkd | 2 | ||||
-rw-r--r-- | src/WEB-INF/web.xml | 41 | ||||
-rw-r--r-- | src/com/gitblit/GitBlit.java | 29 | ||||
-rw-r--r-- | src/com/gitblit/PagesFilter.java | 103 | ||||
-rw-r--r-- | src/com/gitblit/PagesServlet.java | 227 | ||||
-rw-r--r-- | src/com/gitblit/utils/ArrayUtils.java | 4 | ||||
-rw-r--r-- | src/com/gitblit/utils/JGitUtils.java | 33 | ||||
-rw-r--r-- | src/com/gitblit/wicket/GitBlitWebApp.properties | 3 | ||||
-rw-r--r-- | src/com/gitblit/wicket/PageRegistration.java | 18 | ||||
-rw-r--r-- | src/com/gitblit/wicket/pages/RepositoryPage.java | 24 | ||||
-rw-r--r-- | src/com/gitblit/wicket/panels/LinkPanel.java | 20 | ||||
-rw-r--r-- | src/com/gitblit/wicket/panels/NavigationPanel.java | 8 | ||||
-rw-r--r-- | tests/com/gitblit/tests/GitBlitSuite.java | 12 |
14 files changed, 505 insertions, 20 deletions
diff --git a/docs/01_features.mkd b/docs/01_features.mkd index a5856a1c..7eb9e645 100644 --- a/docs/01_features.mkd +++ b/docs/01_features.mkd @@ -19,6 +19,7 @@ - Repository Owners may edit repositories through the web UI
- Gravatar integration
- Git-notes display support
+- gh-pages display support (Jekyll is not supported)
- Branch metrics (uses Google Charts)
- HEAD and Branch RSS feeds
- Blame annotations view
diff --git a/docs/04_releases.mkd b/docs/04_releases.mkd index c142f5f4..89211cc7 100644 --- a/docs/04_releases.mkd +++ b/docs/04_releases.mkd @@ -33,6 +33,8 @@ The original `users.properties` file and it's corresponding implementation are * **New:** *web.allowFlashCopyToClipboard = true*
- JavaScript-based 3-step (click, ctrl+c, enter) *copy to clipboard* of the primary repository url in the event that you do not want to use Flash on your installation
- Empty repositories now link to an *empty repository* page which gives some direction to the user for the next step in using Gitblit. This page displays the primary push/clone url of the repository and gives sample syntax for the git command-line client. (issue 31)
+- automatic *gh-pages* branch serving (Jekyll is not supported)
+Gitblit does not checkout your gh-pages branch to a temporary filesystem, all page and resource requests are live through the repository
- Gitblit Express bundle to get started running Gitblit on RedHat's OpenShift cloud <span class="label warning">BETA</span>
#### changes
diff --git a/src/WEB-INF/web.xml b/src/WEB-INF/web.xml index afe4552d..eef49d49 100644 --- a/src/WEB-INF/web.xml +++ b/src/WEB-INF/web.xml @@ -82,8 +82,23 @@ <servlet-name>RpcServlet</servlet-name>
<url-pattern>/rpc/*</url-pattern>
</servlet-mapping>
+
+
+ <!-- Pages Servlet
+ <url-pattern> MUST match:
+ * PagesFilter
+ * com.gitblit.Constants.PAGES_PATH
+ * Wicket Filter ignorePaths parameter -->
+ <servlet>
+ <servlet-name>PagesServlet</servlet-name>
+ <servlet-class>com.gitblit.PagesServlet</servlet-class>
+ </servlet>
+ <servlet-mapping>
+ <servlet-name>PagesServlet</servlet-name>
+ <url-pattern>/pages/*</url-pattern>
+ </servlet-mapping>
-
+
<!-- Git Access Restriction Filter
<url-pattern> MUST match:
* GitServlet
@@ -143,7 +158,22 @@ <url-pattern>/rpc/*</url-pattern>
</filter-mapping>
-
+
+ <!-- Pges Restriction Filter
+ <url-pattern> MUST match:
+ * PagesServlet
+ * com.gitblit.Constants.PAGES_PATH
+ * Wicket Filter ignorePaths parameter -->
+ <filter>
+ <filter-name>PagesFilter</filter-name>
+ <filter-class>com.gitblit.PagesFilter</filter-class>
+ </filter>
+ <filter-mapping>
+ <filter-name>PagesFilter</filter-name>
+ <url-pattern>/pages/*</url-pattern>
+ </filter-mapping>
+
+
<!-- Wicket Filter -->
<filter>
<filter-name>wicketFilter</filter-name>
@@ -168,8 +198,11 @@ * com.gitblit.Constants.ZIP_PATH
* FederationServlet <url-pattern>
* RpcFilter <url-pattern>
- * RpcServlet <url-pattern> -->
- <param-value>git/,feed/,zip/,federation/,rpc/</param-value>
+ * RpcServlet <url-pattern>
+ * PagesFilter <url-pattern>
+ * PagesServlet <url-pattern>
+ * com.gitblit.Constants.PAGES_PATH -->
+ <param-value>git/,feed/,zip/,federation/,rpc/,pages/</param-value>
</init-param>
</filter>
<filter-mapping>
diff --git a/src/com/gitblit/GitBlit.java b/src/com/gitblit/GitBlit.java index ce3e16d6..2448f7ae 100644 --- a/src/com/gitblit/GitBlit.java +++ b/src/com/gitblit/GitBlit.java @@ -653,21 +653,38 @@ public class GitBlit implements ServletContextListener { * @return repository or null
*/
public Repository getRepository(String repositoryName) {
+ return getRepository(repositoryName, true);
+ }
+
+ /**
+ * Returns the JGit repository for the specified name.
+ *
+ * @param repositoryName
+ * @param logError
+ * @return repository or null
+ */
+ public Repository getRepository(String repositoryName, boolean logError) {
Repository r = null;
try {
r = repositoryResolver.open(null, repositoryName);
} catch (RepositoryNotFoundException e) {
r = null;
- logger.error("GitBlit.getRepository(String) failed to find "
- + new File(repositoriesFolder, repositoryName).getAbsolutePath());
+ if (logError) {
+ logger.error("GitBlit.getRepository(String) failed to find "
+ + new File(repositoriesFolder, repositoryName).getAbsolutePath());
+ }
} catch (ServiceNotAuthorizedException e) {
r = null;
- logger.error("GitBlit.getRepository(String) failed to find "
- + new File(repositoriesFolder, repositoryName).getAbsolutePath(), e);
+ if (logError) {
+ logger.error("GitBlit.getRepository(String) failed to find "
+ + new File(repositoriesFolder, repositoryName).getAbsolutePath(), e);
+ }
} catch (ServiceNotEnabledException e) {
r = null;
- logger.error("GitBlit.getRepository(String) failed to find "
- + new File(repositoriesFolder, repositoryName).getAbsolutePath(), e);
+ if (logError) {
+ logger.error("GitBlit.getRepository(String) failed to find "
+ + new File(repositoriesFolder, repositoryName).getAbsolutePath(), e);
+ }
}
return r;
}
diff --git a/src/com/gitblit/PagesFilter.java b/src/com/gitblit/PagesFilter.java new file mode 100644 index 00000000..87fef0d2 --- /dev/null +++ b/src/com/gitblit/PagesFilter.java @@ -0,0 +1,103 @@ +/*
+ * Copyright 2012 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;
+
+import org.eclipse.jgit.lib.Repository;
+
+import com.gitblit.Constants.AccessRestrictionType;
+import com.gitblit.models.RepositoryModel;
+import com.gitblit.models.UserModel;
+
+/**
+ * The PagesFilter is an AccessRestrictionFilter which ensures the gh-pages
+ * requests for a view-restricted repository are authenticated and authorized.
+ *
+ * @author James Moger
+ *
+ */
+public class PagesFilter extends AccessRestrictionFilter {
+
+ /**
+ * Extract the repository name from the url.
+ *
+ * @param url
+ * @return repository name
+ */
+ @Override
+ protected String extractRepositoryName(String url) {
+ // get the repository name from the url by finding a known url suffix
+ String repository = "";
+ Repository r = null;
+ int offset = 0;
+ while (r == null) {
+ int slash = url.indexOf('/', offset);
+ if (slash == -1) {
+ repository = url;
+ } else {
+ repository = url.substring(0, slash);
+ }
+ r = GitBlit.self().getRepository(repository, false);
+ if (r == null) {
+ // try again
+ offset = slash + 1;
+ } else {
+ // close the repo
+ r.close();
+ }
+ if (repository.equals(url)) {
+ // either only repository in url or no repository found
+ break;
+ }
+ }
+ return repository;
+ }
+
+ /**
+ * Analyze the url and returns the action of the request.
+ *
+ * @param url
+ * @return action of the request
+ */
+ @Override
+ protected String getUrlRequestAction(String suffix) {
+ return "VIEW";
+ }
+
+ /**
+ * Determine if the repository requires authentication.
+ *
+ * @param repository
+ * @return true if authentication required
+ */
+ @Override
+ protected boolean requiresAuthentication(RepositoryModel repository) {
+ return repository.accessRestriction.atLeast(AccessRestrictionType.VIEW);
+ }
+
+ /**
+ * Determine if the user can access the repository and perform the specified
+ * action.
+ *
+ * @param repository
+ * @param user
+ * @param action
+ * @return true if user may execute the action on the repository
+ */
+ @Override
+ protected boolean canAccess(RepositoryModel repository, UserModel user, String action) {
+ return user.canAccessRepository(repository);
+ }
+}
diff --git a/src/com/gitblit/PagesServlet.java b/src/com/gitblit/PagesServlet.java new file mode 100644 index 00000000..58d67b0e --- /dev/null +++ b/src/com/gitblit/PagesServlet.java @@ -0,0 +1,227 @@ +/*
+ * Copyright 2012 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;
+
+import java.io.IOException;
+import java.text.MessageFormat;
+import java.text.ParseException;
+
+import javax.servlet.ServletContext;
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevTree;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.gitblit.models.RefModel;
+import com.gitblit.utils.ArrayUtils;
+import com.gitblit.utils.JGitUtils;
+import com.gitblit.utils.MarkdownUtils;
+import com.gitblit.utils.StringUtils;
+
+/**
+ * Serves the content of a gh-pages branch.
+ *
+ * @author James Moger
+ *
+ */
+public class PagesServlet extends HttpServlet {
+
+ private static final long serialVersionUID = 1L;
+
+ private transient Logger logger = LoggerFactory.getLogger(PagesServlet.class);
+
+ public PagesServlet() {
+ super();
+ }
+
+ /**
+ * Returns an url to this servlet for the specified parameters.
+ *
+ * @param baseURL
+ * @param repository
+ * @param path
+ * @return an url
+ */
+ public static String asLink(String baseURL, String repository, String path) {
+ if (baseURL.length() > 0 && baseURL.charAt(baseURL.length() - 1) == '/') {
+ baseURL = baseURL.substring(0, baseURL.length() - 1);
+ }
+ return baseURL + Constants.PAGES + repository + "/" + (path == null ? "" : ("/" + path));
+ }
+
+ /**
+ * Retrieves the specified resource from the gh-pages branch of the
+ * repository.
+ *
+ * @param request
+ * @param response
+ * @throws javax.servlet.ServletException
+ * @throws java.io.IOException
+ */
+ private void processRequest(HttpServletRequest request, HttpServletResponse response)
+ throws ServletException, IOException {
+ String path = request.getPathInfo();
+ if (path.toLowerCase().endsWith(".git")) {
+ // forward to url with trailing /
+ // this is important for relative pages links
+ response.sendRedirect(request.getServletPath() + path + "/");
+ return;
+ }
+ if (path.charAt(0) == '/') {
+ // strip leading /
+ path = path.substring(1);
+ }
+
+ // determine repository and resource from url
+ String repository = "";
+ String resource = "";
+ Repository r = null;
+ int offset = 0;
+ while (r == null) {
+ int slash = path.indexOf('/', offset);
+ if (slash == -1) {
+ repository = path;
+ } else {
+ repository = path.substring(0, slash);
+ }
+ r = GitBlit.self().getRepository(repository, false);
+ offset = slash + 1;
+ if (offset > 0) {
+ resource = path.substring(offset);
+ }
+ if (repository.equals(path)) {
+ // either only repository in url or no repository found
+ break;
+ }
+ }
+
+ ServletContext context = request.getSession().getServletContext();
+
+ try {
+ if (r == null) {
+ // repository not found!
+ String mkd = MessageFormat.format(
+ "# Error\nSorry, no valid **repository** specified in this url: {0}!",
+ repository);
+ error(response, mkd);
+ return;
+ }
+
+ // retrieve the content from the repository
+ RefModel pages = JGitUtils.getPagesBranch(r);
+ RevCommit commit = JGitUtils.getCommit(r, pages.getObjectId().getName());
+
+ if (commit == null) {
+ // branch not found!
+ String mkd = MessageFormat.format(
+ "# Error\nSorry, the repository {0} does not have a **gh-pages** branch!",
+ repository);
+ error(response, mkd);
+ r.close();
+ return;
+ }
+ response.setDateHeader("Last-Modified", JGitUtils.getCommitDate(commit).getTime());
+
+ RevTree tree = commit.getTree();
+ byte[] content = null;
+ if (StringUtils.isEmpty(resource)) {
+ // find resource
+ String[] files = { "index.html", "index.htm", "index.mkd" };
+ for (String file : files) {
+ content = JGitUtils.getStringContent(r, tree, file)
+ .getBytes(Constants.ENCODING);
+ if (content != null) {
+ resource = file;
+ // assume text/html unless the servlet container
+ // overrides
+ response.setContentType("text/html; charset=" + Constants.ENCODING);
+ break;
+ }
+ }
+ } else {
+ // specific resource
+ String contentType = context.getMimeType(resource);
+ if (contentType.startsWith("text")) {
+ content = JGitUtils.getStringContent(r, tree, resource).getBytes(
+ Constants.ENCODING);
+ } else {
+ content = JGitUtils.getByteContent(r, tree, resource);
+ }
+ response.setContentType(contentType);
+ }
+
+ // no content, try custom 404 page
+ if (ArrayUtils.isEmpty(content)) {
+ content = JGitUtils.getStringContent(r, tree, "404.html").getBytes(
+ Constants.ENCODING);
+ // still no content
+ if (ArrayUtils.isEmpty(content)) {
+ content = (MessageFormat.format(
+ "# Error\nSorry, the requested resource **{0}** was not found.",
+ resource)).getBytes(Constants.ENCODING);
+ resource = "404.mkd";
+ }
+ }
+
+ // check to see if we should transform markdown files
+ for (String ext : GitBlit.getStrings(Keys.web.markdownExtensions)) {
+ if (resource.endsWith(ext)) {
+ String mkd = new String(content, Constants.ENCODING);
+ content = MarkdownUtils.transformMarkdown(mkd).getBytes(Constants.ENCODING);
+ break;
+ }
+ }
+
+ try {
+ // output the content
+ response.getOutputStream().write(content);
+ response.flushBuffer();
+ } catch (Throwable t) {
+ logger.error("Failed to write page to client", t);
+ }
+
+ // close the repository
+ r.close();
+ } catch (Throwable t) {
+ logger.error("Failed to write page to client", t);
+ }
+ }
+
+ private void error(HttpServletResponse response, String mkd) throws ServletException,
+ IOException, ParseException {
+ String content = MarkdownUtils.transformMarkdown(mkd);
+ response.setContentType("text/html; charset=" + Constants.ENCODING);
+ response.getWriter().write(content);
+ }
+
+ @Override
+ protected void doPost(HttpServletRequest request, HttpServletResponse response)
+ throws ServletException, IOException {
+ processRequest(request, response);
+ }
+
+ @Override
+ protected void doGet(HttpServletRequest request, HttpServletResponse response)
+ throws ServletException, IOException {
+ processRequest(request, response);
+ }
+}
diff --git a/src/com/gitblit/utils/ArrayUtils.java b/src/com/gitblit/utils/ArrayUtils.java index 635d27ab..d0322b6b 100644 --- a/src/com/gitblit/utils/ArrayUtils.java +++ b/src/com/gitblit/utils/ArrayUtils.java @@ -26,6 +26,10 @@ import java.util.Collection; */
public class ArrayUtils {
+ public static boolean isEmpty(byte [] array) {
+ return array == null || array.length == 0;
+ }
+
public static boolean isEmpty(Object [] array) {
return array == null || array.length == 0;
}
diff --git a/src/com/gitblit/utils/JGitUtils.java b/src/com/gitblit/utils/JGitUtils.java index d694ee28..ae53c942 100644 --- a/src/com/gitblit/utils/JGitUtils.java +++ b/src/com/gitblit/utils/JGitUtils.java @@ -1284,6 +1284,39 @@ public class JGitUtils { }
/**
+ * Returns a RefModel for the gh-pages branch in the repository. If the
+ * branch can not be found, null is returned.
+ *
+ * @param repository
+ * @return a refmodel for the gh-pages branch or null
+ */
+ public static RefModel getPagesBranch(Repository repository) {
+ RefModel ghPages = null;
+ try {
+ // search for gh-pages branch in local heads
+ for (RefModel ref : JGitUtils.getLocalBranches(repository, false, -1)) {
+ if (ref.displayName.endsWith("gh-pages")) {
+ ghPages = ref;
+ break;
+ }
+ }
+
+ // search for gh-pages branch in remote heads
+ if (ghPages == null) {
+ for (RefModel ref : JGitUtils.getRemoteBranches(repository, false, -1)) {
+ if (ref.displayName.endsWith("gh-pages")) {
+ ghPages = ref;
+ break;
+ }
+ }
+ }
+ } catch (Throwable t) {
+ LOGGER.error("Failed to find gh-pages branch!", t);
+ }
+ return ghPages;
+ }
+
+ /**
* Returns the list of notes entered about the commit from the refs/notes
* namespace. If the repository does not exist or is empty, an empty list is
* returned.
diff --git a/src/com/gitblit/wicket/GitBlitWebApp.properties b/src/com/gitblit/wicket/GitBlitWebApp.properties index 2abc5479..713fee70 100644 --- a/src/com/gitblit/wicket/GitBlitWebApp.properties +++ b/src/com/gitblit/wicket/GitBlitWebApp.properties @@ -208,4 +208,5 @@ gb.accessPermissionsForUserDescription = set team memberships or grant access to gb.accessPermissionsForTeamDescription = set team members and grant access to specific restricted repositories
gb.federationRepositoryDescription = share this repository with other Gitblit servers
gb.hookScriptsDescription = run Groovy scripts on pushes to this Gitblit server
-gb.reset = reset
\ No newline at end of file +gb.reset = reset
+gb.pages = pages
\ No newline at end of file diff --git a/src/com/gitblit/wicket/PageRegistration.java b/src/com/gitblit/wicket/PageRegistration.java index fe76a85f..e8eeabae 100644 --- a/src/com/gitblit/wicket/PageRegistration.java +++ b/src/com/gitblit/wicket/PageRegistration.java @@ -49,6 +49,24 @@ public class PageRegistration implements Serializable { }
/**
+ * Represents a page link to a non-Wicket page. Might be external.
+ *
+ * @author James Moger
+ *
+ */
+ public static class OtherPageLink extends PageRegistration {
+
+ private static final long serialVersionUID = 1L;
+
+ public final String url;
+
+ public OtherPageLink(String translationKey, String url) {
+ super(translationKey, null);
+ this.url = url;
+ }
+ }
+
+ /**
* Represents a DropDownMenu for the topbar
*
* @author James Moger
diff --git a/src/com/gitblit/wicket/pages/RepositoryPage.java b/src/com/gitblit/wicket/pages/RepositoryPage.java index c84ccb06..5f544012 100644 --- a/src/com/gitblit/wicket/pages/RepositoryPage.java +++ b/src/com/gitblit/wicket/pages/RepositoryPage.java @@ -41,6 +41,7 @@ import org.eclipse.jgit.revwalk.RevCommit; import com.gitblit.Constants;
import com.gitblit.GitBlit;
import com.gitblit.Keys;
+import com.gitblit.PagesServlet;
import com.gitblit.SyndicationServlet;
import com.gitblit.models.RepositoryModel;
import com.gitblit.utils.JGitUtils;
@@ -48,6 +49,7 @@ import com.gitblit.utils.StringUtils; import com.gitblit.utils.TicgitUtils;
import com.gitblit.wicket.GitBlitWebSession;
import com.gitblit.wicket.PageRegistration;
+import com.gitblit.wicket.PageRegistration.OtherPageLink;
import com.gitblit.wicket.WicketUtils;
import com.gitblit.wicket.panels.LinkPanel;
import com.gitblit.wicket.panels.NavigationPanel;
@@ -123,6 +125,12 @@ public abstract class RepositoryPage extends BasePage { if (model.useDocs) {
pages.put("docs", new PageRegistration("gb.docs", DocsPage.class, params));
}
+ if (JGitUtils.getPagesBranch(r) != null) {
+ OtherPageLink pagesLink = new OtherPageLink("gb.pages", PagesServlet.asLink(
+ getRequest().getRelativePathPrefixToContextRoot(), repositoryName, null));
+ pages.put("pages", pagesLink);
+ }
+
// Conditionally add edit link
final boolean showAdmin;
if (GitBlit.getBoolean(Keys.web.authenticateAdminPages, true)) {
@@ -141,9 +149,9 @@ public abstract class RepositoryPage extends BasePage { }
@Override
- protected void setupPage(String repositoryName, String pageName) {
- add(new LinkPanel("repositoryName", null, StringUtils.stripDotGit(repositoryName), SummaryPage.class,
- WicketUtils.newRepositoryParameter(repositoryName)));
+ protected void setupPage(String repositoryName, String pageName) {
+ add(new LinkPanel("repositoryName", null, StringUtils.stripDotGit(repositoryName),
+ SummaryPage.class, WicketUtils.newRepositoryParameter(repositoryName)));
add(new Label("pageName", pageName));
super.setupPage(repositoryName, pageName);
@@ -245,7 +253,8 @@ public abstract class RepositoryPage extends BasePage { }
}
- protected void setPersonSearchTooltip(Component component, String value, Constants.SearchType searchType) {
+ protected void setPersonSearchTooltip(Component component, String value,
+ Constants.SearchType searchType) {
if (searchType.equals(Constants.SearchType.AUTHOR)) {
WicketUtils.setHtmlTooltip(component, getString("gb.searchForAuthor") + " " + value);
} else if (searchType.equals(Constants.SearchType.COMMITTER)) {
@@ -302,13 +311,14 @@ public abstract class RepositoryPage extends BasePage { private final IModel<String> searchBoxModel = new Model<String>("");
- private final IModel<Constants.SearchType> searchTypeModel = new Model<Constants.SearchType>(Constants.SearchType.COMMIT);
+ private final IModel<Constants.SearchType> searchTypeModel = new Model<Constants.SearchType>(
+ Constants.SearchType.COMMIT);
public SearchForm(String id, String repositoryName) {
super(id);
this.repositoryName = repositoryName;
- DropDownChoice<Constants.SearchType> searchType = new DropDownChoice<Constants.SearchType>("searchType",
- Arrays.asList(Constants.SearchType.values()));
+ DropDownChoice<Constants.SearchType> searchType = new DropDownChoice<Constants.SearchType>(
+ "searchType", Arrays.asList(Constants.SearchType.values()));
searchType.setModel(searchTypeModel);
add(searchType.setVisible(GitBlit.getBoolean(Keys.web.showSearchTypeSelection, false)));
TextField<String> searchBox = new TextField<String>("searchBox", searchBoxModel);
diff --git a/src/com/gitblit/wicket/panels/LinkPanel.java b/src/com/gitblit/wicket/panels/LinkPanel.java index 2872d4bf..16b8cd46 100644 --- a/src/com/gitblit/wicket/panels/LinkPanel.java +++ b/src/com/gitblit/wicket/panels/LinkPanel.java @@ -20,6 +20,7 @@ import org.apache.wicket.behavior.SimpleAttributeModifier; import org.apache.wicket.markup.html.WebPage;
import org.apache.wicket.markup.html.basic.Label;
import org.apache.wicket.markup.html.link.BookmarkablePageLink;
+import org.apache.wicket.markup.html.link.ExternalLink;
import org.apache.wicket.markup.html.link.Link;
import org.apache.wicket.markup.html.panel.Panel;
import org.apache.wicket.model.IModel;
@@ -71,4 +72,23 @@ public class LinkPanel extends Panel { add(link);
}
+ public LinkPanel(String wicketId, String linkCssClass, String label, String href) {
+ this(wicketId, linkCssClass, label, href, false);
+ }
+
+ public LinkPanel(String wicketId, String linkCssClass, String label, String href,
+ boolean newWindow) {
+ super(wicketId);
+ this.labelModel = new Model<String>(label);
+ ExternalLink link = new ExternalLink("link", href);
+ if (newWindow) {
+ link.add(new SimpleAttributeModifier("target", "_blank"));
+ }
+ if (linkCssClass != null) {
+ link.add(new SimpleAttributeModifier("class", linkCssClass));
+ }
+ link.add(new Label("label", labelModel));
+ add(link);
+ }
+
}
diff --git a/src/com/gitblit/wicket/panels/NavigationPanel.java b/src/com/gitblit/wicket/panels/NavigationPanel.java index 018bbb2f..57c82e80 100644 --- a/src/com/gitblit/wicket/panels/NavigationPanel.java +++ b/src/com/gitblit/wicket/panels/NavigationPanel.java @@ -25,6 +25,7 @@ import org.apache.wicket.markup.repeater.data.ListDataProvider; import com.gitblit.wicket.PageRegistration;
import com.gitblit.wicket.PageRegistration.DropDownMenuRegistration;
+import com.gitblit.wicket.PageRegistration.OtherPageLink;
import com.gitblit.wicket.WicketUtils;
import com.gitblit.wicket.pages.BasePage;
@@ -43,7 +44,12 @@ public class NavigationPanel extends Panel { public void populateItem(final Item<PageRegistration> item) {
PageRegistration entry = item.getModelObject();
- if (entry instanceof DropDownMenuRegistration) {
+ if (entry instanceof OtherPageLink) {
+ // other link
+ OtherPageLink link = (OtherPageLink) entry;
+ Component c = new LinkPanel("link", null, getString(entry.translationKey), link.url);
+ item.add(c);
+ } else if (entry instanceof DropDownMenuRegistration) {
// drop down menu
DropDownMenuRegistration reg = (DropDownMenuRegistration) entry;
Component c = new DropDownMenu("link", getString(entry.translationKey), reg);
diff --git a/tests/com/gitblit/tests/GitBlitSuite.java b/tests/com/gitblit/tests/GitBlitSuite.java index f697c178..71947e14 100644 --- a/tests/com/gitblit/tests/GitBlitSuite.java +++ b/tests/com/gitblit/tests/GitBlitSuite.java @@ -82,6 +82,14 @@ public class GitBlitSuite { return new FileRepository(new File(REPOSITORIES, "test/bluez-gnome.git"));
}
+ public static Repository getAmbitionRepository() throws Exception {
+ return new FileRepository(new File(REPOSITORIES, "test/ambition.git"));
+ }
+
+ public static Repository getTheoreticalPhysicsRepository() throws Exception {
+ return new FileRepository(new File(REPOSITORIES, "test/theoretical-physics.git"));
+ }
+
public static boolean startGitblit() throws Exception {
if (started.get()) {
// already started
@@ -123,7 +131,9 @@ public class GitBlitSuite { "https://git.kernel.org/pub/scm/bluetooth/bluez-gnome.git");
cloneOrFetch("test/jgit.git", "https://github.com/eclipse/jgit.git");
cloneOrFetch("test/helloworld.git", "https://github.com/git/hello-world.git");
-
+ cloneOrFetch("test/ambition.git", "https://github.com/defunkt/ambition.git");
+ cloneOrFetch("test/theoretical-physics.git", "https://github.com/certik/theoretical-physics.git");
+
enableTickets("ticgit.git");
enableDocs("ticgit.git");
showRemoteBranches("ticgit.git");
|