diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/AbstractHttpFilter.java b/gitiles-servlet/src/main/java/com/google/gitiles/AbstractHttpFilter.java
new file mode 100644
index 0000000..092e12d
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/AbstractHttpFilter.java
@@ -0,0 +1,49 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import java.io.IOException;
+
+import javax.servlet.Filter;
+import javax.servlet.FilterChain;
+import javax.servlet.FilterConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+abstract class AbstractHttpFilter implements Filter {
+  @Override
+  public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
+      throws IOException, ServletException {
+    doFilter((HttpServletRequest) req, (HttpServletResponse) res, chain);
+  }
+
+  @Override
+  @SuppressWarnings("unused") // Allow subclasses to throw ServletException.
+  public void init(FilterConfig config) throws ServletException {
+    // Default implementation does nothing.
+  }
+
+  @Override
+  public void destroy() {
+    // Default implementation does nothing.
+  }
+
+  /** @see #doFilter(ServletRequest, ServletResponse, FilterChain) */
+  public abstract void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain)
+      throws IOException, ServletException;
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/BaseServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/BaseServlet.java
new file mode 100644
index 0000000..70dc14e
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/BaseServlet.java
@@ -0,0 +1,119 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+
+import com.google.common.base.Charsets;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Maps;
+import com.google.common.net.HttpHeaders;
+
+import org.joda.time.Instant;
+
+import java.io.IOException;
+import java.util.Map;
+
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Base servlet class for Gitiles servlets that serve Soy templates. */
+public abstract class BaseServlet extends HttpServlet {
+  private static final String DATA_ATTRIBUTE = BaseServlet.class.getName() + "/Data";
+
+  static void setNotCacheable(HttpServletResponse res) {
+    res.setHeader(HttpHeaders.CACHE_CONTROL, "no-cache, no-store, max-age=0, must-revalidate");
+    res.setHeader(HttpHeaders.PRAGMA, "no-cache");
+    res.setHeader(HttpHeaders.EXPIRES, "Fri, 01 Jan 1990 00:00:00 GMT");
+    res.setDateHeader(HttpHeaders.DATE, new Instant().getMillis());
+  }
+
+  public static BaseServlet notFoundServlet() {
+    return new BaseServlet(null) {
+      @Override
+      public void service(HttpServletRequest req, HttpServletResponse res) {
+        res.setStatus(SC_NOT_FOUND);
+      }
+    };
+  }
+
+  public static Map<String, String> menuEntry(String text, String url) {
+    if (url != null) {
+      return ImmutableMap.of("text", text, "url", url);
+    } else {
+      return ImmutableMap.of("text", text);
+    }
+  }
+
+  protected static Map<String, Object> getData(HttpServletRequest req) {
+    @SuppressWarnings("unchecked")
+    Map<String, Object> data = (Map<String, Object>) req.getAttribute(DATA_ATTRIBUTE);
+    if (data == null) {
+      data = Maps.newHashMap();
+      req.setAttribute(DATA_ATTRIBUTE, data);
+    }
+    return data;
+  }
+
+  protected final Renderer renderer;
+
+  protected BaseServlet(Renderer renderer) {
+    this.renderer = renderer;
+  }
+
+  /**
+   * Put a value into a request's Soy data map.
+   * <p>
+   * This method is intended to support a composition pattern whereby a
+   * {@link BaseServlet} is wrapped in a different {@link HttpServlet} that can
+   * update its data map.
+   *
+   * @param req in-progress request.
+   * @param key key.
+   * @param value Soy data value.
+   */
+  public void put(HttpServletRequest req, String key, Object value) {
+    getData(req).put(key, value);
+  }
+
+  protected void render(HttpServletRequest req, HttpServletResponse res, String templateName,
+      Map<String, ?> soyData) throws IOException {
+    try {
+      res.setContentType(FormatType.HTML.getMimeType());
+      res.setCharacterEncoding(Charsets.UTF_8.name());
+      setCacheHeaders(req, res);
+
+      Map<String, Object> allData = getData(req);
+      allData.putAll(soyData);
+      GitilesView view = ViewFilter.getView(req);
+      if (!allData.containsKey("repositoryName") && view.getRepositoryName() != null) {
+        allData.put("repositoryName", view.getRepositoryName());
+      }
+      if (!allData.containsKey("breadcrumbs")) {
+        allData.put("breadcrumbs", view.getBreadcrumbs());
+      }
+
+      res.setStatus(HttpServletResponse.SC_OK);
+      renderer.render(res, templateName, allData);
+    } finally {
+      req.removeAttribute(DATA_ATTRIBUTE);
+    }
+  }
+
+  protected void setCacheHeaders(HttpServletRequest req, HttpServletResponse res) {
+    setNotCacheable(res);
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/BlobSoyData.java b/gitiles-servlet/src/main/java/com/google/gitiles/BlobSoyData.java
new file mode 100644
index 0000000..6b57cbc
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/BlobSoyData.java
@@ -0,0 +1,109 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static org.eclipse.jgit.lib.Constants.OBJ_COMMIT;
+
+import com.google.common.collect.Maps;
+
+import org.eclipse.jgit.diff.RawText;
+import org.eclipse.jgit.errors.LargeObjectException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.ObjectLoader;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.eclipse.jgit.util.RawParseUtils;
+
+import java.io.IOException;
+import java.util.Map;
+
+/** Soy data converter for git blobs. */
+public class BlobSoyData {
+  /**
+   * Maximum number of bytes to load from a supposed text file for display.
+   * Files larger than this will be displayed as binary files, even if the
+   * contents was text. For example really big XML files may be above this limit
+   * and will get displayed as binary.
+   */
+  private static final int MAX_FILE_SIZE = 10 << 20;
+
+  private final GitilesView view;
+  private final RevWalk walk;
+
+  public BlobSoyData(RevWalk walk, GitilesView view) {
+    this.view = view;
+    this.walk = walk;
+  }
+
+  public Map<String, Object> toSoyData(ObjectId blobId)
+      throws MissingObjectException, IOException {
+    return toSoyData(null, blobId);
+  }
+
+  public Map<String, Object> toSoyData(String path, ObjectId blobId)
+      throws MissingObjectException, IOException {
+    Map<String, Object> data = Maps.newHashMapWithExpectedSize(4);
+    data.put("sha", ObjectId.toString(blobId));
+
+    ObjectLoader loader = walk.getObjectReader().open(blobId, Constants.OBJ_BLOB);
+    String content;
+    try {
+      byte[] raw = loader.getCachedBytes(MAX_FILE_SIZE);
+      content = !RawText.isBinary(raw) ? RawParseUtils.decode(raw) : null;
+    } catch (LargeObjectException.OutOfMemory e) {
+      throw e;
+    } catch (LargeObjectException e) {
+      content = null;
+    }
+
+    data.put("data", content);
+    if (content != null) {
+      data.put("lang", guessPrettifyLang(path, content));
+    } else if (content == null) {
+      data.put("size", Long.toString(loader.getSize()));
+    }
+    if (path != null && view.getRevision().getPeeledType() == OBJ_COMMIT) {
+      data.put("logUrl", GitilesView.log().copyFrom(view).toUrl());
+    }
+    return data;
+  }
+
+  private static String guessPrettifyLang(String path, String content) {
+    if (content.startsWith("#!/bin/sh") || content.startsWith("#!/bin/bash")) {
+      return "sh";
+    } else if (content.startsWith("#!/usr/bin/perl")) {
+      return "perl";
+    } else if (content.startsWith("#!/usr/bin/python")) {
+      return "py";
+    } else if (path == null) {
+      return null;
+    }
+
+    int slash = path.lastIndexOf('/');
+    int dot = path.lastIndexOf('.');
+    String lang = ((0 < dot) && (slash < dot)) ? path.substring(dot + 1) : null;
+    if ("txt".equalsIgnoreCase(lang)) {
+      return null;
+    } else if ("mk".equalsIgnoreCase(lang)) {
+      return "sh";
+    } else if ("Makefile".equalsIgnoreCase(path)
+        || ((0 < slash) && "Makefile".equalsIgnoreCase(path.substring(slash + 1)))) {
+      return "sh";
+    } else {
+      return lang;
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/CommitSoyData.java b/gitiles-servlet/src/main/java/com/google/gitiles/CommitSoyData.java
new file mode 100644
index 0000000..9f8a97d
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/CommitSoyData.java
@@ -0,0 +1,287 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
+import com.google.template.soy.data.restricted.NullData;
+
+import org.eclipse.jgit.diff.DiffEntry;
+import org.eclipse.jgit.diff.DiffEntry.ChangeType;
+import org.eclipse.jgit.diff.DiffFormatter;
+import org.eclipse.jgit.lib.AnyObjectId;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.ObjectReader;
+import org.eclipse.jgit.lib.PersonIdent;
+import org.eclipse.jgit.lib.Ref;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.eclipse.jgit.treewalk.AbstractTreeIterator;
+import org.eclipse.jgit.treewalk.CanonicalTreeParser;
+import org.eclipse.jgit.treewalk.EmptyTreeIterator;
+import org.eclipse.jgit.util.GitDateFormatter;
+import org.eclipse.jgit.util.GitDateFormatter.Format;
+import org.eclipse.jgit.util.RelativeDateFormatter;
+import org.eclipse.jgit.util.io.NullOutputStream;
+
+import java.io.IOException;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import javax.annotation.Nullable;
+import javax.servlet.http.HttpServletRequest;
+
+/** Soy data converter for git commits. */
+public class CommitSoyData {
+  /** Valid sets of keys to include in Soy data for commits. */
+  public static enum KeySet {
+    DETAIL("author", "committer", "sha", "tree", "treeUrl", "parents", "message", "logUrl"),
+    DETAIL_DIFF_TREE(DETAIL, "diffTree"),
+    SHORTLOG("abbrevSha", "url", "shortMessage", "author", "branches", "tags"),
+    DEFAULT(DETAIL);
+
+    private final Set<String> keys;
+
+    private KeySet(String... keys) {
+      this.keys = ImmutableSet.copyOf(keys);
+    }
+
+    private KeySet(KeySet other, String... keys) {
+      this.keys = ImmutableSet.<String> builder().addAll(other.keys).add(keys).build();
+    }
+  }
+
+  private final Linkifier linkifier;
+  private final HttpServletRequest req;
+  private final Repository repo;
+  private final RevWalk walk;
+  private final GitilesView view;
+  private final Map<AnyObjectId, Set<Ref>> refsById;
+  private final GitDateFormatter dateFormatter;
+
+  // TODO(dborowitz): This constructor is getting a bit ridiculous.
+  public CommitSoyData(@Nullable Linkifier linkifier, HttpServletRequest req, Repository repo,
+      RevWalk walk, GitilesView view) {
+    this(linkifier, req, repo, walk, view, null);
+  }
+
+  public CommitSoyData(@Nullable Linkifier linkifier, HttpServletRequest req, Repository repo,
+      RevWalk walk, GitilesView view, @Nullable Map<AnyObjectId, Set<Ref>> refsById) {
+    this.linkifier = linkifier;
+    this.req = req;
+    this.repo = repo;
+    this.walk = walk;
+    this.view = view;
+    this.refsById = refsById;
+    this.dateFormatter = new GitDateFormatter(Format.DEFAULT);
+  }
+
+  public Map<String, Object> toSoyData(RevCommit commit, KeySet keys) throws IOException {
+    Map<String, Object> data = Maps.newHashMapWithExpectedSize(KeySet.DEFAULT.keys.size());
+    if (keys.keys.contains("author")) {
+      data.put("author", toSoyData(commit.getAuthorIdent(), dateFormatter));
+    }
+    if (keys.keys.contains("committer")) {
+      data.put("committer", toSoyData(commit.getCommitterIdent(), dateFormatter));
+    }
+    if (keys.keys.contains("sha")) {
+      data.put("sha", ObjectId.toString(commit));
+    }
+    if (keys.keys.contains("abbrevSha")) {
+      ObjectReader reader = repo.getObjectDatabase().newReader();
+      try {
+        data.put("abbrevSha", reader.abbreviate(commit).name());
+      } finally {
+        reader.release();
+      }
+    }
+    if (keys.keys.contains("url")) {
+      data.put("url", GitilesView.revision()
+          .copyFrom(view)
+          .setRevision(commit)
+          .toUrl());
+    }
+    if (keys.keys.contains("logUrl")) {
+      Revision rev = view.getRevision();
+      GitilesView.Builder logView = GitilesView.log()
+          .copyFrom(view)
+          .setRevision(rev.getId().equals(commit) ? rev.getName() : commit.name(), commit)
+          .setOldRevision(Revision.NULL)
+          .setTreePath(null);
+      data.put("logUrl", logView.toUrl());
+    }
+    if (keys.keys.contains("tree")) {
+      data.put("tree", ObjectId.toString(commit.getTree()));
+    }
+    if (keys.keys.contains("treeUrl")) {
+      data.put("treeUrl", GitilesView.path().copyFrom(view).setTreePath("/").toUrl());
+    }
+    if (keys.keys.contains("parents")) {
+      data.put("parents", toSoyData(view, commit.getParents()));
+    }
+    if (keys.keys.contains("shortMessage")) {
+      data.put("shortMessage", commit.getShortMessage());
+    }
+    if (keys.keys.contains("branches")) {
+      data.put("branches", getRefsById(commit, Constants.R_HEADS));
+    }
+    if (keys.keys.contains("tags")) {
+      data.put("tags", getRefsById(commit, Constants.R_TAGS));
+    }
+    if (keys.keys.contains("message")) {
+      if (linkifier != null) {
+        data.put("message", linkifier.linkify(req, commit.getFullMessage()));
+      } else {
+        data.put("message", commit.getFullMessage());
+      }
+    }
+    if (keys.keys.contains("diffTree")) {
+      data.put("diffTree", computeDiffTree(commit));
+    }
+    checkState(keys.keys.size() == data.size(), "bad commit data keys: %s != %s", keys.keys,
+        data.keySet());
+    return ImmutableMap.copyOf(data);
+  }
+
+  public Map<String, Object> toSoyData(RevCommit commit) throws IOException {
+    return toSoyData(commit, KeySet.DEFAULT);
+  }
+
+  // TODO(dborowitz): Extract this.
+  static Map<String, String> toSoyData(PersonIdent ident, GitDateFormatter dateFormatter) {
+    return ImmutableMap.of(
+        "name", ident.getName(),
+        "email", ident.getEmailAddress(),
+        "time", dateFormatter.formatDate(ident),
+        // TODO(dborowitz): Switch from relative to absolute at some threshold.
+        "relativeTime", RelativeDateFormatter.format(ident.getWhen()));
+  }
+
+  private List<Map<String, String>> toSoyData(GitilesView view, RevCommit[] parents) {
+    List<Map<String, String>> result = Lists.newArrayListWithCapacity(parents.length);
+    int i = 1;
+    // TODO(dborowitz): Render something slightly different when we're actively
+    // viewing a diff against one of the parents.
+    for (RevCommit parent : parents) {
+      String name = parent.name();
+      GitilesView.Builder diff = GitilesView.diff().copyFrom(view).setTreePath("");
+      String parentName;
+      if (parents.length == 1) {
+        parentName = view.getRevision().getName() + "^";
+      } else {
+        parentName = view.getRevision().getName() + "^" + (i++);
+      }
+      result.add(ImmutableMap.of(
+          "sha", name,
+          "url", GitilesView.revision()
+              .copyFrom(view)
+              .setRevision(parentName, parent)
+              .toUrl(),
+          "diffUrl", diff.setOldRevision(parentName, parent).toUrl()));
+    }
+    return result;
+  }
+
+  private AbstractTreeIterator getTreeIterator(RevWalk walk, RevCommit commit) throws IOException {
+    CanonicalTreeParser p = new CanonicalTreeParser();
+    p.reset(walk.getObjectReader(), walk.parseTree(walk.parseCommit(commit).getTree()));
+    return p;
+  }
+
+  private Object computeDiffTree(RevCommit commit) throws IOException {
+    AbstractTreeIterator oldTree;
+    GitilesView.Builder diffUrl = GitilesView.diff().copyFrom(view)
+        .setTreePath("");
+    switch (commit.getParentCount()) {
+      case 0:
+        oldTree = new EmptyTreeIterator();
+        diffUrl.setOldRevision(Revision.NULL);
+        break;
+      case 1:
+        oldTree = getTreeIterator(walk, commit.getParent(0));
+        diffUrl.setOldRevision(view.getRevision().getName() + "^", commit.getParent(0));
+        break;
+      default:
+        // TODO(dborowitz): handle merges
+        return NullData.INSTANCE;
+    }
+    AbstractTreeIterator newTree = getTreeIterator(walk, commit);
+
+    DiffFormatter diff = new DiffFormatter(NullOutputStream.INSTANCE);
+    try {
+      diff.setRepository(repo);
+      diff.setDetectRenames(true);
+
+      List<Object> result = Lists.newArrayList();
+      for (DiffEntry e : diff.scan(oldTree, newTree)) {
+        Map<String, Object> entry = Maps.newHashMapWithExpectedSize(5);
+        entry.put("path", e.getNewPath());
+        entry.put("url", GitilesView.path()
+            .copyFrom(view)
+            .setTreePath(e.getNewPath())
+            .toUrl());
+        entry.put("diffUrl", diffUrl.setAnchor("F" + result.size()).toUrl());
+        entry.put("changeType", e.getChangeType().toString());
+        if (e.getChangeType() == ChangeType.COPY || e.getChangeType() == ChangeType.RENAME) {
+          entry.put("oldPath", e.getOldPath());
+        }
+        result.add(entry);
+      }
+      return result;
+    } finally {
+      diff.release();
+    }
+  }
+
+  private static final Comparator<Map<String, String>> NAME_COMPARATOR =
+      new Comparator<Map<String, String>>() {
+        @Override
+        public int compare(Map<String, String> o1, Map<String, String> o2) {
+          return o1.get("name").compareTo(o2.get("name"));
+        }
+      };
+
+  private List<Map<String, String>> getRefsById(ObjectId id, String prefix) {
+    checkNotNull(refsById, "must pass in ID to ref map to look up refs by ID");
+    Set<Ref> refs = refsById.get(id);
+    if (refs == null) {
+      return ImmutableList.of();
+    }
+    List<Map<String, String>> result = Lists.newArrayListWithCapacity(refs.size());
+    for (Ref ref : refs) {
+      if (ref.getName().startsWith(prefix)) {
+        result.add(ImmutableMap.of(
+          "name", ref.getName().substring(prefix.length()),
+          "url", GitilesView.revision()
+              .copyFrom(view)
+              .setRevision(Revision.unpeeled(ref.getName(), ref.getObjectId()))
+              .toUrl()));
+      }
+    }
+    Collections.sort(result, NAME_COMPARATOR);
+    return result;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/ConfigUtil.java b/gitiles-servlet/src/main/java/com/google/gitiles/ConfigUtil.java
new file mode 100644
index 0000000..4f8733b
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/ConfigUtil.java
@@ -0,0 +1,141 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import com.google.common.base.Predicates;
+import com.google.common.cache.CacheBuilder;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.Iterables;
+
+import org.eclipse.jgit.lib.Config;
+import org.joda.time.Duration;
+
+import java.util.concurrent.TimeUnit;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/** Utilities for working with {@link Config} objects. */
+public class ConfigUtil {
+  /**
+   * Read a duration value from the configuration.
+   * <p>
+   * Durations can be written as expressions, for example {@code "1 s"} or
+   * {@code "5 days"}. If units are not specified, milliseconds are assumed.
+   *
+   * @param config JGit config object.
+   * @param section section to read, e.g. "google"
+   * @param subsection subsection to read, e.g. "bigtable"
+   * @param name variable to read, e.g. "deadline".
+   * @param defaultValue value to use when the value is not assigned.
+   * @return a standard duration representing the time read, or defaultValue.
+   */
+  public static Duration getDuration(Config config, String section, String subsection, String name,
+      Duration defaultValue) {
+    String valStr = config.getString(section, subsection, name);
+    if (valStr == null) {
+        return defaultValue;
+    }
+
+    valStr = valStr.trim();
+    if (valStr.length() == 0) {
+        return defaultValue;
+    }
+
+    Matcher m = matcher("^([1-9][0-9]*(?:\\.[0-9]*)?)\\s*(.*)$", valStr);
+    if (!m.matches()) {
+      String key = section + (subsection != null ? "." + subsection : "") + "." + name;
+      throw new IllegalStateException("Not time unit: " + key + " = " + valStr);
+    }
+
+    String digits = m.group(1);
+    String unitName = m.group(2).trim();
+
+    TimeUnit unit;
+    if ("".equals(unitName)) {
+      unit = TimeUnit.MILLISECONDS;
+    } else if (anyOf(unitName, "ms", "millis", "millisecond", "milliseconds")) {
+      unit = TimeUnit.MILLISECONDS;
+    } else if (anyOf(unitName, "s", "sec", "second", "seconds")) {
+      unit = TimeUnit.SECONDS;
+    } else if (anyOf(unitName, "m", "min", "minute", "minutes")) {
+      unit = TimeUnit.MINUTES;
+    } else if (anyOf(unitName, "h", "hr", "hour", "hours")) {
+      unit = TimeUnit.HOURS;
+    } else if (anyOf(unitName, "d", "day", "days")) {
+      unit = TimeUnit.DAYS;
+    } else {
+      String key = section + (subsection != null ? "." + subsection : "") + "." + name;
+      throw new IllegalStateException("Not time unit: " + key + " = " + valStr);
+    }
+
+    try {
+      if (digits.indexOf('.') == -1) {
+        long val = Long.parseLong(digits);
+        return new Duration(val * TimeUnit.MILLISECONDS.convert(1, unit));
+      } else {
+        double val = Double.parseDouble(digits);
+        return new Duration((long) (val * TimeUnit.MILLISECONDS.convert(1, unit)));
+      }
+    } catch (NumberFormatException nfe) {
+      String key = section + (subsection != null ? "." + subsection : "") + "." + name;
+      throw new IllegalStateException("Not time unit: " + key + " = " + valStr, nfe);
+    }
+  }
+
+  /**
+   * Get a {@link CacheBuilder} from a config.
+   *
+   * @param config JGit config object.
+   * @param name name of the cache subsection under the "cache" section.
+   * @return a new cache builder.
+   */
+  public static CacheBuilder<Object, Object> getCacheBuilder(Config config, String name) {
+    CacheBuilder<Object, Object> b = CacheBuilder.newBuilder();
+    try {
+      if (config.getString("cache", name, "maximumWeight") != null) {
+        b.maximumWeight(config.getLong("cache", name, "maximumWeight", 20 << 20));
+      }
+      if (config.getString("cache", name, "maximumSize") != null) {
+        b.maximumSize(config.getLong("cache", name, "maximumSize", 16384));
+      }
+      Duration expireAfterWrite = getDuration(config, "cache", name, "expireAfterWrite", null);
+      if (expireAfterWrite != null) {
+        b.expireAfterWrite(expireAfterWrite.getMillis(), TimeUnit.MILLISECONDS);
+      }
+      Duration expireAfterAccess = getDuration(config, "cache", name, "expireAfterAccess", null);
+      if (expireAfterAccess != null) {
+        b.expireAfterAccess(expireAfterAccess.getMillis(), TimeUnit.MILLISECONDS);
+      }
+      // Add other methods as needed.
+    } catch (IllegalArgumentException e) {
+      throw new IllegalArgumentException("Error getting CacheBuilder for " + name, e);
+    } catch (IllegalStateException e) {
+      throw new IllegalStateException("Error getting CacheBuilder for " + name, e);
+    }
+    return b;
+  }
+
+  private static Matcher matcher(String pattern, String valStr) {
+      return Pattern.compile(pattern).matcher(valStr);
+  }
+
+  private static boolean anyOf(String a, String... cases) {
+    return Iterables.any(ImmutableList.copyOf(cases),
+        Predicates.equalTo(a.toLowerCase()));
+  }
+
+  private ConfigUtil() {
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/DebugRenderer.java b/gitiles-servlet/src/main/java/com/google/gitiles/DebugRenderer.java
new file mode 100644
index 0000000..e56518a
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/DebugRenderer.java
@@ -0,0 +1,57 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkState;
+
+import com.google.common.base.Function;
+import com.google.common.collect.ImmutableMap;
+import com.google.template.soy.SoyFileSet;
+import com.google.template.soy.tofu.SoyTofu;
+
+import java.io.File;
+import java.net.URISyntaxException;
+import java.net.URL;
+
+/** Renderer that reloads Soy templates from the filesystem on every request. */
+public class DebugRenderer extends Renderer {
+  public DebugRenderer(String staticPrefix, String customTemplatesFilename,
+      final String soyTemplatesRoot) {
+    super(
+        new Function<String, URL>() {
+          @Override
+          public URL apply(String name) {
+            return toFileURL(soyTemplatesRoot + File.separator + name);
+          }
+        },
+        ImmutableMap.<String, String> of(), staticPrefix,
+        toFileURL(customTemplatesFilename));
+  }
+
+  @Override
+  protected SoyTofu getTofu() {
+    SoyFileSet.Builder builder = new SoyFileSet.Builder()
+        .setCompileTimeGlobals(globals);
+    for (URL template : templates) {
+      try {
+        checkState(new File(template.toURI()).exists(), "Missing Soy template %s", template);
+      } catch (URISyntaxException e) {
+        throw new IllegalStateException(e);
+      }
+      builder.add(template);
+    }
+    return builder.build().compileToTofu();
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/DefaultAccess.java b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultAccess.java
new file mode 100644
index 0000000..5b6d822
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultAccess.java
@@ -0,0 +1,239 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
+import com.google.common.collect.Queues;
+
+import org.eclipse.jgit.errors.ConfigInvalidException;
+import org.eclipse.jgit.errors.RepositoryNotFoundException;
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.Ref;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.lib.StoredConfig;
+import org.eclipse.jgit.transport.resolver.FileResolver;
+import org.eclipse.jgit.transport.resolver.ServiceNotEnabledException;
+import org.eclipse.jgit.util.IO;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.Queue;
+import java.util.Set;
+
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * Default implementation of {@link GitilesAccess} with local repositories.
+ * <p>
+ * Repositories are scanned on-demand under the given path, configured by
+ * default from {@code gitiles.basePath}. There is no access control beyond what
+ * user the JVM is running under.
+ */
+public class DefaultAccess implements GitilesAccess {
+  private static final String ANONYMOUS_USER_KEY = "anonymous user";
+
+  public static class Factory implements GitilesAccess.Factory {
+    private final File basePath;
+    private final String canonicalBasePath;
+    private final String baseGitUrl;
+    private final FileResolver<HttpServletRequest> resolver;
+
+    Factory(File basePath, String baseGitUrl, FileResolver<HttpServletRequest> resolver)
+        throws IOException {
+      this.basePath = checkNotNull(basePath, "basePath");
+      this.baseGitUrl = checkNotNull(baseGitUrl, "baseGitUrl");
+      this.resolver = checkNotNull(resolver, "resolver");
+      this.canonicalBasePath = basePath.getCanonicalPath();
+    }
+
+    @Override
+    public GitilesAccess forRequest(HttpServletRequest req) {
+      String path = req.getPathInfo();
+      String repositoryPath;
+      if (path == null || path == "/") {
+        repositoryPath = null;
+      } else {
+        int slashPlus = path.indexOf("/+/");
+        if (slashPlus >= 0) {
+          repositoryPath = path.substring(0, slashPlus);
+        } else if (path.endsWith("/+")) {
+          repositoryPath = path.substring(0, path.length() - 2);
+        } else {
+          repositoryPath = path;
+        }
+      }
+      return newAccess(basePath, canonicalBasePath, baseGitUrl, resolver, req);
+    }
+
+    protected DefaultAccess newAccess(File basePath, String canonicalBasePath, String baseGitUrl,
+        FileResolver<HttpServletRequest> resolver, HttpServletRequest req) {
+      return new DefaultAccess(basePath, canonicalBasePath, baseGitUrl, resolver, req);
+    }
+  }
+
+  protected final File basePath;
+  protected final String canonicalBasePath;
+  protected final String baseGitUrl;
+  protected final FileResolver<HttpServletRequest> resolver;
+  protected final HttpServletRequest req;
+
+  protected DefaultAccess(File basePath, String canonicalBasePath, String baseGitUrl,
+      FileResolver<HttpServletRequest> resolver, HttpServletRequest req) {
+    this.basePath = checkNotNull(basePath, "basePath");
+    this.canonicalBasePath = checkNotNull(canonicalBasePath, "canonicalBasePath");
+    this.baseGitUrl = checkNotNull(baseGitUrl, "baseGitUrl");
+    this.resolver = checkNotNull(resolver, "resolver");
+    this.req = checkNotNull(req, "req");
+  }
+
+  @Override
+  public Map<String, RepositoryDescription> listRepositories(Set<String> branches)
+      throws IOException {
+    Map<String, RepositoryDescription> repos = Maps.newTreeMap();
+    for (Repository repo : scanRepositories(basePath, req)) {
+      repos.put(getRepositoryName(repo), buildDescription(repo, branches));
+      repo.close();
+    }
+    return repos;
+  }
+
+  @Override
+  public Object getUserKey() {
+    // Always return the same anonymous user key (effectively running with the
+    // same user permissions as the JVM). Subclasses may override this behavior.
+    return ANONYMOUS_USER_KEY;
+  }
+
+  @Override
+  public String getRepositoryName() {
+    return getRepositoryName(ServletUtils.getRepository(req));
+  }
+
+  @Override
+  public RepositoryDescription getRepositoryDescription() throws IOException {
+    return buildDescription(ServletUtils.getRepository(req), Collections.<String> emptySet());
+  }
+
+  private String getRepositoryName(Repository repo) {
+    String path = getRelativePath(repo);
+    if (repo.isBare() && path.endsWith(".git")) {
+      path = path.substring(0, path.length() - 4);
+    }
+    return path;
+  }
+
+  private String getRelativePath(Repository repo) {
+    String path = repo.isBare() ? repo.getDirectory().getPath() : repo.getDirectory().getParent();
+    if (repo.isBare()) {
+      path = repo.getDirectory().getPath();
+      if (path.endsWith(".git")) {
+        path = path.substring(0, path.length() - 4);
+      }
+    } else {
+      path = repo.getDirectory().getParent();
+    }
+    return getRelativePath(path);
+  }
+
+  private String getRelativePath(String path) {
+    String base = basePath.getPath();
+    if (path.startsWith(base)) {
+      return path.substring(base.length() + 1);
+    }
+    if (path.startsWith(canonicalBasePath)) {
+      return path.substring(canonicalBasePath.length() + 1);
+    }
+    throw new IllegalStateException(String.format(
+          "Repository path %s is outside base path %s", path, base));
+  }
+
+  private String loadDescriptionText(Repository repo) throws IOException {
+    String desc = null;
+    StoredConfig config = repo.getConfig();
+    IOException configError = null;
+    try {
+      config.load();
+      desc = config.getString("gitweb", null, "description");
+    } catch (ConfigInvalidException e) {
+      configError = new IOException(e);
+    }
+    if (desc == null) {
+      File descFile = new File(repo.getDirectory(), "description");
+      if (descFile.exists()) {
+        desc = new String(IO.readFully(descFile));
+      } else if (configError != null) {
+        throw configError;
+      }
+    }
+    return desc;
+  }
+
+  private RepositoryDescription buildDescription(Repository repo, Set<String> branches)
+      throws IOException {
+    RepositoryDescription desc = new RepositoryDescription();
+    desc.name = getRepositoryName(repo);
+    desc.cloneUrl = baseGitUrl + getRelativePath(repo);
+    desc.description = loadDescriptionText(repo);
+    if (!branches.isEmpty()) {
+      desc.branches = Maps.newLinkedHashMap();
+      for (String name : branches) {
+        Ref ref = repo.getRef(normalizeRefName(name));
+        if ((ref != null) && (ref.getObjectId() != null)) {
+          desc.branches.put(name, ref.getObjectId().name());
+        }
+      }
+    }
+    return desc;
+  }
+
+  private static String normalizeRefName(String name) {
+    if (name.startsWith("refs/")) {
+      return name;
+    }
+    return "refs/heads/" + name;
+  }
+
+  private Collection<Repository> scanRepositories(final File basePath, final HttpServletRequest req) throws IOException {
+    List<Repository> repos = Lists.newArrayList();
+    Queue<File> todo = Queues.newArrayDeque();
+    File[] baseFiles = basePath.listFiles();
+    if (baseFiles == null) {
+      throw new IOException("base path is not a directory: " + basePath.getPath());
+    }
+    todo.addAll(Arrays.asList(baseFiles));
+    while (!todo.isEmpty()) {
+      File file = todo.remove();
+      try {
+        repos.add(resolver.open(req, getRelativePath(file.getPath())));
+      } catch (RepositoryNotFoundException e) {
+        File[] children = file.listFiles();
+        if (children != null) {
+          todo.addAll(Arrays.asList(children));
+        }
+      } catch (ServiceNotEnabledException e) {
+        throw new IOException(e);
+      }
+    }
+    return repos;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/DefaultRenderer.java b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultRenderer.java
new file mode 100644
index 0000000..f4bd1fb
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultRenderer.java
@@ -0,0 +1,59 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import com.google.common.base.Function;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.io.Resources;
+import com.google.template.soy.SoyFileSet;
+import com.google.template.soy.tofu.SoyTofu;
+
+import java.net.URL;
+import java.util.Map;
+
+/** Renderer that precompiles Soy and uses static precompiled CSS. */
+public class DefaultRenderer extends Renderer {
+  private final SoyTofu tofu;
+
+  DefaultRenderer() {
+    this("", null);
+  }
+
+  public DefaultRenderer(String staticPrefix, URL customTemplates) {
+    this(ImmutableMap.<String, String> of(), staticPrefix, customTemplates);
+  }
+
+  public DefaultRenderer(Map<String, String> globals, String staticPrefix, URL customTemplates) {
+    super(
+        new Function<String, URL>() {
+          @Override
+          public URL apply(String name) {
+            return Resources.getResource(Renderer.class, "templates/" + name);
+          }
+        },
+        globals, staticPrefix, customTemplates);
+    SoyFileSet.Builder builder = new SoyFileSet.Builder()
+        .setCompileTimeGlobals(this.globals);
+    for (URL template : templates) {
+      builder.add(template);
+    }
+    tofu = builder.build().compileToTofu();
+  }
+
+  @Override
+  protected SoyTofu getTofu() {
+    return tofu;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/DefaultUrls.java b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultUrls.java
new file mode 100644
index 0000000..6495b5d
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/DefaultUrls.java
@@ -0,0 +1,60 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * Default implementation of {@link GitilesUrls}.
+ * <p>
+ * This implementation uses statically-configured defaults, and thus assumes
+ * that the servlet is running a single virtual host.
+ */
+class DefaultUrls implements GitilesUrls {
+  private final String canonicalHostName;
+  private final String baseGitUrl;
+  private final String baseGerritUrl;
+
+  DefaultUrls(String canonicalHostName, String baseGitUrl, String baseGerritUrl)
+      throws UnknownHostException {
+    if (canonicalHostName != null) {
+      this.canonicalHostName = canonicalHostName;
+    } else {
+      this.canonicalHostName = InetAddress.getLocalHost().getCanonicalHostName();
+    }
+    this.baseGitUrl = checkNotNull(baseGitUrl, "baseGitUrl");
+    this.baseGerritUrl = checkNotNull(baseGerritUrl, "baseGerritUrl");
+  }
+
+  @Override
+  public String getHostName(HttpServletRequest req) {
+    return canonicalHostName;
+  }
+
+  @Override
+  public String getBaseGitUrl(HttpServletRequest req) {
+    return baseGitUrl;
+  }
+
+  @Override
+  public String getBaseGerritUrl(HttpServletRequest req) {
+    return baseGerritUrl;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/DiffServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/DiffServlet.java
new file mode 100644
index 0000000..2408cd7
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/DiffServlet.java
@@ -0,0 +1,162 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+
+import com.google.common.base.Charsets;
+
+import org.eclipse.jgit.diff.DiffFormatter;
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.eclipse.jgit.treewalk.AbstractTreeIterator;
+import org.eclipse.jgit.treewalk.CanonicalTreeParser;
+import org.eclipse.jgit.treewalk.EmptyTreeIterator;
+import org.eclipse.jgit.treewalk.filter.PathFilter;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.Arrays;
+import java.util.Map;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves an HTML page with all the diffs for a commit. */
+public class DiffServlet extends BaseServlet {
+  private static final String PLACEHOLDER = "id=\"DIFF_OUTPUT_BLOCK\"";
+
+  private final Linkifier linkifier;
+
+  public DiffServlet(Renderer renderer, Linkifier linkifier) {
+    super(renderer);
+    this.linkifier = checkNotNull(linkifier, "linkifier");
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    Repository repo = ServletUtils.getRepository(req);
+
+    RevWalk walk = new RevWalk(repo);
+    try {
+      boolean showCommit;
+      AbstractTreeIterator oldTree;
+      AbstractTreeIterator newTree;
+      try {
+        // If we are viewing the diff between a commit and one of its parents,
+        // include the commit detail in the rendered page.
+        showCommit = isParentOf(walk, view.getOldRevision(), view.getRevision());
+        oldTree = getTreeIterator(walk, view.getOldRevision().getId());
+        newTree = getTreeIterator(walk, view.getRevision().getId());
+      } catch (MissingObjectException e) {
+        res.setStatus(SC_NOT_FOUND);
+        return;
+      } catch (IncorrectObjectTypeException e) {
+        res.setStatus(SC_NOT_FOUND);
+        return;
+      }
+
+      Map<String, Object> data = getData(req);
+      data.put("title", "Diff - " + view.getRevisionRange());
+      if (showCommit) {
+        data.put("commit", new CommitSoyData(linkifier, req, repo, walk, view)
+            .toSoyData(walk.parseCommit(view.getRevision().getId())));
+      }
+      if (!data.containsKey("repositoryName") && (view.getRepositoryName() != null)) {
+        data.put("repositoryName", view.getRepositoryName());
+      }
+      if (!data.containsKey("breadcrumbs")) {
+        data.put("breadcrumbs", view.getBreadcrumbs());
+      }
+
+      String[] html = renderAndSplit(data);
+      res.setStatus(HttpServletResponse.SC_OK);
+      res.setContentType(FormatType.HTML.getMimeType());
+      res.setCharacterEncoding(Charsets.UTF_8.name());
+      setCacheHeaders(req, res);
+
+      OutputStream out = res.getOutputStream();
+      try {
+        out.write(html[0].getBytes(Charsets.UTF_8));
+        formatHtmlDiff(out, repo, walk, oldTree, newTree, view.getTreePath());
+        out.write(html[1].getBytes(Charsets.UTF_8));
+      } finally {
+        out.close();
+      }
+    } finally {
+      walk.release();
+    }
+  }
+
+  private static boolean isParentOf(RevWalk walk, Revision oldRevision, Revision newRevision)
+      throws MissingObjectException, IncorrectObjectTypeException, IOException {
+    RevCommit newCommit = walk.parseCommit(newRevision.getId());
+    if (newCommit.getParentCount() > 0) {
+      return Arrays.asList(newCommit.getParents()).contains(oldRevision.getId());
+    } else {
+      return oldRevision == Revision.NULL;
+    }
+  }
+
+  private String[] renderAndSplit(Map<String, Object> data) {
+    String html = renderer.newRenderer("gitiles.diffDetail")
+        .setData(data)
+        .render();
+    int id = html.indexOf(PLACEHOLDER);
+    if (id < 0) {
+      throw new IllegalStateException("Template must contain " + PLACEHOLDER);
+    }
+
+    int lt = html.lastIndexOf('<', id);
+    int gt = html.indexOf('>', id + PLACEHOLDER.length());
+    return new String[] {html.substring(0, lt), html.substring(gt + 1)};
+  }
+
+  private void formatHtmlDiff(OutputStream out,
+      Repository repo, RevWalk walk,
+      AbstractTreeIterator oldTree, AbstractTreeIterator newTree,
+      String path)
+      throws IOException {
+    DiffFormatter diff = new HtmlDiffFormatter(renderer, out);
+    try {
+      if (!path.equals("")) {
+        diff.setPathFilter(PathFilter.create(path));
+      }
+      diff.setRepository(repo);
+      diff.setDetectRenames(true);
+      diff.format(oldTree, newTree);
+    } finally {
+      diff.release();
+    }
+  }
+
+  private static AbstractTreeIterator getTreeIterator(RevWalk walk, ObjectId id)
+      throws IOException {
+    if (!id.equals(ObjectId.zeroId())) {
+      CanonicalTreeParser p = new CanonicalTreeParser();
+      p.reset(walk.getObjectReader(), walk.parseTree(id));
+      return p;
+    } else {
+      return new EmptyTreeIterator();
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/FormatType.java b/gitiles-servlet/src/main/java/com/google/gitiles/FormatType.java
new file mode 100644
index 0000000..9417a4c
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/FormatType.java
@@ -0,0 +1,76 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import com.google.common.base.Strings;
+import com.google.common.net.HttpHeaders;
+
+import javax.servlet.http.HttpServletRequest;
+
+/** Type of formatting to use in the response to the client. */
+public enum FormatType {
+  HTML("text/html"),
+  TEXT("text/plain"),
+  JSON("application/json"),
+  DEFAULT("*/*");
+
+  private static final String FORMAT_TYPE_ATTRIBUTE = FormatType.class.getName();
+
+  public static FormatType getFormatType(HttpServletRequest req) {
+    FormatType result = (FormatType) req.getAttribute(FORMAT_TYPE_ATTRIBUTE);
+    if (result != null) {
+      return result;
+    }
+
+    String format = req.getParameter("format");
+    if (format != null) {
+      for (FormatType type : FormatType.values()) {
+        if (format.equalsIgnoreCase(type.name())) {
+          return set(req, type);
+        }
+      }
+      throw new IllegalArgumentException("Invalid format " + format);
+    }
+
+    String accept = req.getHeader(HttpHeaders.ACCEPT);
+    if (Strings.isNullOrEmpty(accept)) {
+      return set(req, DEFAULT);
+    }
+
+    for (String p : accept.split("[ ,;][ ,;]*")) {
+      for (FormatType type : FormatType.values()) {
+        if (p.equals(type.mimeType)) {
+          return set(req, type != HTML ? type : DEFAULT);
+        }
+      }
+    }
+    return set(req, DEFAULT);
+  }
+
+  private static FormatType set(HttpServletRequest req, FormatType format) {
+    req.setAttribute(FORMAT_TYPE_ATTRIBUTE, format);
+    return format;
+  }
+
+  private final String mimeType;
+
+  private FormatType(String mimeType) {
+    this.mimeType = mimeType;
+  }
+
+  public String getMimeType() {
+    return mimeType;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/GitilesAccess.java b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesAccess.java
new file mode 100644
index 0000000..648d709
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesAccess.java
@@ -0,0 +1,68 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import org.eclipse.jgit.transport.resolver.ServiceNotAuthorizedException;
+import org.eclipse.jgit.transport.resolver.ServiceNotEnabledException;
+
+import java.io.IOException;
+import java.util.Map;
+import java.util.Set;
+
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * Git storage interface for Gitiles.
+ * <p>
+ * Each instance is associated with a single end-user request, which implicitly
+ * includes information about the host and repository.
+ */
+public interface GitilesAccess {
+  /** Factory for per-request access. */
+  public interface Factory {
+    public GitilesAccess forRequest(HttpServletRequest req);
+  }
+
+  /**
+   * List repositories on the host.
+   *
+   * @param branches branches to list along with each repository.
+   * @return map of repository names to descriptions.
+   * @throws ServiceNotEnabledException to trigger an HTTP 403 Forbidden
+   *     (matching behavior in {@link org.eclipse.jgit.http.server.RepositoryFilter}).
+   * @throws ServiceNotAuthorizedException to trigger an HTTP 401 Unauthorized
+   *     (matching behavior in {@link org.eclipse.jgit.http.server.RepositoryFilter}).
+   * @throws IOException if an error occurred.
+   */
+  public Map<String, RepositoryDescription> listRepositories(Set<String> branches)
+      throws ServiceNotEnabledException, ServiceNotAuthorizedException, IOException;
+
+  /**
+   * @return an opaque object that uniquely identifies the end-user making the
+   *     request, and supports {@link #equals(Object)} and {@link #hashCode()}.
+   *     Never null.
+   */
+  public Object getUserKey();
+
+  /** @return the repository name associated with the request. */
+  public String getRepositoryName();
+
+  /**
+   * @return the description attached to the repository of this request.
+   * @throws IOException an error occurred reading the description string from
+   *         the repository.
+   */
+  public RepositoryDescription getRepositoryDescription() throws IOException;
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/GitilesFilter.java b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesFilter.java
new file mode 100644
index 0000000..b2cf9ec
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesFilter.java
@@ -0,0 +1,362 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+import static com.google.gitiles.GitilesServlet.STATIC_PREFIX;
+import static com.google.gitiles.ViewFilter.getRegexGroup;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.Joiner;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.LinkedListMultimap;
+import com.google.common.collect.ListMultimap;
+import com.google.common.collect.Maps;
+
+import org.eclipse.jgit.errors.ConfigInvalidException;
+import org.eclipse.jgit.errors.RepositoryNotFoundException;
+import org.eclipse.jgit.http.server.RepositoryFilter;
+import org.eclipse.jgit.http.server.glue.MetaFilter;
+import org.eclipse.jgit.lib.Config;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.storage.file.FileBasedConfig;
+import org.eclipse.jgit.transport.ServiceMayNotContinueException;
+import org.eclipse.jgit.transport.resolver.FileResolver;
+import org.eclipse.jgit.transport.resolver.RepositoryResolver;
+import org.eclipse.jgit.transport.resolver.ServiceNotAuthorizedException;
+import org.eclipse.jgit.transport.resolver.ServiceNotEnabledException;
+import org.eclipse.jgit.util.FS;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.UnknownHostException;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.regex.Pattern;
+
+import javax.servlet.Filter;
+import javax.servlet.FilterChain;
+import javax.servlet.FilterConfig;
+import javax.servlet.ServletException;
+import javax.servlet.ServletRequest;
+import javax.servlet.ServletResponse;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/**
+ * MetaFilter to serve Gitiles.
+ * <p>
+ * Do not use directly; use {@link GitilesServlet}.
+ */
+class GitilesFilter extends MetaFilter {
+  private static final String CONFIG_PATH_PARAM = "configPath";
+
+  // The following regexes have the following capture groups:
+  // 1. The whole string, which causes RegexPipeline to set REGEX_GROUPS but
+  //    not otherwise modify the original request.
+  // 2. The repository name part, before /<CMD>.
+  // 3. The command, <CMD>, with no slashes and beginning with +. Commands have
+  //    names analogous to (but not exactly the same as) git command names, such
+  //    as "+log" and "+show". The bare command "+" maps to one of the other
+  //    commands based on the revision/path, and may change over time.
+  // 4. The revision/path part, after /<CMD> (called just "path" below). This is
+  //    split into a revision and a path by RevisionParser.
+
+  private static final String CMD = "\\+[a-z0-9-]*";
+
+  @VisibleForTesting
+  static final Pattern ROOT_REGEX = Pattern.compile(""
+      + "^(      " // 1. Everything
+      + "  /*    " // Excess slashes
+      + "  (/)   " // 2. Repo name (just slash)
+      + "  ()    " // 3. Command
+      + "  ()    " // 4. Path
+      + ")$      ",
+      Pattern.COMMENTS);
+
+  @VisibleForTesting
+  static final Pattern REPO_REGEX = Pattern.compile(""
+      + "^(                     " // 1. Everything
+      + "  /*                   " // Excess slashes
+      + "  (                    " // 2. Repo name
+      + "   /                   " // Leading slash
+      + "   (?:.(?!             " // Anything, as long as it's not followed by...
+      + "        /" + CMD + "/  " // the special "/<CMD>/" separator,
+      + "        |/" + CMD + "$ " // or "/<CMD>" at the end of the string
+      + "        ))*?           "
+      + "  )                    "
+      + "  /*                   " // Trailing slashes
+      + "  ()                   " // 3. Command
+      + "  ()                   " // 4. Path
+      + ")$                     ",
+      Pattern.COMMENTS);
+
+  @VisibleForTesting
+  static final Pattern REPO_PATH_REGEX = Pattern.compile(""
+      + "^(              " // 1. Everything
+      + "  /*            " // Excess slashes
+      + "  (             " // 2. Repo name
+      + "   /            " // Leading slash
+      + "   .*?          " // Anything, non-greedy
+      + "  )             "
+      + "  /(" + CMD + ")" // 3. Command
+      + "  (             " // 4. Path
+      + "   (?:/.*)?     " // Slash path, or nothing.
+      + "  )             "
+      + ")$              ",
+      Pattern.COMMENTS);
+
+  private static class DispatchFilter extends AbstractHttpFilter {
+    private final ListMultimap<GitilesView.Type, Filter> filters;
+    private final Map<GitilesView.Type, HttpServlet> servlets;
+
+    private DispatchFilter(ListMultimap<GitilesView.Type, Filter> filters,
+        Map<GitilesView.Type, HttpServlet> servlets) {
+      this.filters = LinkedListMultimap.create(filters);
+      this.servlets = ImmutableMap.copyOf(servlets);
+      for (GitilesView.Type type : GitilesView.Type.values()) {
+        checkState(servlets.containsKey(type), "Missing handler for view %s", type);
+      }
+    }
+
+    @Override
+    public void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain)
+        throws IOException, ServletException {
+      GitilesView view = checkNotNull(ViewFilter.getView(req));
+      final Iterator<Filter> itr = filters.get(view.getType()).iterator();
+      final HttpServlet servlet = servlets.get(view.getType());
+      new FilterChain() {
+        @Override
+        public void doFilter(ServletRequest req, ServletResponse res)
+            throws IOException, ServletException {
+          if (itr.hasNext()) {
+            itr.next().doFilter(req, res, this);
+          } else {
+            servlet.service(req, res);
+          }
+        }
+      }.doFilter(req, res);
+    }
+  }
+
+  private final ListMultimap<GitilesView.Type, Filter> filters = LinkedListMultimap.create();
+  private final Map<GitilesView.Type, HttpServlet> servlets = Maps.newHashMap();
+
+  private Renderer renderer;
+  private GitilesUrls urls;
+  private Linkifier linkifier;
+  private GitilesAccess.Factory accessFactory;
+  private RepositoryResolver<HttpServletRequest> resolver;
+  private VisibilityCache visibilityCache;
+  private boolean initialized;
+
+  GitilesFilter() {
+  }
+
+  GitilesFilter(
+      Renderer renderer,
+      GitilesUrls urls,
+      GitilesAccess.Factory accessFactory,
+      final RepositoryResolver<HttpServletRequest> resolver,
+      VisibilityCache visibilityCache) {
+    this.renderer = checkNotNull(renderer, "renderer");
+    this.urls = checkNotNull(urls, "urls");
+    this.accessFactory = checkNotNull(accessFactory, "accessFactory");
+    this.visibilityCache = checkNotNull(visibilityCache, "visibilityCache");
+    this.linkifier = new Linkifier(urls);
+    this.resolver = wrapResolver(resolver);
+  }
+
+  @Override
+  public synchronized void init(FilterConfig config) throws ServletException {
+    super.init(config);
+    setDefaultFields(config);
+
+    for (GitilesView.Type type : GitilesView.Type.values()) {
+      if (!servlets.containsKey(type)) {
+        servlets.put(type, getDefaultHandler(type));
+      }
+    }
+
+    Filter repositoryFilter = new RepositoryFilter(resolver);
+    Filter viewFilter = new ViewFilter(accessFactory, urls, visibilityCache);
+    Filter dispatchFilter = new DispatchFilter(filters, servlets);
+    String browserCssName;
+    String prettifyCssName;
+    String prettifyJsName;
+
+    serveRegex(ROOT_REGEX)
+        .through(viewFilter)
+        .through(dispatchFilter);
+
+    serveRegex(REPO_REGEX)
+        .through(repositoryFilter)
+        .through(viewFilter)
+        .through(dispatchFilter);
+
+    serveRegex(REPO_PATH_REGEX)
+        .through(repositoryFilter)
+        .through(viewFilter)
+        .through(dispatchFilter);
+
+    initialized = true;
+  }
+
+  public synchronized BaseServlet getDefaultHandler(GitilesView.Type view) {
+    checkNotInitialized();
+    switch (view) {
+      case HOST_INDEX:
+        return new HostIndexServlet(renderer, urls, accessFactory);
+      case REPOSITORY_INDEX:
+        return new RepositoryIndexServlet(renderer, accessFactory);
+      case REVISION:
+        return new RevisionServlet(renderer, linkifier);
+      case PATH:
+        return new PathServlet(renderer);
+      case DIFF:
+        return new DiffServlet(renderer, linkifier);
+      case LOG:
+        return new LogServlet(renderer, linkifier);
+      default:
+        throw new IllegalArgumentException("Invalid view type: " + view);
+    }
+  }
+
+  synchronized void addFilter(GitilesView.Type view, Filter filter) {
+    checkNotInitialized();
+    filters.put(checkNotNull(view, "view"), checkNotNull(filter, "filter for %s", view));
+  }
+
+  synchronized void setHandler(GitilesView.Type view, HttpServlet handler) {
+    checkNotInitialized();
+    servlets.put(checkNotNull(view, "view"),
+        checkNotNull(handler, "handler for %s", view));
+  }
+
+  private synchronized void checkNotInitialized() {
+    checkState(!initialized, "Gitiles already initialized");
+  }
+
+  private static RepositoryResolver<HttpServletRequest> wrapResolver(
+      final RepositoryResolver<HttpServletRequest> resolver) {
+    checkNotNull(resolver, "resolver");
+    return new RepositoryResolver<HttpServletRequest>() {
+      @Override
+      public Repository open(HttpServletRequest req, String name)
+          throws RepositoryNotFoundException, ServiceNotAuthorizedException,
+          ServiceNotEnabledException, ServiceMayNotContinueException {
+        return resolver.open(req, ViewFilter.trimLeadingSlash(getRegexGroup(req, 1)));
+      }
+    };
+  }
+
+  private void setDefaultFields(FilterConfig config) throws ServletException {
+    if (renderer != null && urls != null && accessFactory != null && resolver != null
+        && visibilityCache != null) {
+      return;
+    }
+    String configPath = config.getInitParameter(CONFIG_PATH_PARAM);
+    if (configPath == null) {
+      throw new ServletException("Missing required parameter " + configPath);
+    }
+    FileBasedConfig jgitConfig = new FileBasedConfig(new File(configPath), FS.DETECTED);
+    try {
+      jgitConfig.load();
+    } catch (IOException e) {
+      throw new ServletException(e);
+    } catch (ConfigInvalidException e) {
+      throw new ServletException(e);
+    }
+
+    if (renderer == null) {
+      String staticPrefix = config.getServletContext().getContextPath() + STATIC_PREFIX;
+      String customTemplates = jgitConfig.getString("gitiles", null, "customTemplates");
+      // TODO(dborowitz): Automatically set to true when run with mvn jetty:run.
+      if (jgitConfig.getBoolean("gitiles", null, "reloadTemplates", false)) {
+        renderer = new DebugRenderer(staticPrefix, customTemplates,
+            Joiner.on(File.separatorChar).join(System.getProperty("user.dir"),
+                "gitiles-servlet", "src", "main", "resources",
+                "com", "google", "gitiles", "templates"));
+      } else {
+        renderer = new DefaultRenderer(staticPrefix, Renderer.toFileURL(customTemplates));
+      }
+    }
+    if (urls == null) {
+      try {
+        urls = new DefaultUrls(
+            jgitConfig.getString("gitiles", null, "canonicalHostName"),
+            getBaseGitUrl(jgitConfig),
+            getGerritUrl(jgitConfig));
+      } catch (UnknownHostException e) {
+        throw new ServletException(e);
+      }
+    }
+    linkifier = new Linkifier(urls);
+    if (accessFactory == null || resolver == null) {
+      String basePath = jgitConfig.getString("gitiles", null, "basePath");
+      if (basePath == null) {
+        throw new ServletException("gitiles.basePath not set");
+      }
+      boolean exportAll = jgitConfig.getBoolean("gitiles", null, "exportAll", false);
+
+      FileResolver<HttpServletRequest> fileResolver;
+      if (resolver == null) {
+        fileResolver = new FileResolver<HttpServletRequest>(new File(basePath), exportAll);
+        resolver = wrapResolver(fileResolver);
+      } else if (resolver instanceof FileResolver) {
+        fileResolver = (FileResolver<HttpServletRequest>) resolver;
+      } else {
+        fileResolver = null;
+      }
+      if (accessFactory == null) {
+        checkState(fileResolver != null, "need a FileResolver when GitilesAccess.Factory not set");
+        try {
+        accessFactory = new DefaultAccess.Factory(
+            new File(basePath),
+            getBaseGitUrl(jgitConfig),
+            fileResolver);
+        } catch (IOException e) {
+          throw new ServletException(e);
+        }
+      }
+    }
+    if (visibilityCache == null) {
+      if (jgitConfig.getSubsections("cache").contains("visibility")) {
+        visibilityCache =
+            new VisibilityCache(false, ConfigUtil.getCacheBuilder(jgitConfig, "visibility"));
+      } else {
+        visibilityCache = new VisibilityCache(false);
+      }
+    }
+  }
+
+  private static String getBaseGitUrl(Config config) throws ServletException {
+    String baseGitUrl = config.getString("gitiles", null, "baseGitUrl");
+    if (baseGitUrl == null) {
+      throw new ServletException("gitiles.baseGitUrl not set");
+    }
+    return baseGitUrl;
+  }
+
+  private static String getGerritUrl(Config config) throws ServletException {
+    String gerritUrl = config.getString("gitiles", null, "gerritUrl");
+    if (gerritUrl == null) {
+      throw new ServletException("gitiles.gerritUrl not set");
+    }
+    return gerritUrl;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/GitilesServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesServlet.java
new file mode 100644
index 0000000..2cdbc02
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesServlet.java
@@ -0,0 +1,113 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import org.eclipse.jgit.http.server.glue.MetaServlet;
+import org.eclipse.jgit.transport.resolver.RepositoryResolver;
+
+import java.util.Enumeration;
+
+import javax.servlet.Filter;
+import javax.servlet.FilterConfig;
+import javax.servlet.ServletConfig;
+import javax.servlet.ServletContext;
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * Servlet to serve Gitiles.
+ * <p>
+ * This servlet can either be constructed manually with its dependencies, or
+ * configured to use default implementations for the Gitiles interfaces. To
+ * configure the defaults, you must provide a single init parameter
+ * "configPath", which is the path to a git config file containing additional
+ * configuration.
+ */
+public class GitilesServlet extends MetaServlet {
+  /** The prefix from which static resources are served. */
+  public static final String STATIC_PREFIX = "/+static/";
+
+  public GitilesServlet(Renderer renderer,
+      GitilesUrls urls,
+      GitilesAccess.Factory accessFactory,
+      RepositoryResolver<HttpServletRequest> resolver,
+      VisibilityCache visibilityCache) {
+    super(new GitilesFilter(renderer, urls, accessFactory, resolver, visibilityCache));
+  }
+
+  public GitilesServlet() {
+    super(new GitilesFilter());
+  }
+
+  @Override
+  protected GitilesFilter getDelegateFilter() {
+    return (GitilesFilter) super.getDelegateFilter();
+  }
+
+  @Override
+  public void init(final ServletConfig config) throws ServletException {
+    getDelegateFilter().init(new FilterConfig() {
+      @Override
+      public String getFilterName() {
+        return getDelegateFilter().getClass().getName();
+      }
+
+      @Override
+      public String getInitParameter(String name) {
+        return config.getInitParameter(name);
+      }
+
+      @SuppressWarnings("rawtypes")
+      @Override
+      public Enumeration getInitParameterNames() {
+        return config.getInitParameterNames();
+      }
+
+      @Override
+      public ServletContext getServletContext() {
+        return config.getServletContext();
+      }
+    });
+  }
+
+  /**
+   * Add a custom filter for a view.
+   * <p>
+   * Must be called before initializing the servlet.
+   *
+   * @param view view type.
+   * @param filter filter.
+   */
+  public void addFilter(GitilesView.Type view, Filter filter) {
+    getDelegateFilter().addFilter(view, filter);
+  }
+
+  /**
+   * Set a custom handler for a view.
+   * <p>
+   * Must be called before initializing the servlet.
+   *
+   * @param view view type.
+   * @param handler handler.
+   */
+  public void setHandler(GitilesView.Type view, HttpServlet handler) {
+    getDelegateFilter().setHandler(view, handler);
+  }
+
+  public BaseServlet getDefaultHandler(GitilesView.Type view) {
+    return getDelegateFilter().getDefaultHandler(view);
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/GitilesUrls.java b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesUrls.java
new file mode 100644
index 0000000..fb7ff3b
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesUrls.java
@@ -0,0 +1,79 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import com.google.common.base.Charsets;
+import com.google.common.base.Function;
+
+import java.io.UnsupportedEncodingException;
+import java.net.URLEncoder;
+
+import javax.servlet.http.HttpServletRequest;
+
+/** Interface for URLs displayed on source browsing pages. */
+public interface GitilesUrls {
+  /**
+   * Escapes repository or path names to be safely embedded into a URL.
+   * <p>
+   * This escape implementation escapes a repository or path name such as
+   * "foo/bar</child" to appear as "foo/bar%3C/child". Spaces are escaped as
+   * "%20". Its purpose is to escape a repository name to be safe for inclusion
+   * in the path component of the URL, where "/" is a valid character that
+   * should not be encoded, while almost any other non-alpha, non-numeric
+   * character will be encoded using URL style encoding.
+   */
+  public static final Function<String, String> NAME_ESCAPER = new Function<String, String>() {
+    @Override
+    public String apply(String s) {
+      try {
+        return URLEncoder.encode(s, Charsets.UTF_8.name())
+            .replace("%2F", "/")
+            .replace("%2f", "/")
+            .replace("+", "%20")
+            .replace("%2B", "+")
+            .replace("%2b", "+");
+      } catch (UnsupportedEncodingException e) {
+        throw new IllegalStateException(e);
+      }
+    }
+  };
+
+  /**
+   * Return the name of the host from the request.
+   *
+   * Used in various user-visible text, like "MyHost Git Repositories".
+   *
+   * @param req request.
+   * @return host name; may be null.
+   */
+  public String getHostName(HttpServletRequest req);
+
+  /**
+   * Return the base URL for git repositories on this host.
+   *
+   * @param req request.
+   * @return base URL for git repositories.
+   */
+  public String getBaseGitUrl(HttpServletRequest req);
+
+  /**
+   * Return the base URL for Gerrit projects on this host.
+   *
+   * @param req request.
+   * @return base URL for Gerrit Code Review, or null if Gerrit is not
+   *     configured.
+   */
+  public String getBaseGerritUrl(HttpServletRequest req);
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/GitilesView.java b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesView.java
new file mode 100644
index 0000000..ad685c4
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/GitilesView.java
@@ -0,0 +1,563 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+import static com.google.gitiles.GitilesUrls.NAME_ESCAPER;
+
+import com.google.common.base.Charsets;
+import com.google.common.base.Objects;
+import com.google.common.base.Strings;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.LinkedListMultimap;
+import com.google.common.collect.ListMultimap;
+import com.google.common.collect.Multimaps;
+
+import org.eclipse.jgit.revwalk.RevObject;
+
+import java.io.UnsupportedEncodingException;
+import java.net.URLEncoder;
+import java.util.List;
+import java.util.Map;
+
+import javax.servlet.http.HttpServletRequest;
+
+/**
+ * Information about a view in Gitiles.
+ * <p>
+ * Views are uniquely identified by a type, and dispatched to servlet types by
+ * {@link GitilesServlet}. This class contains the list of all types, as
+ * well as some methods containing basic information parsed from the URL.
+ * Construction happens in {@link ViewFilter}.
+ */
+public class GitilesView {
+  /** All the possible view types supported in the application. */
+  public static enum Type {
+    HOST_INDEX,
+    REPOSITORY_INDEX,
+    REVISION,
+    PATH,
+    DIFF,
+    LOG;
+  }
+
+  /** Builder for views. */
+  public static class Builder {
+    private final Type type;
+    private final ListMultimap<String, String> params = LinkedListMultimap.create();
+
+    private String hostName;
+    private String servletPath;
+    private String repositoryName;
+    private Revision revision = Revision.NULL;
+    private Revision oldRevision = Revision.NULL;
+    private String path;
+    private String anchor;
+
+    private Builder(Type type) {
+      this.type = type;
+    }
+
+    public Builder copyFrom(GitilesView other) {
+      hostName = other.hostName;
+      servletPath = other.servletPath;
+      switch (type) {
+        case LOG:
+        case DIFF:
+          oldRevision = other.oldRevision;
+          // Fallthrough.
+        case PATH:
+          path = other.path;
+          // Fallthrough.
+        case REVISION:
+          revision = other.revision;
+          // Fallthrough.
+        case REPOSITORY_INDEX:
+          repositoryName = other.repositoryName;
+      }
+      // Don't copy params.
+      return this;
+    }
+
+    public Builder copyFrom(HttpServletRequest req) {
+      return copyFrom(ViewFilter.getView(req));
+    }
+
+    public Builder setHostName(String hostName) {
+      this.hostName = checkNotNull(hostName);
+      return this;
+    }
+
+    public String getHostName() {
+      return hostName;
+    }
+
+    public Builder setServletPath(String servletPath) {
+      this.servletPath = checkNotNull(servletPath);
+      return this;
+    }
+
+    public String getServletPath() {
+      return servletPath;
+    }
+
+    public Builder setRepositoryName(String repositoryName) {
+      switch (type) {
+        case HOST_INDEX:
+          throw new IllegalStateException(String.format(
+              "cannot set repository name on %s view", type));
+        default:
+          this.repositoryName = checkNotNull(repositoryName);
+          return this;
+      }
+    }
+
+    public String getRepositoryName() {
+      return repositoryName;
+    }
+
+    public Builder setRevision(Revision revision) {
+      switch (type) {
+        case HOST_INDEX:
+        case REPOSITORY_INDEX:
+          throw new IllegalStateException(String.format("cannot set revision on %s view", type));
+        default:
+          this.revision = checkNotNull(revision);
+          return this;
+      }
+    }
+
+    public Builder setRevision(String name) {
+      return setRevision(Revision.named(name));
+    }
+
+    public Builder setRevision(RevObject obj) {
+      return setRevision(Revision.peeled(obj.name(), obj));
+    }
+
+    public Builder setRevision(String name, RevObject obj) {
+      return setRevision(Revision.peeled(name, obj));
+    }
+
+    public Revision getRevision() {
+      return revision;
+    }
+
+    public Builder setOldRevision(Revision revision) {
+      switch (type) {
+        case DIFF:
+        case LOG:
+          this.oldRevision = checkNotNull(revision);
+          return this;
+        default:
+          throw new IllegalStateException(
+              String.format("cannot set old revision on %s view", type));
+      }
+    }
+
+    public Builder setOldRevision(RevObject obj) {
+      return setOldRevision(Revision.peeled(obj.name(), obj));
+    }
+
+    public Builder setOldRevision(String name, RevObject obj) {
+      return setOldRevision(Revision.peeled(name, obj));
+    }
+
+    public Revision getOldRevision() {
+      return revision;
+    }
+
+    public Builder setTreePath(String path) {
+      switch (type) {
+        case PATH:
+        case DIFF:
+          this.path = maybeTrimLeadingAndTrailingSlash(checkNotNull(path));
+          return this;
+        case LOG:
+          this.path = path != null ? maybeTrimLeadingAndTrailingSlash(path) : null;
+          return this;
+        default:
+          throw new IllegalStateException(String.format("cannot set path on %s view", type));
+      }
+    }
+
+    public String getTreePath() {
+      return path;
+    }
+
+    public Builder putParam(String key, String value) {
+      params.put(key, value);
+      return this;
+    }
+
+    public Builder replaceParam(String key, String value) {
+      params.replaceValues(key, ImmutableList.of(value));
+      return this;
+    }
+
+    public Builder putAllParams(Map<String, String[]> params) {
+      for (Map.Entry<String, String[]> e : params.entrySet()) {
+        for (String v : e.getValue()) {
+          this.params.put(e.getKey(), v);
+        }
+      }
+      return this;
+    }
+
+    public ListMultimap<String, String> getParams() {
+      return params;
+    }
+
+    public Builder setAnchor(String anchor) {
+      this.anchor = anchor;
+      return this;
+    }
+
+    public String getAnchor() {
+      return anchor;
+    }
+
+    public GitilesView build() {
+      switch (type) {
+        case HOST_INDEX:
+          checkHostIndex();
+          break;
+        case REPOSITORY_INDEX:
+          checkRepositoryIndex();
+          break;
+        case REVISION:
+          checkRevision();
+          break;
+        case PATH:
+          checkPath();
+          break;
+        case DIFF:
+          checkDiff();
+          break;
+        case LOG:
+          checkLog();
+          break;
+      }
+      return new GitilesView(type, hostName, servletPath, repositoryName, revision,
+          oldRevision, path, params, anchor);
+    }
+
+    public String toUrl() {
+      return build().toUrl();
+    }
+
+    private void checkHostIndex() {
+      checkState(hostName != null, "missing hostName on %s view", type);
+      checkState(servletPath != null, "missing hostName on %s view", type);
+    }
+
+    private void checkRepositoryIndex() {
+      checkState(repositoryName != null, "missing repository name on %s view", type);
+      checkHostIndex();
+    }
+
+    private void checkRevision() {
+      checkState(revision != Revision.NULL, "missing revision on %s view", type);
+      checkRepositoryIndex();
+    }
+
+    private void checkDiff() {
+      checkPath();
+    }
+
+    private void checkLog() {
+      checkRevision();
+    }
+
+    private void checkPath() {
+      checkState(path != null, "missing path on %s view", type);
+      checkRevision();
+    }
+  }
+
+  public static Builder hostIndex() {
+    return new Builder(Type.HOST_INDEX);
+  }
+
+  public static Builder repositoryIndex() {
+    return new Builder(Type.REPOSITORY_INDEX);
+  }
+
+  public static Builder revision() {
+    return new Builder(Type.REVISION);
+  }
+
+  public static Builder path() {
+    return new Builder(Type.PATH);
+  }
+
+  public static Builder diff() {
+    return new Builder(Type.DIFF);
+  }
+
+  public static Builder log() {
+    return new Builder(Type.LOG);
+  }
+
+  private static String maybeTrimLeadingAndTrailingSlash(String str) {
+    if (str.startsWith("/")) {
+      str = str.substring(1);
+    }
+    return !str.isEmpty() && str.endsWith("/") ? str.substring(0, str.length() - 1) : str;
+  }
+
+  private final Type type;
+  private final String hostName;
+  private final String servletPath;
+  private final String repositoryName;
+  private final Revision revision;
+  private final Revision oldRevision;
+  private final String path;
+  private final ListMultimap<String, String> params;
+  private final String anchor;
+
+  private GitilesView(Type type,
+      String hostName,
+      String servletPath,
+      String repositoryName,
+      Revision revision,
+      Revision oldRevision,
+      String path,
+      ListMultimap<String, String> params,
+      String anchor) {
+    this.type = type;
+    this.hostName = hostName;
+    this.servletPath = servletPath;
+    this.repositoryName = repositoryName;
+    this.revision = Objects.firstNonNull(revision, Revision.NULL);
+    this.oldRevision = Objects.firstNonNull(oldRevision, Revision.NULL);
+    this.path = path;
+    this.params = Multimaps.unmodifiableListMultimap(params);
+    this.anchor = anchor;
+  }
+
+  public String getHostName() {
+    return hostName;
+  }
+
+  public String getServletPath() {
+    return servletPath;
+  }
+
+  public String getRepositoryName() {
+    return repositoryName;
+  }
+
+  public Revision getRevision() {
+    return revision;
+  }
+
+  public Revision getOldRevision() {
+    return oldRevision;
+  }
+
+  public String getRevisionRange() {
+    if (oldRevision == Revision.NULL) {
+      switch (type) {
+        case LOG:
+        case DIFF:
+          // For types that require two revisions, NULL indicates the empty
+          // tree/commit.
+          return revision.getName() + "^!";
+        default:
+          // For everything else NULL indicates it is not a range, just a single
+          // revision.
+          return null;
+      }
+    } else if (type == Type.DIFF && isFirstParent(revision, oldRevision)) {
+      return revision.getName() + "^!";
+    } else {
+      return oldRevision.getName() + ".." + revision.getName();
+    }
+  }
+
+  public String getTreePath() {
+    return path;
+  }
+
+  public ListMultimap<String, String> getParameters() {
+    return params;
+  }
+
+  public String getAnchor() {
+    return anchor;
+  }
+
+  public Type getType() {
+    return type;
+  }
+
+  /** @return an escaped, relative URL representing this view. */
+  public String toUrl() {
+    StringBuilder url = new StringBuilder(servletPath).append('/');
+    ListMultimap<String, String> params = this.params;
+    switch (type) {
+      case HOST_INDEX:
+        params = LinkedListMultimap.create();
+        if (!this.params.containsKey("format")) {
+          params.put("format", FormatType.HTML.toString());
+        }
+        params.putAll(this.params);
+        break;
+      case REPOSITORY_INDEX:
+        url.append(repositoryName).append('/');
+        break;
+      case REVISION:
+        url.append(repositoryName).append("/+");
+        if (!getRevision().nameIsId()) {
+          url.append("show"); // Default for /+/master is +log.
+        }
+        url.append('/').append(revision.getName());
+        break;
+      case PATH:
+        url.append(repositoryName).append("/+/").append(revision.getName()).append('/')
+            .append(path);
+        break;
+      case DIFF:
+        url.append(repositoryName).append("/+/");
+        if (isFirstParent(revision, oldRevision)) {
+          url.append(revision.getName()).append("^!");
+        } else {
+          url.append(oldRevision.getName()).append("..").append(revision.getName());
+        }
+        url.append('/').append(path);
+        break;
+      case LOG:
+        url.append(repositoryName).append("/+");
+        if (getRevision().nameIsId() || oldRevision != Revision.NULL || path != null) {
+         // Default for /+/c0ffee/(...) is +show.
+         // Default for /+/c0ffee..deadbeef(/...) is +diff.
+          url.append("log");
+        }
+        url.append('/');
+        if (oldRevision != Revision.NULL) {
+          url.append(oldRevision.getName()).append("..");
+        }
+        url.append(revision.getName());
+        if (path != null) {
+          url.append('/').append(path);
+        }
+        break;
+      default:
+        throw new IllegalStateException("Unknown view type: " + type);
+    }
+    String baseUrl = NAME_ESCAPER.apply(url.toString());
+    url = new StringBuilder();
+    if (!params.isEmpty()) {
+      url.append('?').append(paramsToString(params));
+    }
+    if (!Strings.isNullOrEmpty(anchor)) {
+      url.append('#').append(NAME_ESCAPER.apply(anchor));
+    }
+    return baseUrl + url.toString();
+  }
+
+  public List<Map<String, String>> getBreadcrumbs() {
+    String path = this.path;
+    ImmutableList.Builder<Map<String, String>> breadcrumbs = ImmutableList.builder();
+    breadcrumbs.add(breadcrumb(hostName, hostIndex().copyFrom(this)));
+    if (repositoryName != null) {
+      breadcrumbs.add(breadcrumb(repositoryName, repositoryIndex().copyFrom(this)));
+    }
+    if (type == Type.DIFF) {
+      // TODO(dborowitz): Tweak the breadcrumbs template to allow us to render
+      // separate links in "old..new".
+      breadcrumbs.add(breadcrumb(getRevisionRange(), diff().copyFrom(this).setTreePath("")));
+    } else if (type == Type.LOG) {
+      // TODO(dborowitz): Add something in the navigation area (probably not
+      // a breadcrumb) to allow switching between /+log/ and /+/.
+      if (oldRevision == Revision.NULL) {
+        breadcrumbs.add(breadcrumb(revision.getName(), log().copyFrom(this).setTreePath(null)));
+      } else {
+        breadcrumbs.add(breadcrumb(getRevisionRange(), log().copyFrom(this).setTreePath(null)));
+      }
+      path = Strings.emptyToNull(path);
+    } else if (revision != Revision.NULL) {
+      breadcrumbs.add(breadcrumb(revision.getName(), revision().copyFrom(this)));
+    }
+    if (path != null) {
+      if (type != Type.LOG) { // The "." breadcrumb would be no different for LOG.
+        breadcrumbs.add(breadcrumb(".", copyWithPath().setTreePath("")));
+      }
+      StringBuilder cur = new StringBuilder();
+      boolean first = true;
+      for (String part : RevisionParser.PATH_SPLITTER.omitEmptyStrings().split(path)) {
+        if (!first) {
+          cur.append('/');
+        } else {
+          first = false;
+        }
+        cur.append(part);
+        breadcrumbs.add(breadcrumb(part, copyWithPath().setTreePath(cur.toString())));
+      }
+    }
+    return breadcrumbs.build();
+  }
+
+  private static Map<String, String> breadcrumb(String text, Builder url) {
+    return ImmutableMap.of("text", text, "url", url.toUrl());
+  }
+
+  private Builder copyWithPath() {
+    Builder copy;
+    switch (type) {
+      case DIFF:
+        copy = diff();
+        break;
+      case LOG:
+        copy = log();
+        break;
+      default:
+        copy = path();
+        break;
+    }
+    return copy.copyFrom(this);
+  }
+
+  private static boolean isFirstParent(Revision rev1, Revision rev2) {
+    return rev2 == Revision.NULL
+        || rev2.getName().equals(rev1.getName() + "^")
+        || rev2.getName().equals(rev1.getName() + "~1");
+  }
+
+  private static String paramsToString(ListMultimap<String, String> params) {
+    try {
+    StringBuilder sb = new StringBuilder();
+    boolean first = true;
+    for (Map.Entry<String, String> e : params.entries()) {
+      if (!first) {
+        sb.append('&');
+      } else {
+        first = false;
+      }
+      sb.append(URLEncoder.encode(e.getKey(), Charsets.UTF_8.name()));
+      if (!"".equals(e.getValue())) {
+        sb.append('=')
+            .append(URLEncoder.encode(e.getValue(), Charsets.UTF_8.name()));
+      }
+    }
+    return sb.toString();
+    } catch (UnsupportedEncodingException e) {
+      throw new IllegalStateException(e);
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/HostIndexServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/HostIndexServlet.java
new file mode 100644
index 0000000..bf9ffd1
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/HostIndexServlet.java
@@ -0,0 +1,199 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.gitiles.FormatType.JSON;
+import static com.google.gitiles.FormatType.TEXT;
+import static javax.servlet.http.HttpServletResponse.SC_BAD_REQUEST;
+import static javax.servlet.http.HttpServletResponse.SC_FORBIDDEN;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+import static javax.servlet.http.HttpServletResponse.SC_SERVICE_UNAVAILABLE;
+import static javax.servlet.http.HttpServletResponse.SC_UNAUTHORIZED;
+
+import com.google.common.base.Strings;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Sets;
+import com.google.common.net.HttpHeaders;
+import com.google.gson.FieldNamingPolicy;
+import com.google.gson.GsonBuilder;
+import com.google.gson.reflect.TypeToken;
+import com.google.template.soy.data.SoyListData;
+import com.google.template.soy.data.SoyMapData;
+
+import org.eclipse.jgit.errors.RepositoryNotFoundException;
+import org.eclipse.jgit.transport.ServiceMayNotContinueException;
+import org.eclipse.jgit.transport.resolver.ServiceNotAuthorizedException;
+import org.eclipse.jgit.transport.resolver.ServiceNotEnabledException;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.Arrays;
+import java.util.Map;
+import java.util.Set;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves the top level index page for a Gitiles host. */
+public class HostIndexServlet extends BaseServlet {
+  private static final Logger log = LoggerFactory.getLogger(HostIndexServlet.class);
+
+  protected final GitilesUrls urls;
+  private final GitilesAccess.Factory accessFactory;
+
+  public HostIndexServlet(Renderer renderer, GitilesUrls urls,
+      GitilesAccess.Factory accessFactory) {
+    super(renderer);
+    this.urls = checkNotNull(urls, "urls");
+    this.accessFactory = checkNotNull(accessFactory, "accessFactory");
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    FormatType format;
+    try {
+      format = FormatType.getFormatType(req);
+    } catch (IllegalArgumentException err) {
+      res.sendError(SC_BAD_REQUEST);
+      return;
+    }
+
+    Set<String> branches = parseShowBranch(req);
+    Map<String, RepositoryDescription> descs;
+    try {
+      descs = accessFactory.forRequest(req).listRepositories(branches);
+    } catch (RepositoryNotFoundException e) {
+      res.sendError(SC_NOT_FOUND);
+      return;
+    } catch (ServiceNotEnabledException e) {
+      res.sendError(SC_FORBIDDEN);
+      return;
+    } catch (ServiceNotAuthorizedException e) {
+      res.sendError(SC_UNAUTHORIZED);
+      return;
+    } catch (ServiceMayNotContinueException e) {
+      // TODO(dborowitz): Show the error message to the user.
+      res.sendError(SC_FORBIDDEN);
+      return;
+    } catch (IOException err) {
+      String name = urls.getHostName(req);
+      log.warn("Cannot scan repositories" + (name != null ? "for " + name : ""), err);
+      res.sendError(SC_SERVICE_UNAVAILABLE);
+      return;
+    }
+
+    switch (format) {
+      case HTML:
+      case DEFAULT:
+      default:
+        displayHtml(req, res, descs);
+        break;
+
+      case TEXT:
+        displayText(req, res, branches, descs);
+        break;
+
+      case JSON:
+        displayJson(req, res, descs);
+        break;
+    }
+  }
+
+  private SoyMapData toSoyMapData(RepositoryDescription desc, GitilesView view) {
+    return new SoyMapData(
+        "name", desc.name,
+        "description", Strings.nullToEmpty(desc.description),
+        "url", GitilesView.repositoryIndex()
+            .copyFrom(view)
+            .setRepositoryName(desc.name)
+            .toUrl());
+  }
+
+  private void displayHtml(HttpServletRequest req, HttpServletResponse res,
+      Map<String, RepositoryDescription> descs) throws IOException {
+    SoyListData repos = new SoyListData();
+    for (RepositoryDescription desc : descs.values()) {
+      repos.add(toSoyMapData(desc, ViewFilter.getView(req)));
+    }
+
+    render(req, res, "gitiles.hostIndex", ImmutableMap.of(
+        "hostName", urls.getHostName(req),
+        "baseUrl", urls.getBaseGitUrl(req),
+        "repositories", repos));
+  }
+
+  private void displayText(HttpServletRequest req, HttpServletResponse res,
+      Set<String> branches, Map<String, RepositoryDescription> descs) throws IOException {
+    res.setContentType(TEXT.getMimeType());
+    res.setCharacterEncoding("UTF-8");
+    res.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment");
+    setNotCacheable(res);
+
+    PrintWriter writer = res.getWriter();
+    for (RepositoryDescription repo : descs.values()) {
+      for (String name : branches) {
+        String ref = repo.branches.get(name);
+        if (ref == null) {
+          // Print stub (forty '-' symbols)
+          ref = "----------------------------------------";
+        }
+        writer.print(ref);
+        writer.print(' ');
+      }
+      writer.print(GitilesUrls.NAME_ESCAPER.apply(repo.name));
+      writer.print('\n');
+    }
+    writer.flush();
+    writer.close();
+  }
+
+  private void displayJson(HttpServletRequest req, HttpServletResponse res,
+      Map<String, RepositoryDescription> descs) throws IOException {
+    res.setContentType(JSON.getMimeType());
+    res.setCharacterEncoding("UTF-8");
+    res.setHeader(HttpHeaders.CONTENT_DISPOSITION, "attachment");
+    setNotCacheable(res);
+
+    PrintWriter writer = res.getWriter();
+    new GsonBuilder()
+        .setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_UNDERSCORES)
+        .setPrettyPrinting()
+        .generateNonExecutableJson()
+        .create()
+        .toJson(descs,
+          new TypeToken<Map<String, RepositoryDescription>>() {}.getType(),
+          writer);
+    writer.print('\n');
+    writer.close();
+  }
+
+  private static Set<String> parseShowBranch(HttpServletRequest req) {
+    // Roughly match Gerrit Code Review's /projects/ API by supporting
+    // both show-branch and b as query parameters.
+    Set<String> branches = Sets.newLinkedHashSet();
+    String[] values = req.getParameterValues("show-branch");
+    if (values != null) {
+      branches.addAll(Arrays.asList(values));
+    }
+    values = req.getParameterValues("b");
+    if (values != null) {
+      branches.addAll(Arrays.asList(values));
+    }
+    return branches;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/HtmlDiffFormatter.java b/gitiles-servlet/src/main/java/com/google/gitiles/HtmlDiffFormatter.java
new file mode 100644
index 0000000..63b1eb8
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/HtmlDiffFormatter.java
@@ -0,0 +1,128 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.base.Charsets;
+import com.google.common.collect.ImmutableMap;
+
+import org.apache.commons.lang3.StringEscapeUtils;
+import org.eclipse.jgit.diff.DiffEntry;
+import org.eclipse.jgit.diff.DiffFormatter;
+import org.eclipse.jgit.diff.RawText;
+import org.eclipse.jgit.patch.FileHeader;
+import org.eclipse.jgit.patch.FileHeader.PatchType;
+import org.eclipse.jgit.util.RawParseUtils;
+
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.List;
+
+/** Formats a unified format patch as UTF-8 encoded HTML. */
+final class HtmlDiffFormatter extends DiffFormatter {
+  private static final byte[] DIFF_BEGIN = "<pre class=\"diff-unified\">".getBytes(Charsets.UTF_8);
+  private static final byte[] DIFF_END = "</pre>".getBytes(Charsets.UTF_8);
+
+  private static final byte[] HUNK_BEGIN = "<span class=\"h\">".getBytes(Charsets.UTF_8);
+  private static final byte[] HUNK_END = "</span>".getBytes(Charsets.UTF_8);
+
+  private static final byte[] LINE_INSERT_BEGIN = "<span class=\"i\">".getBytes(Charsets.UTF_8);
+  private static final byte[] LINE_DELETE_BEGIN = "<span class=\"d\">".getBytes(Charsets.UTF_8);
+  private static final byte[] LINE_CHANGE_BEGIN = "<span class=\"c\">".getBytes(Charsets.UTF_8);
+  private static final byte[] LINE_END = "</span>\n".getBytes(Charsets.UTF_8);
+
+  private final Renderer renderer;
+  private int fileIndex;
+
+  HtmlDiffFormatter(Renderer renderer, OutputStream out) {
+    super(out);
+    this.renderer = checkNotNull(renderer, "renderer");
+  }
+
+  @Override
+  public void format(List<? extends DiffEntry> entries) throws IOException {
+    for (fileIndex = 0; fileIndex < entries.size(); fileIndex++) {
+      format(entries.get(fileIndex));
+    }
+  }
+
+  @Override
+  public void format(FileHeader hdr, RawText a, RawText b)
+      throws IOException {
+    int start = hdr.getStartOffset();
+    int end = hdr.getEndOffset();
+    if (!hdr.getHunks().isEmpty()) {
+      end = hdr.getHunks().get(0).getStartOffset();
+    }
+    renderHeader(RawParseUtils.decode(hdr.getBuffer(), start, end));
+
+    if (hdr.getPatchType() == PatchType.UNIFIED) {
+      getOutputStream().write(DIFF_BEGIN);
+      format(hdr.toEditList(), a, b);
+      getOutputStream().write(DIFF_END);
+    }
+  }
+
+  private void renderHeader(String header)
+      throws IOException {
+    int lf = header.indexOf('\n');
+    String first;
+    String rest;
+    if (0 <= lf) {
+      first = header.substring(0, lf);
+      rest = header.substring(lf + 1);
+    } else {
+      first = header;
+      rest = "";
+    }
+    getOutputStream().write(renderer.newRenderer("gitiles.diffHeader")
+        .setData(ImmutableMap.of("first", first, "rest", rest, "fileIndex", fileIndex))
+        .render()
+        .getBytes(Charsets.UTF_8));
+  }
+
+  @Override
+  protected void writeHunkHeader(int aStartLine, int aEndLine,
+      int bStartLine, int bEndLine) throws IOException {
+    getOutputStream().write(HUNK_BEGIN);
+    // TODO(sop): If hunk header starts including method names, escape it.
+    super.writeHunkHeader(aStartLine, aEndLine, bStartLine, bEndLine);
+    getOutputStream().write(HUNK_END);
+  }
+
+  @Override
+  protected void writeLine(char prefix, RawText text, int cur)
+      throws IOException {
+    // Manually render each line, rather than invoke a Soy template. This method
+    // can be called thousands of times in a single request. Avoid unnecessary
+    // overheads by formatting as-is.
+    OutputStream out = getOutputStream();
+    switch (prefix) {
+      case '+':
+        out.write(LINE_INSERT_BEGIN);
+        break;
+      case '-':
+        out.write(LINE_DELETE_BEGIN);
+        break;
+      case ' ':
+      default:
+        out.write(LINE_CHANGE_BEGIN);
+        break;
+    }
+    out.write(StringEscapeUtils.escapeHtml4(text.getString(cur)).getBytes(Charsets.UTF_8));
+    out.write(LINE_END);
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/Linkifier.java b/gitiles-servlet/src/main/java/com/google/gitiles/Linkifier.java
new file mode 100644
index 0000000..735e6f5
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/Linkifier.java
@@ -0,0 +1,96 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.base.Joiner;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Lists;
+
+import java.util.List;
+import java.util.Map;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import javax.servlet.http.HttpServletRequest;
+
+/** Linkifier for blocks of text such as commit message descriptions. */
+public class Linkifier {
+  private static final Pattern LINK_PATTERN;
+
+  static {
+    // HTTP URL regex adapted from com.google.gwtexpui.safehtml.client.SafeHtml.
+    String part = "[a-zA-Z0-9$_.+!*',%;:@=?#/~<>-]";
+    String httpUrl = "https?://" +
+        part + "{2,}" +
+        "(?:[(]" + part + "*" + "[)])*" +
+        part + "*";
+    String changeId = "\\bI[0-9a-f]{8,40}\\b";
+    LINK_PATTERN = Pattern.compile(Joiner.on("|").join(
+        "(" + httpUrl + ")",
+        "(" + changeId + ")"));
+  }
+
+  private final GitilesUrls urls;
+
+  public Linkifier(GitilesUrls urls) {
+    this.urls = checkNotNull(urls, "urls");
+  }
+
+  public List<Map<String, String>> linkify(HttpServletRequest req, String message) {
+    String baseGerritUrl = urls.getBaseGerritUrl(req);
+    List<Map<String, String>> parsed = Lists.newArrayList();
+    Matcher m = LINK_PATTERN.matcher(message);
+    int last = 0;
+    while (m.find()) {
+      addText(parsed, message.substring(last, m.start()));
+      if (m.group(1) != null) {
+        // Bare URL.
+        parsed.add(link(m.group(1), m.group(1)));
+      } else if (m.group(2) != null) {
+        if (baseGerritUrl != null) {
+          // Gerrit Change-Id.
+          parsed.add(link(m.group(2), baseGerritUrl + "#/q/" + m.group(2) + ",n,z"));
+        } else {
+          addText(parsed, m.group(2));
+        }
+      }
+      last = m.end();
+    }
+    addText(parsed, message.substring(last));
+    return parsed;
+  }
+
+  private static Map<String, String> link(String text, String url) {
+    return ImmutableMap.of("text", text, "url", url);
+  }
+
+  private static void addText(List<Map<String, String>> parts, String text) {
+    if (text.isEmpty()) {
+      return;
+    }
+    if (parts.isEmpty()) {
+      parts.add(ImmutableMap.of("text", text));
+    } else {
+      Map<String, String> old = parts.get(parts.size() - 1);
+      if (!old.containsKey("url")) {
+        parts.set(parts.size() - 1, ImmutableMap.of("text", old.get("text") + text));
+      } else {
+        parts.add(ImmutableMap.of("text", text));
+      }
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/LogServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/LogServlet.java
new file mode 100644
index 0000000..07977f7
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/LogServlet.java
@@ -0,0 +1,193 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+import static javax.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+
+import com.google.common.base.Optional;
+import com.google.common.base.Strings;
+import com.google.common.collect.Iterables;
+import com.google.common.collect.ListMultimap;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
+import com.google.gitiles.CommitSoyData.KeySet;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.errors.RevWalkException;
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.AbbreviatedObjectId;
+import org.eclipse.jgit.lib.AnyObjectId;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.ObjectReader;
+import org.eclipse.jgit.lib.Ref;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.FollowFilter;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevObject;
+import org.eclipse.jgit.revwalk.RevTag;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves an HTML page with a shortlog for commits and paths. */
+public class LogServlet extends BaseServlet {
+  private static final Logger log = LoggerFactory.getLogger(LogServlet.class);
+
+  private static final String START_PARAM = "s";
+
+  private final Linkifier linkifier;
+  private final int limit;
+
+  public LogServlet(Renderer renderer, Linkifier linkifier) {
+    this(renderer, linkifier, 100);
+  }
+
+  private LogServlet(Renderer renderer, Linkifier linkifier, int limit) {
+    super(renderer);
+    this.linkifier = checkNotNull(linkifier, "linkifier");
+    checkArgument(limit >= 0, "limit must be positive: %s", limit);
+    this.limit = limit;
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    Repository repo = ServletUtils.getRepository(req);
+    RevWalk walk = null;
+    try {
+      try {
+        walk = newWalk(repo, view);
+      } catch (IncorrectObjectTypeException e) {
+        res.setStatus(SC_NOT_FOUND);
+        return;
+      }
+
+      Optional<ObjectId> start = getStart(view.getParameters(), walk.getObjectReader());
+      if (start == null) {
+        res.setStatus(SC_NOT_FOUND);
+        return;
+      }
+
+      Map<String, Object> data = Maps.newHashMapWithExpectedSize(5);
+
+      if (!view.getRevision().nameIsId()) {
+        List<Map<String, Object>> tags = Lists.newArrayListWithExpectedSize(1);
+        for (RevObject o : RevisionServlet.listObjects(walk, view.getRevision().getId())) {
+          if (o instanceof RevTag) {
+            tags.add(new TagSoyData(linkifier, req).toSoyData((RevTag) o));
+          }
+        }
+        if (!tags.isEmpty()) {
+          data.put("tags", tags);
+        }
+      }
+
+      Paginator paginator = new Paginator(walk, limit, start.orNull());
+      Map<AnyObjectId, Set<Ref>> refsById = repo.getAllRefsByPeeledObjectId();
+      List<Map<String, Object>> entries = Lists.newArrayListWithCapacity(limit);
+      for (RevCommit c : paginator) {
+        entries.add(new CommitSoyData(null, req, repo, walk, view, refsById)
+            .toSoyData(c, KeySet.SHORTLOG));
+      }
+
+      String title = "Log - ";
+      if (view.getOldRevision() != Revision.NULL) {
+        title += view.getRevisionRange();
+      } else {
+        title += view.getRevision().getName();
+      }
+
+      data.put("title", title);
+      data.put("entries", entries);
+      ObjectId next = paginator.getNextStart();
+      if (next != null) {
+        data.put("nextUrl", copyAndCanonicalize(view)
+            .replaceParam(START_PARAM, next.name())
+            .toUrl());
+      }
+      ObjectId prev = paginator.getPreviousStart();
+      if (prev != null) {
+        GitilesView.Builder prevView = copyAndCanonicalize(view);
+        if (!prevView.getRevision().getId().equals(prev)) {
+          prevView.replaceParam(START_PARAM, prev.name());
+        }
+        data.put("previousUrl", prevView.toUrl());
+      }
+
+      render(req, res, "gitiles.logDetail", data);
+    } catch (RevWalkException e) {
+      log.warn("Error in rev walk", e);
+      res.setStatus(SC_INTERNAL_SERVER_ERROR);
+      return;
+    } finally {
+      if (walk != null) {
+        walk.release();
+      }
+    }
+  }
+
+  private static GitilesView.Builder copyAndCanonicalize(GitilesView view) {
+    // Canonicalize the view by using full SHAs.
+    GitilesView.Builder copy = GitilesView.log().copyFrom(view)
+        .setRevision(view.getRevision());
+    if (view.getOldRevision() != Revision.NULL) {
+      copy.setOldRevision(view.getOldRevision());
+    }
+    return copy;
+  }
+
+  private static Optional<ObjectId> getStart(ListMultimap<String, String> params,
+      ObjectReader reader) throws IOException {
+    List<String> values = params.get(START_PARAM);
+    switch (values.size()) {
+      case 0:
+        return Optional.absent();
+      case 1:
+        Collection<ObjectId> ids = reader.resolve(AbbreviatedObjectId.fromString(values.get(0)));
+        if (ids.size() != 1) {
+          return null;
+        }
+        return Optional.of(Iterables.getOnlyElement(ids));
+      default:
+        return null;
+    }
+  }
+
+  private static RevWalk newWalk(Repository repo, GitilesView view)
+      throws MissingObjectException, IncorrectObjectTypeException, IOException {
+    RevWalk walk = new RevWalk(repo);
+    walk.markStart(walk.parseCommit(view.getRevision().getId()));
+    if (view.getOldRevision() != Revision.NULL) {
+      walk.markUninteresting(walk.parseCommit(view.getOldRevision().getId()));
+    }
+    if (!Strings.isNullOrEmpty(view.getTreePath())) {
+      walk.setTreeFilter(FollowFilter.create(view.getTreePath()));
+    }
+    return walk;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/Paginator.java b/gitiles-servlet/src/main/java/com/google/gitiles/Paginator.java
new file mode 100644
index 0000000..0454556
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/Paginator.java
@@ -0,0 +1,176 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.errors.RevWalkException;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevWalk;
+
+import java.io.IOException;
+import java.util.ArrayDeque;
+import java.util.Deque;
+import java.util.Iterator;
+
+import javax.annotation.Nullable;
+
+/**
+ * Wrapper around {@link RevWalk} that paginates for Gitiles.
+ *
+ * A single page of a shortlog is defined by a revision range, such as "master"
+ * or "master..next", a page size, and a start commit, such as "c0ffee". The
+ * distance between the first commit in the walk ("next") and the first commit
+ * in the page may be arbitrarily long, but in order to present the commit list
+ * in a stable way, we must always start from the first commit in the walk. This
+ * is because there may be arbitrary merge commits between "c0ffee" and "next"
+ * that effectively insert arbitrary commits into the history starting from
+ * "c0ffee".
+ */
+class Paginator implements Iterable<RevCommit> {
+  private final RevWalk walk;
+  private final ObjectId start;
+  private final int limit;
+  private final Deque<ObjectId> prevBuffer;
+
+  private boolean done;
+  private int i;
+  private int n;
+  private int foundIndex;
+  private ObjectId nextStart;
+
+  /**
+   * @param walk revision walk.
+   * @param limit page size.
+   * @param start commit at which to start the walk, or null to start at the
+   *     beginning.
+   */
+  Paginator(RevWalk walk, int limit, @Nullable ObjectId start) {
+    this.walk = checkNotNull(walk, "walk");
+    this.start = start;
+    checkArgument(limit > 0, "limit must be positive: %s", limit);
+    this.limit = limit;
+    prevBuffer = new ArrayDeque<ObjectId>(start != null ? limit : 0);
+    i = -1;
+    foundIndex = -1;
+  }
+
+  /**
+   * Get the next element in this page of the walk.
+   *
+   * @return the next element, or null if the walk is finished.
+   *
+   * @throws MissingObjectException See {@link RevWalk#next()}.
+   * @throws IncorrectObjectTypeException See {@link RevWalk#next()}.
+   * @throws IOException See {@link RevWalk#next()}.
+   */
+  public RevCommit next() throws MissingObjectException, IncorrectObjectTypeException,
+      IOException {
+    RevCommit commit;
+    if (foundIndex < 0) {
+      while (true) {
+        commit = walk.next();
+        if (commit == null) {
+          done = true;
+          return null;
+        }
+        i++;
+        if (start == null || start.equals(commit)) {
+          foundIndex = i;
+          break;
+        }
+        if (prevBuffer.size() == limit) {
+          prevBuffer.remove();
+        }
+        prevBuffer.add(commit);
+      }
+    } else {
+      commit = walk.next();
+    }
+
+    if (++n == limit) {
+      done = true;
+    } else if (n == limit + 1 || commit == null) {
+      nextStart = commit;
+      done = true;
+      return null;
+    }
+    return commit;
+  }
+
+  /**
+   * @return the ID at the start of the page of results preceding this one, or
+   *     null if this is the first page.
+   */
+  public ObjectId getPreviousStart() {
+    checkState(done, "getPreviousStart() invalid before walk done");
+    return prevBuffer.pollFirst();
+  }
+
+  /**
+   * @return the ID at the start of the page of results after this one, or null
+   *     if this is the last page.
+   */
+  public ObjectId getNextStart() {
+    checkState(done, "getNextStart() invalid before walk done");
+    return nextStart;
+  }
+
+  /**
+   * @return an iterator over the commits in this walk.
+   * @throws RevWalkException if an error occurred, wrapping the checked
+   *     exception from {@link #next()}.
+   */
+  @Override
+  public Iterator<RevCommit> iterator() {
+    return new Iterator<RevCommit>() {
+      RevCommit next = nextUnchecked();
+
+      @Override
+      public boolean hasNext() {
+        return next != null;
+      }
+
+      @Override
+      public RevCommit next() {
+        RevCommit r = next;
+        next = nextUnchecked();
+        return r;
+      }
+
+      @Override
+      public void remove() {
+        throw new UnsupportedOperationException();
+      }
+    };
+  }
+
+  private RevCommit nextUnchecked() {
+    try {
+      return next();
+    } catch (MissingObjectException e) {
+      throw new RevWalkException(e);
+    } catch (IncorrectObjectTypeException e) {
+      throw new RevWalkException(e);
+    } catch (IOException e) {
+      throw new RevWalkException(e);
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/PathServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/PathServlet.java
new file mode 100644
index 0000000..d228202
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/PathServlet.java
@@ -0,0 +1,276 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.gitiles.TreeSoyData.resolveTargetUrl;
+import static javax.servlet.http.HttpServletResponse.SC_INTERNAL_SERVER_ERROR;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+import static org.eclipse.jgit.lib.Constants.OBJ_BLOB;
+import static org.eclipse.jgit.lib.Constants.OBJ_COMMIT;
+import static org.eclipse.jgit.lib.Constants.OBJ_TREE;
+
+import com.google.common.base.Joiner;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Maps;
+
+import org.eclipse.jgit.errors.ConfigInvalidException;
+import org.eclipse.jgit.errors.LargeObjectException;
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.FileMode;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.ObjectLoader;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevObject;
+import org.eclipse.jgit.revwalk.RevTree;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.eclipse.jgit.submodule.SubmoduleWalk;
+import org.eclipse.jgit.treewalk.TreeWalk;
+import org.eclipse.jgit.util.RawParseUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.util.Map;
+import java.util.regex.Pattern;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves an HTML page with detailed information about a path within a tree. */
+// TODO(dborowitz): Handle non-UTF-8 names.
+public class PathServlet extends BaseServlet {
+  private static final Logger log = LoggerFactory.getLogger(PathServlet.class);
+
+  /**
+   * Submodule URLs where we know there is a web page if the user visits the
+   * repository URL verbatim in a web browser.
+   */
+  private static final Pattern VERBATIM_SUBMODULE_URL_PATTERN =
+      Pattern.compile("^(" + Joiner.on('|').join(
+          "https?://[^.]+.googlesource.com/.*",
+          "https?://[^.]+.googlecode.com/.*",
+          "https?://code.google.com/p/.*",
+          "https?://github.com/.*") + ")$", Pattern.CASE_INSENSITIVE);
+
+  static enum FileType {
+    TREE(FileMode.TREE),
+    SYMLINK(FileMode.SYMLINK),
+    REGULAR_FILE(FileMode.REGULAR_FILE),
+    EXECUTABLE_FILE(FileMode.EXECUTABLE_FILE),
+    GITLINK(FileMode.GITLINK);
+
+    private final FileMode mode;
+
+    private FileType(FileMode mode) {
+      this.mode = mode;
+    }
+
+    static FileType forEntry(TreeWalk tw) {
+      int mode = tw.getRawMode(0);
+      for (FileType type : values()) {
+        if (type.mode.equals(mode)) {
+          return type;
+        }
+      }
+      return null;
+    }
+  }
+
+  public PathServlet(Renderer renderer) {
+    super(renderer);
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    Repository repo = ServletUtils.getRepository(req);
+
+    RevWalk rw = new RevWalk(repo);
+    try {
+      RevObject obj = rw.peel(rw.parseAny(view.getRevision().getId()));
+      RevTree root;
+
+      switch (obj.getType()) {
+        case OBJ_COMMIT:
+          root = ((RevCommit) obj).getTree();
+          break;
+        case OBJ_TREE:
+          root = (RevTree) obj;
+          break;
+        default:
+          res.setStatus(SC_NOT_FOUND);
+          return;
+      }
+
+      TreeWalk tw;
+      FileType type;
+      String path = view.getTreePath();
+      if (path.isEmpty()) {
+        tw = new TreeWalk(rw.getObjectReader());
+        tw.addTree(root);
+        tw.setRecursive(false);
+        type = FileType.TREE;
+      } else {
+        tw = TreeWalk.forPath(rw.getObjectReader(), path, root);
+        if (tw == null) {
+          res.setStatus(SC_NOT_FOUND);
+          return;
+        }
+        type = FileType.forEntry(tw);
+        if (type == FileType.TREE) {
+          tw.enterSubtree();
+          tw.setRecursive(false);
+        }
+      }
+
+      switch (type) {
+        case TREE:
+          showTree(req, res, rw, tw, obj);
+          break;
+        case SYMLINK:
+          showSymlink(req, res, rw, tw);
+          break;
+        case REGULAR_FILE:
+        case EXECUTABLE_FILE:
+          showFile(req, res, rw, tw);
+          break;
+        case GITLINK:
+          showGitlink(req, res, rw, tw, root);
+          break;
+        default:
+          log.error("Bad file type: %s", type);
+          res.setStatus(SC_NOT_FOUND);
+          break;
+      }
+    } catch (LargeObjectException e) {
+      res.setStatus(SC_INTERNAL_SERVER_ERROR);
+    } finally {
+      rw.release();
+    }
+  }
+
+  private void showTree(HttpServletRequest req, HttpServletResponse res, RevWalk rw, TreeWalk tw,
+      ObjectId id) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    // TODO(sop): Allow caching trees by SHA-1 when no S cookie is sent.
+    render(req, res, "gitiles.pathDetail", ImmutableMap.of(
+        "title", !view.getTreePath().isEmpty() ? view.getTreePath() : "/",
+        "type", FileType.TREE.toString(),
+        "data", new TreeSoyData(rw, view).toSoyData(id, tw)));
+  }
+
+  private void showFile(HttpServletRequest req, HttpServletResponse res, RevWalk rw, TreeWalk tw)
+      throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    // TODO(sop): Allow caching files by SHA-1 when no S cookie is sent.
+    render(req, res, "gitiles.pathDetail", ImmutableMap.of(
+        "title", ViewFilter.getView(req).getTreePath(),
+        "type", FileType.forEntry(tw).toString(),
+        "data", new BlobSoyData(rw, view).toSoyData(tw.getPathString(), tw.getObjectId(0))));
+  }
+
+  private void showSymlink(HttpServletRequest req, HttpServletResponse res, RevWalk rw,
+      TreeWalk tw) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    ObjectId id = tw.getObjectId(0);
+    Map<String, Object> data = Maps.newHashMap();
+
+    ObjectLoader loader = rw.getObjectReader().open(id, OBJ_BLOB);
+    String target;
+    try {
+      target = RawParseUtils.decode(loader.getCachedBytes(TreeSoyData.MAX_SYMLINK_SIZE));
+    } catch (LargeObjectException.OutOfMemory e) {
+      throw e;
+    } catch (LargeObjectException e) {
+      data.put("sha", ObjectId.toString(id));
+      data.put("data", null);
+      data.put("size", Long.toString(loader.getSize()));
+      render(req, res, "gitiles.pathDetail", ImmutableMap.of(
+          "title", ViewFilter.getView(req).getTreePath(),
+          "type", FileType.REGULAR_FILE.toString(),
+          "data", data));
+      return;
+    }
+
+    String url = resolveTargetUrl(
+        GitilesView.path()
+            .copyFrom(view)
+            .setTreePath(dirname(view.getTreePath()))
+            .build(),
+        target);
+    data.put("title", view.getTreePath());
+    data.put("target", target);
+    if (url != null) {
+      data.put("targetUrl", url);
+    }
+
+    // TODO(sop): Allow caching files by SHA-1 when no S cookie is sent.
+    render(req, res, "gitiles.pathDetail", ImmutableMap.of(
+        "title", ViewFilter.getView(req).getTreePath(),
+        "type", FileType.SYMLINK.toString(),
+        "data", data));
+  }
+
+  private static String dirname(String path) {
+    while (path.charAt(path.length() - 1) == '/') {
+      path = path.substring(0, path.length() - 1);
+    }
+    int lastSlash = path.lastIndexOf('/');
+    if (lastSlash > 0) {
+      return path.substring(0, lastSlash - 1);
+    } else if (lastSlash == 0) {
+      return "/";
+    } else {
+      return ".";
+    }
+  }
+
+  private void showGitlink(HttpServletRequest req, HttpServletResponse res, RevWalk rw,
+      TreeWalk tw, RevTree root) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    SubmoduleWalk sw = SubmoduleWalk.forPath(ServletUtils.getRepository(req), root,
+        view.getTreePath());
+
+    String remoteUrl;
+    try {
+      remoteUrl = sw.getRemoteUrl();
+    } catch (ConfigInvalidException e) {
+      throw new IOException(e);
+    } finally {
+      sw.release();
+    }
+
+    Map<String, Object> data = Maps.newHashMap();
+    data.put("sha", ObjectId.toString(tw.getObjectId(0)));
+    data.put("remoteUrl", remoteUrl);
+
+      // TODO(dborowitz): Guess when we can put commit SHAs in the URL.
+      String httpUrl = resolveHttpUrl(remoteUrl);
+      if (httpUrl != null) {
+        data.put("httpUrl", httpUrl);
+      }
+
+      // TODO(sop): Allow caching links by SHA-1 when no S cookie is sent.
+      render(req, res, "gitiles.pathDetail", ImmutableMap.of(
+          "title", view.getTreePath(),
+          "type", FileType.GITLINK.toString(),
+          "data", data));
+  }
+
+  private static String resolveHttpUrl(String remoteUrl) {
+    return VERBATIM_SUBMODULE_URL_PATTERN.matcher(remoteUrl).matches() ? remoteUrl : null;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/Renderer.java b/gitiles-servlet/src/main/java/com/google/gitiles/Renderer.java
new file mode 100644
index 0000000..42ce635
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/Renderer.java
@@ -0,0 +1,107 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.base.Charsets;
+import com.google.common.base.Function;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
+import com.google.template.soy.tofu.SoyTofu;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.util.List;
+import java.util.Map;
+
+import javax.servlet.http.HttpServletResponse;
+
+/** Renderer for Soy templates used by Gitiles. */
+public abstract class Renderer {
+  private static final List<String> SOY_FILENAMES = ImmutableList.of(
+      "Common.soy",
+      "DiffDetail.soy",
+      "HostIndex.soy",
+      "LogDetail.soy",
+      "ObjectDetail.soy",
+      "PathDetail.soy",
+      "RevisionDetail.soy",
+      "RepositoryIndex.soy");
+
+  public static final Map<String, String> STATIC_URL_GLOBALS = ImmutableMap.of(
+      "gitiles.CSS_URL", "gitiles.css",
+      "gitiles.PRETTIFY_CSS_URL", "prettify/prettify.css",
+      "gitiles.PRETTIFY_JS_URL", "prettify/prettify.js");
+
+  protected static final URL toFileURL(String filename) {
+    if (filename == null) {
+      return null;
+    }
+    try {
+      return new File(filename).toURI().toURL();
+    } catch (MalformedURLException e) {
+      throw new IllegalArgumentException(e);
+    }
+  }
+
+  protected ImmutableList<URL> templates;
+  protected ImmutableMap<String, String> globals;
+
+  protected Renderer(Function<String, URL> resourceMapper, Map<String, String> globals,
+      String staticPrefix, URL customTemplates) {
+    checkNotNull(staticPrefix, "staticPrefix");
+    List<URL> allTemplates = Lists.newArrayListWithCapacity(SOY_FILENAMES.size() + 1);
+    for (String filename : SOY_FILENAMES) {
+      allTemplates.add(resourceMapper.apply(filename));
+    }
+    if (customTemplates != null) {
+      allTemplates.add(customTemplates);
+    } else {
+      allTemplates.add(resourceMapper.apply("DefaultCustomTemplates.soy"));
+    }
+    templates = ImmutableList.copyOf(allTemplates);
+
+    Map<String, String> allGlobals = Maps.newHashMap();
+    for (Map.Entry<String, String> e : STATIC_URL_GLOBALS.entrySet()) {
+      allGlobals.put(e.getKey(), staticPrefix + e.getValue());
+    }
+    allGlobals.putAll(globals);
+    this.globals = ImmutableMap.copyOf(allGlobals);
+  }
+
+  public void render(HttpServletResponse res, String templateName) throws IOException {
+    render(res, templateName, ImmutableMap.<String, Object> of());
+  }
+
+  public void render(HttpServletResponse res, String templateName, Map<String, ?> soyData)
+      throws IOException {
+    res.setContentType("text/html");
+    res.setCharacterEncoding("UTF-8");
+    byte[] data = newRenderer(templateName).setData(soyData).render().getBytes(Charsets.UTF_8);
+    res.setContentLength(data.length);
+    res.getOutputStream().write(data);
+  }
+
+  SoyTofu.Renderer newRenderer(String templateName) {
+    return getTofu().newRenderer(templateName);
+  }
+
+  protected abstract SoyTofu getTofu();
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryDescription.java b/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryDescription.java
new file mode 100644
index 0000000..06ee4da
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryDescription.java
@@ -0,0 +1,25 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import java.util.Map;
+
+/** Describes a repository in the {@link HostIndexServlet} JSON output. */
+public class RepositoryDescription {
+  public String name;
+  public String cloneUrl;
+  public String description;
+  public Map<String, String> branches;
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryIndexServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryIndexServlet.java
new file mode 100644
index 0000000..325068a
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/RepositoryIndexServlet.java
@@ -0,0 +1,80 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.Strings;
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Lists;
+
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.Ref;
+import org.eclipse.jgit.lib.RefComparator;
+import org.eclipse.jgit.lib.RefDatabase;
+
+import java.io.IOException;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves the index page for a repository, if accessed directly by a browser. */
+public class RepositoryIndexServlet extends BaseServlet {
+  private final GitilesAccess.Factory accessFactory;
+
+  public RepositoryIndexServlet(Renderer renderer, GitilesAccess.Factory accessFactory) {
+    super(renderer);
+    this.accessFactory = checkNotNull(accessFactory, "accessFactory");
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    render(req, res, "gitiles.repositoryIndex", buildData(req));
+  }
+
+  @VisibleForTesting
+  Map<String, ?> buildData(HttpServletRequest req) throws IOException {
+    RepositoryDescription desc = accessFactory.forRequest(req).getRepositoryDescription();
+    return ImmutableMap.of(
+        "cloneUrl", desc.cloneUrl,
+        "description", Strings.nullToEmpty(desc.description),
+        "branches", getRefs(req, Constants.R_HEADS),
+        "tags", getRefs(req, Constants.R_TAGS));
+  }
+
+  private List<Map<String, String>> getRefs(HttpServletRequest req, String prefix)
+      throws IOException {
+    RefDatabase refdb = ServletUtils.getRepository(req).getRefDatabase();
+    String repoName = ViewFilter.getView(req).getRepositoryName();
+    Collection<Ref> refs = RefComparator.sort(refdb.getRefs(prefix).values());
+    List<Map<String, String>> result = Lists.newArrayListWithCapacity(refs.size());
+
+    for (Ref ref : refs) {
+      String name = ref.getName().substring(prefix.length());
+      boolean needPrefix = !ref.getName().equals(refdb.getRef(name).getName());
+      result.add(ImmutableMap.of(
+          "url", GitilesView.log().copyFrom(req).setRevision(
+              Revision.unpeeled(needPrefix ? ref.getName() : name, ref.getObjectId())).toUrl(),
+          "name", name));
+    }
+
+    return result;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/Revision.java b/gitiles-servlet/src/main/java/com/google/gitiles/Revision.java
new file mode 100644
index 0000000..05778e0
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/Revision.java
@@ -0,0 +1,138 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static org.eclipse.jgit.lib.Constants.OBJ_BAD;
+import static org.eclipse.jgit.lib.Constants.OBJ_TAG;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.Objects;
+
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.lib.AbbreviatedObjectId;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.revwalk.RevObject;
+import org.eclipse.jgit.revwalk.RevWalk;
+
+import java.io.IOException;
+
+/**
+ * Object encapsulating a single revision as seen by Gitiles.
+ * <p>
+ * A single revision consists of a name, an ID, and a type. Name parsing is done
+ * once per request by {@link RevisionParser}.
+ */
+public class Revision {
+  /** Sentinel indicating a missing or empty revision. */
+  public static final Revision NULL = peeled("", ObjectId.zeroId(), OBJ_BAD);
+
+  /** Common default branch given to clients. */
+  public static final Revision HEAD = named("HEAD");
+
+  private final String name;
+  private final ObjectId id;
+  private final int type;
+  private final ObjectId peeledId;
+  private final int peeledType;
+
+  public static Revision peeled(String name, RevObject obj) {
+    return peeled(name, obj, obj.getType());
+  }
+
+  public static Revision unpeeled(String name, ObjectId id) {
+    return peeled(name, id, OBJ_BAD);
+  }
+
+  public static Revision named(String name) {
+    return peeled(name, null, OBJ_BAD);
+  }
+
+  public static Revision peel(String name, ObjectId id, RevWalk walk)
+      throws MissingObjectException, IOException {
+    RevObject obj = walk.parseAny(id);
+    RevObject peeled = walk.peel(obj);
+    return new Revision(name, obj, obj.getType(), peeled, peeled.getType());
+  }
+
+  private static Revision peeled(String name, ObjectId id, int type) {
+    checkArgument(type != OBJ_TAG, "expected non-tag for %s/%s", name, id);
+    return new Revision(name, id, type, id, type);
+  }
+
+  @VisibleForTesting
+  Revision(String name, ObjectId id, int type, ObjectId peeledId, int peeledType) {
+    this.name = name;
+    this.id = id;
+    this.type = type;
+    this.peeledId = peeledId;
+    this.peeledType = peeledType;
+  }
+
+  public String getName() {
+    return name;
+  }
+
+  public int getType() {
+    return type;
+  }
+
+  public ObjectId getId() {
+    return id;
+  }
+
+  public ObjectId getPeeledId() {
+    return peeledId;
+  }
+
+  public int getPeeledType() {
+    return peeledType;
+  }
+
+  public boolean nameIsId() {
+    return AbbreviatedObjectId.isId(name)
+        && (AbbreviatedObjectId.fromString(name).prefixCompare(id) == 0);
+  }
+
+  @Override
+  public boolean equals(Object o) {
+    if (o instanceof Revision) {
+      Revision r = (Revision) o;
+      return Objects.equal(name, r.name)
+          && Objects.equal(id, r.id)
+          && Objects.equal(type, r.type)
+          && Objects.equal(peeledId, r.peeledId)
+          && Objects.equal(peeledType, r.peeledType);
+    }
+    return false;
+  }
+
+  @Override
+  public int hashCode() {
+    return Objects.hashCode(name, id, type, peeledId, peeledType);
+  }
+
+  @Override
+  public String toString() {
+    return Objects.toStringHelper(this)
+        .omitNullValues()
+        .add("name", name)
+        .add("id", id)
+        .add("type", type)
+        .add("peeledId", peeledId)
+        .add("peeledType", peeledType)
+        .toString();
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/RevisionParser.java b/gitiles-servlet/src/main/java/com/google/gitiles/RevisionParser.java
new file mode 100644
index 0000000..3e0acfa
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/RevisionParser.java
@@ -0,0 +1,214 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.CharMatcher;
+import com.google.common.base.Objects;
+import com.google.common.base.Splitter;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevWalk;
+
+import java.io.IOException;
+
+/** Object to parse revisions out of Gitiles paths. */
+class RevisionParser {
+  static final Splitter PATH_SPLITTER = Splitter.on('/');
+  private static final Splitter OPERATOR_SPLITTER = Splitter.on(CharMatcher.anyOf("^~"));
+
+  static class Result {
+    private final Revision revision;
+    private final Revision oldRevision;
+    private final int pathStart;
+
+    @VisibleForTesting
+    Result(Revision revision) {
+      this(revision, null, revision.getName().length());
+    }
+
+    @VisibleForTesting
+    Result(Revision revision, Revision oldRevision, int pathStart) {
+      this.revision = revision;
+      this.oldRevision = oldRevision;
+      this.pathStart = pathStart;
+    }
+
+    public Revision getRevision() {
+      return revision;
+    }
+
+    public Revision getOldRevision() {
+      return oldRevision;
+    }
+
+    @Override
+    public boolean equals(Object o) {
+      if (o instanceof Result) {
+        Result r = (Result) o;
+        return Objects.equal(revision, r.revision)
+            && Objects.equal(oldRevision, r.oldRevision)
+            && Objects.equal(pathStart, r.pathStart);
+      }
+      return false;
+    }
+
+    @Override
+    public int hashCode() {
+      return Objects.hashCode(revision, oldRevision, pathStart);
+    }
+
+    @Override
+    public String toString() {
+      return Objects.toStringHelper(this)
+          .omitNullValues()
+          .add("revision", revision)
+          .add("oldRevision", oldRevision)
+          .add("pathStart", pathStart)
+          .toString();
+    }
+
+    int getPathStart() {
+      return pathStart;
+    }
+  }
+
+  private final Repository repo;
+  private final GitilesAccess access;
+  private final VisibilityCache cache;
+
+  RevisionParser(Repository repo, GitilesAccess access, VisibilityCache cache) {
+    this.repo = checkNotNull(repo, "repo");
+    this.access = checkNotNull(access, "access");
+    this.cache = checkNotNull(cache, "cache");
+  }
+
+  Result parse(String path) throws IOException {
+    RevWalk walk = new RevWalk(repo);
+    try {
+      Revision oldRevision = null;
+
+      StringBuilder b = new StringBuilder();
+      boolean first = true;
+      for (String part : PATH_SPLITTER.split(path)) {
+        if (part.isEmpty()) {
+          return null; // No valid revision contains empty segments.
+        }
+        if (!first) {
+          b.append('/');
+        }
+
+        if (oldRevision == null) {
+          int dots = part.indexOf("..");
+          int firstParent = part.indexOf("^!");
+          if (dots == 0 || firstParent == 0) {
+            return null;
+          } else if (dots > 0) {
+            b.append(part.substring(0, dots));
+            String oldName = b.toString();
+            if (!isValidRevision(oldName)) {
+              return null;
+            } else {
+              ObjectId old = repo.resolve(oldName);
+              if (old == null) {
+                return null;
+              }
+              oldRevision = Revision.peel(oldName, old, walk);
+            }
+            part = part.substring(dots + 2);
+            b = new StringBuilder();
+          } else if (firstParent > 0) {
+            if (firstParent != part.length() - 2) {
+              return null;
+            }
+            b.append(part.substring(0, part.length() - 2));
+            String name = b.toString();
+            if (!isValidRevision(name)) {
+              return null;
+            }
+            ObjectId id = repo.resolve(name);
+            if (id == null) {
+              return null;
+            }
+            RevCommit c;
+            try {
+              c = walk.parseCommit(id);
+            } catch (IncorrectObjectTypeException e) {
+              return null; // Not a commit, ^! is invalid.
+            }
+            if (c.getParentCount() > 0) {
+              oldRevision = Revision.peeled(name + "^", c.getParent(0));
+            } else {
+              oldRevision = Revision.NULL;
+            }
+            Result result = new Result(Revision.peeled(name, c), oldRevision, name.length() + 2);
+            return isVisible(walk, result) ? result : null;
+          }
+        }
+        b.append(part);
+
+        String name = b.toString();
+        if (!isValidRevision(name)) {
+          return null;
+        }
+        ObjectId id = repo.resolve(name);
+        if (id != null) {
+          int pathStart;
+          if (oldRevision == null) {
+            pathStart = name.length(); // foo
+          } else {
+            // foo..bar (foo may be empty)
+            pathStart = oldRevision.getName().length() + 2 + name.length();
+          }
+          Result result = new Result(Revision.peel(name, id, walk), oldRevision, pathStart);
+          return isVisible(walk, result) ? result : null;
+        }
+        first = false;
+      }
+      return null;
+    } finally {
+      walk.release();
+    }
+  }
+
+  private static boolean isValidRevision(String revision) {
+    // Disallow some uncommon but valid revision expressions that either we
+    // don't support or we represent differently in our URLs.
+    return revision.indexOf(':') < 0
+        && revision.indexOf("^{") < 0
+        && revision.indexOf('@') < 0;
+  }
+
+  private boolean isVisible(RevWalk walk, Result result) throws IOException {
+    String maybeRef = OPERATOR_SPLITTER.split(result.getRevision().getName()).iterator().next();
+    if (repo.getRef(maybeRef) != null) {
+      // Name contains a visible ref; skip expensive reachability check.
+      return true;
+    }
+    if (!cache.isVisible(repo, walk, access, result.getRevision().getId())) {
+      return false;
+    }
+    if (result.getOldRevision() != null && result.getOldRevision() != Revision.NULL) {
+      return cache.isVisible(repo, walk, access, result.getOldRevision().getId());
+    } else {
+      return true;
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/RevisionServlet.java b/gitiles-servlet/src/main/java/com/google/gitiles/RevisionServlet.java
new file mode 100644
index 0000000..66a7086
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/RevisionServlet.java
@@ -0,0 +1,136 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+import static org.eclipse.jgit.lib.Constants.OBJ_BLOB;
+import static org.eclipse.jgit.lib.Constants.OBJ_COMMIT;
+import static org.eclipse.jgit.lib.Constants.OBJ_TAG;
+import static org.eclipse.jgit.lib.Constants.OBJ_TREE;
+
+import com.google.common.collect.ImmutableMap;
+import com.google.common.collect.Lists;
+import com.google.gitiles.CommitSoyData.KeySet;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevObject;
+import org.eclipse.jgit.revwalk.RevTag;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.Map;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Serves an HTML page with detailed information about a ref. */
+public class RevisionServlet extends BaseServlet {
+  private static final Logger log = LoggerFactory.getLogger(RevisionServlet.class);
+
+  private final Linkifier linkifier;
+
+  public RevisionServlet(Renderer renderer, Linkifier linkifier) {
+    super(renderer);
+    this.linkifier = checkNotNull(linkifier, "linkifier");
+  }
+
+  @Override
+  protected void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException {
+    GitilesView view = ViewFilter.getView(req);
+    Repository repo = ServletUtils.getRepository(req);
+
+    RevWalk walk = new RevWalk(repo);
+    try {
+      List<RevObject> objects = listObjects(walk, view.getRevision().getId());
+      List<Map<String, ?>> soyObjects = Lists.newArrayListWithCapacity(objects.size());
+      boolean hasBlob = false;
+
+      // TODO(sop): Allow caching commits by SHA-1 when no S cookie is sent.
+      for (RevObject obj : objects) {
+        try {
+          switch (obj.getType()) {
+            case OBJ_COMMIT:
+              soyObjects.add(ImmutableMap.of(
+                  "type", Constants.TYPE_COMMIT,
+                  "data", new CommitSoyData(linkifier, req, repo, walk, view)
+                      .toSoyData((RevCommit) obj, KeySet.DETAIL_DIFF_TREE)));
+              break;
+            case OBJ_TREE:
+              soyObjects.add(ImmutableMap.of(
+                  "type", Constants.TYPE_TREE,
+                  "data", new TreeSoyData(walk, view).toSoyData(obj)));
+              break;
+            case OBJ_BLOB:
+              soyObjects.add(ImmutableMap.of(
+                  "type", Constants.TYPE_BLOB,
+                  "data", new BlobSoyData(walk, view).toSoyData(obj)));
+              hasBlob = true;
+              break;
+            case OBJ_TAG:
+              soyObjects.add(ImmutableMap.of(
+                  "type", Constants.TYPE_TAG,
+                  "data", new TagSoyData(linkifier, req).toSoyData((RevTag) obj)));
+              break;
+            default:
+              log.warn("Bad object type for %s: %s", ObjectId.toString(obj.getId()), obj.getType());
+              res.setStatus(SC_NOT_FOUND);
+              return;
+          }
+        } catch (MissingObjectException e) {
+          log.warn("Missing object " + ObjectId.toString(obj.getId()), e);
+          res.setStatus(SC_NOT_FOUND);
+          return;
+        } catch (IncorrectObjectTypeException e) {
+          log.warn("Incorrect object type for " + ObjectId.toString(obj.getId()), e);
+          res.setStatus(SC_NOT_FOUND);
+          return;
+        }
+      }
+
+      render(req, res, "gitiles.revisionDetail", ImmutableMap.of(
+          "title", view.getRevision().getName(),
+          "objects", soyObjects,
+          "hasBlob", hasBlob));
+    } finally {
+      walk.release();
+    }
+  }
+
+  // TODO(dborowitz): Extract this.
+  static List<RevObject> listObjects(RevWalk walk, ObjectId id)
+      throws MissingObjectException, IOException {
+    List<RevObject> objects = Lists.newArrayListWithExpectedSize(1);
+    while (true) {
+      RevObject cur = walk.parseAny(id);
+      objects.add(cur);
+      if (cur.getType() == Constants.OBJ_TAG) {
+        id = ((RevTag) cur).getObject();
+      } else {
+        break;
+      }
+    }
+    return objects;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/TagSoyData.java b/gitiles-servlet/src/main/java/com/google/gitiles/TagSoyData.java
new file mode 100644
index 0000000..9ddf1e5
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/TagSoyData.java
@@ -0,0 +1,50 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import com.google.common.collect.Maps;
+
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.revwalk.RevTag;
+import org.eclipse.jgit.util.GitDateFormatter;
+import org.eclipse.jgit.util.GitDateFormatter.Format;
+
+import java.util.Map;
+
+import javax.servlet.http.HttpServletRequest;
+
+/** Soy data converter for git tags. */
+public class TagSoyData {
+  private final Linkifier linkifier;
+  private final HttpServletRequest req;
+  private final GitDateFormatter dateFormatter;
+
+  public TagSoyData(Linkifier linkifier, HttpServletRequest req) {
+    this.linkifier = linkifier;
+    this.req = req;
+    this.dateFormatter = new GitDateFormatter(Format.DEFAULT);
+  }
+
+  public Map<String, Object> toSoyData(RevTag tag) {
+    Map<String, Object> data = Maps.newHashMapWithExpectedSize(4);
+    data.put("sha", ObjectId.toString(tag));
+    if (tag.getTaggerIdent() != null) {
+      data.put("tagger", CommitSoyData.toSoyData(tag.getTaggerIdent(), dateFormatter));
+    }
+    data.put("object", ObjectId.toString(tag.getObject()));
+    data.put("message", linkifier.linkify(req, tag.getFullMessage()));
+    return data;
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/TreeSoyData.java b/gitiles-servlet/src/main/java/com/google/gitiles/TreeSoyData.java
new file mode 100644
index 0000000..6cbf541
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/TreeSoyData.java
@@ -0,0 +1,160 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.gitiles.RevisionParser.PATH_SPLITTER;
+import static org.eclipse.jgit.lib.Constants.OBJ_COMMIT;
+
+import com.google.common.annotations.VisibleForTesting;
+import com.google.common.base.Charsets;
+import com.google.common.collect.Lists;
+import com.google.common.collect.Maps;
+import com.google.common.io.Files;
+import com.google.gitiles.PathServlet.FileType;
+
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.revwalk.RevWalk;
+import org.eclipse.jgit.treewalk.TreeWalk;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.Map;
+import java.util.StringTokenizer;
+
+/** Soy data converter for git trees. */
+public class TreeSoyData {
+  /**
+   * Number of characters to display for a symlink target. Targets longer than
+   * this are abbreviated for display in a tree listing.
+   */
+  private static final int MAX_SYMLINK_TARGET_LENGTH = 72;
+
+  /**
+   * Maximum number of bytes to load from a blob that claims to be a symlink. If
+   * the blob is larger than this byte limit it will be displayed as a binary
+   * file instead of as a symlink.
+   */
+  static final int MAX_SYMLINK_SIZE = 16 << 10;
+
+  static String resolveTargetUrl(GitilesView view, String target) {
+    if (target.startsWith("/")) {
+      return null;
+    }
+
+    // simplifyPath() normalizes "a/../../" to "a", so manually check whether
+    // the path leads above the git root.
+    int depth = new StringTokenizer(view.getTreePath(), "/").countTokens();
+    for (String part : PATH_SPLITTER.split(target)) {
+      if (part.equals("..")) {
+        depth--;
+        if (depth < 0) {
+          return null;
+        }
+      } else if (!part.isEmpty() && !part.equals(".")) {
+        depth++;
+      }
+    }
+
+    String path = Files.simplifyPath(view.getTreePath() + "/" + target);
+    return GitilesView.path()
+        .copyFrom(view)
+        .setTreePath(!path.equals(".") ? path : "")
+        .toUrl();
+  }
+
+  @VisibleForTesting
+  static String getTargetDisplayName(String target) {
+    if (target.length() <= MAX_SYMLINK_TARGET_LENGTH) {
+      return target;
+    } else {
+      int lastSlash = target.lastIndexOf('/');
+      // TODO(dborowitz): Doesn't abbreviate a long last path component.
+      return lastSlash >= 0 ? "..." + target.substring(lastSlash) : target;
+    }
+  }
+
+  private final RevWalk rw;
+  private final GitilesView view;
+
+  public TreeSoyData(RevWalk rw, GitilesView view) {
+    this.rw = rw;
+    this.view = view;
+  }
+
+  public Map<String, Object> toSoyData(ObjectId treeId, TreeWalk tw) throws MissingObjectException,
+         IOException {
+    List<Object> entries = Lists.newArrayList();
+    GitilesView.Builder urlBuilder = GitilesView.path().copyFrom(view);
+    while (tw.next()) {
+      FileType type = FileType.forEntry(tw);
+      String name = tw.getNameString();
+
+      switch (view.getType()) {
+        case PATH:
+          urlBuilder.setTreePath(view.getTreePath() + "/" + name);
+          break;
+        case REVISION:
+          // Got here from a tag pointing at a tree.
+          urlBuilder.setTreePath(name);
+          break;
+        default:
+          throw new IllegalStateException(String.format(
+              "Cannot render TreeSoyData from %s view", view.getType()));
+      }
+
+      String url = urlBuilder.toUrl();
+      if (type == FileType.TREE) {
+        name += "/";
+        url += "/";
+      }
+      Map<String, String> entry = Maps.newHashMapWithExpectedSize(4);
+      entry.put("type", type.toString());
+      entry.put("name", name);
+      entry.put("url", url);
+      if (type == FileType.SYMLINK) {
+        String target = new String(
+            rw.getObjectReader().open(tw.getObjectId(0)).getCachedBytes(),
+            Charsets.UTF_8);
+        // TODO(dborowitz): Merge Shawn's changes before copying these methods
+        // in.
+        entry.put("targetName", getTargetDisplayName(target));
+        String targetUrl = resolveTargetUrl(view, target);
+        if (targetUrl != null) {
+          entry.put("targetUrl", targetUrl);
+        }
+      }
+      entries.add(entry);
+    }
+
+    Map<String, Object> data = Maps.newHashMapWithExpectedSize(3);
+    data.put("sha", treeId.name());
+    data.put("entries", entries);
+
+    if (view.getType() == GitilesView.Type.PATH
+        && view.getRevision().getPeeledType() == OBJ_COMMIT) {
+      data.put("logUrl", GitilesView.log().copyFrom(view).toUrl());
+    }
+
+    return data;
+  }
+
+  public Map<String, Object> toSoyData(ObjectId treeId) throws MissingObjectException, IOException {
+    TreeWalk tw = new TreeWalk(rw.getObjectReader());
+    tw.addTree(treeId);
+    tw.setRecursive(false);
+    return toSoyData(treeId, tw);
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/ViewFilter.java b/gitiles-servlet/src/main/java/com/google/gitiles/ViewFilter.java
new file mode 100644
index 0000000..8874b1d
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/ViewFilter.java
@@ -0,0 +1,160 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+import static javax.servlet.http.HttpServletResponse.SC_NOT_FOUND;
+
+import org.eclipse.jgit.http.server.ServletUtils;
+import org.eclipse.jgit.http.server.glue.WrappedRequest;
+import org.eclipse.jgit.lib.Constants;
+
+import java.io.IOException;
+import java.util.Map;
+
+import javax.servlet.FilterChain;
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/** Filter to parse URLs and convert them to {@link GitilesView}s. */
+public class ViewFilter extends AbstractHttpFilter {
+  // TODO(dborowitz): Make this public in JGit (or implement getRegexGroup
+  // upstream).
+  private static final String REGEX_GROUPS_ATTRIBUTE =
+      "org.eclipse.jgit.http.server.glue.MetaServlet.serveRegex";
+
+  private static final String VIEW_ATTIRBUTE = ViewFilter.class.getName() + "/View";
+
+  private static final String CMD_AUTO = "+";
+  private static final String CMD_DIFF = "+diff";
+  private static final String CMD_LOG = "+log";
+  private static final String CMD_SHOW = "+show";
+
+  public static GitilesView getView(HttpServletRequest req) {
+    return (GitilesView) req.getAttribute(VIEW_ATTIRBUTE);
+  }
+
+  static String getRegexGroup(HttpServletRequest req, int groupId) {
+    WrappedRequest[] groups = (WrappedRequest[]) req.getAttribute(REGEX_GROUPS_ATTRIBUTE);
+    return checkNotNull(groups)[groupId].getPathInfo();
+  }
+
+  static void setView(HttpServletRequest req, GitilesView view) {
+    req.setAttribute(VIEW_ATTIRBUTE, view);
+  }
+
+  static String trimLeadingSlash(String str) {
+    checkArgument(str.startsWith("/"), "expected string starting with a slash: %s", str);
+    return str.substring(1);
+  }
+
+  private final GitilesUrls urls;
+  private final GitilesAccess.Factory accessFactory;
+  private final VisibilityCache visibilityCache;
+
+  public ViewFilter(GitilesAccess.Factory accessFactory, GitilesUrls urls,
+      VisibilityCache visibilityCache) {
+    this.urls = checkNotNull(urls, "urls");
+    this.accessFactory = checkNotNull(accessFactory, "accessFactory");
+    this.visibilityCache = checkNotNull(visibilityCache, "visibilityCache");
+  }
+
+  @Override
+  public void doFilter(HttpServletRequest req, HttpServletResponse res, FilterChain chain)
+      throws IOException, ServletException {
+    GitilesView.Builder view = parse(req);
+    if (view == null) {
+      res.setStatus(SC_NOT_FOUND);
+      return;
+    }
+    @SuppressWarnings("unchecked")
+    Map<String, String[]> params = req.getParameterMap();
+    view.setHostName(urls.getHostName(req))
+        .setServletPath(req.getContextPath() + req.getServletPath())
+        .putAllParams(params);
+    setView(req, view.build());
+    try {
+      chain.doFilter(req, res);
+    } finally {
+      req.removeAttribute(VIEW_ATTIRBUTE);
+    }
+  }
+
+  private GitilesView.Builder parse(HttpServletRequest req) throws IOException {
+    String repoName = trimLeadingSlash(getRegexGroup(req, 1));
+    String command = getRegexGroup(req, 2);
+    String path = getRegexGroup(req, 3);
+
+    // Non-path cases.
+    if (repoName.isEmpty()) {
+      return GitilesView.hostIndex();
+    } else if (command.isEmpty()) {
+      return GitilesView.repositoryIndex().setRepositoryName(repoName);
+    } else if (path.isEmpty()) {
+      return null; // Command but no path.
+    }
+
+    path = trimLeadingSlash(path);
+    RevisionParser revParser = new RevisionParser(
+        ServletUtils.getRepository(req), accessFactory.forRequest(req), visibilityCache);
+    RevisionParser.Result result = revParser.parse(path);
+    if (result == null) {
+      return null;
+    }
+    path = path.substring(result.getPathStart());
+
+    command = getCommand(command, result, path);
+    GitilesView.Builder view;
+    if (CMD_LOG.equals(command)) {
+      view = GitilesView.log().setTreePath(path);
+    } else if (CMD_SHOW.equals(command)) {
+      if (path.isEmpty()) {
+        view = GitilesView.revision();
+      } else {
+        view = GitilesView.path().setTreePath(path);
+      }
+    } else if (CMD_DIFF.equals(command)) {
+      view = GitilesView.diff().setTreePath(path);
+    } else {
+      return null; // Bad command.
+    }
+    if (result.getOldRevision() != null) { // May be NULL.
+      view.setOldRevision(result.getOldRevision());
+    }
+    view.setRepositoryName(repoName)
+        .setRevision(result.getRevision());
+    return view;
+  }
+
+  private String getCommand(String command, RevisionParser.Result result, String path) {
+    // Note: if you change the mapping for +, make sure to change
+    // GitilesView.toUrl() correspondingly.
+    if (!CMD_AUTO.equals(command)) {
+      return command;
+    } else if (result.getOldRevision() != null) {
+      return CMD_DIFF;
+    }
+    Revision rev = result.getRevision();
+    if (rev.getPeeledType() != Constants.OBJ_COMMIT
+        || !path.isEmpty()
+        || result.getRevision().nameIsId()) {
+      return CMD_SHOW;
+    } else {
+      return CMD_LOG;
+    }
+  }
+}
diff --git a/gitiles-servlet/src/main/java/com/google/gitiles/VisibilityCache.java b/gitiles-servlet/src/main/java/com/google/gitiles/VisibilityCache.java
new file mode 100644
index 0000000..22969d1
--- /dev/null
+++ b/gitiles-servlet/src/main/java/com/google/gitiles/VisibilityCache.java
@@ -0,0 +1,189 @@
+// Copyright 2012 Google Inc. All Rights Reserved.
+//
+// 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.google.gitiles;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Predicates.not;
+import static com.google.common.collect.Collections2.filter;
+
+import com.google.common.base.Objects;
+import com.google.common.base.Predicate;
+import com.google.common.base.Throwables;
+import com.google.common.cache.Cache;
+import com.google.common.cache.CacheBuilder;
+
+import org.eclipse.jgit.errors.IncorrectObjectTypeException;
+import org.eclipse.jgit.errors.MissingObjectException;
+import org.eclipse.jgit.lib.Constants;
+import org.eclipse.jgit.lib.ObjectId;
+import org.eclipse.jgit.lib.Ref;
+import org.eclipse.jgit.lib.RefDatabase;
+import org.eclipse.jgit.lib.Repository;
+import org.eclipse.jgit.revwalk.RevCommit;
+import org.eclipse.jgit.revwalk.RevSort;
+import org.eclipse.jgit.revwalk.RevWalk;
+
+import java.io.IOException;
+import java.util.Collection;
+import java.util.concurrent.Callable;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.TimeUnit;
+
+/** Cache of per-user object visibility. */
+public class VisibilityCache {
+  private static class Key {
+    private final Object user;
+    private final String repositoryName;
+    private final ObjectId objectId;
+
+    private Key(Object user, String repositoryName, ObjectId objectId) {
+      this.user = checkNotNull(user, "user");
+      this.repositoryName = checkNotNull(repositoryName, "repositoryName");
+      this.objectId = checkNotNull(objectId, "objectId");
+    }
+
+    @Override
+    public boolean equals(Object o) {
+      if (o instanceof Key) {
+        Key k = (Key) o;
+        return Objects.equal(user, k.user)
+            && Objects.equal(repositoryName, k.repositoryName)
+            && Objects.equal(objectId, k.objectId);
+      }
+      return false;
+    }
+
+    @Override
+    public int hashCode() {
+      return Objects.hashCode(user, repositoryName, objectId);
+    }
+
+    @Override
+    public String toString() {
+      return Objects.toStringHelper(this)
+        .add("user", user)
+        .add("repositoryName", repositoryName)
+        .add("objectId", objectId)
+        .toString();
+    }
+  }
+
+  private final Cache<Key, Boolean> cache;
+  private final boolean topoSort;
+
+  public static CacheBuilder<Object, Object> newBuilder() {
+    return CacheBuilder.newBuilder()
+        .maximumSize(1 << 10)
+        .expireAfterWrite(30, TimeUnit.MINUTES);
+  }
+
+  public VisibilityCache(boolean topoSort) {
+    this(topoSort, newBuilder());
+  }
+
+  public VisibilityCache(boolean topoSort, CacheBuilder<Object, Object> builder) {
+    this.cache = builder.build();
+    this.topoSort = topoSort;
+  }
+
+  public Cache<?, Boolean> getCache() {
+    return cache;
+  }
+
+  boolean isVisible(final Repository repo, final RevWalk walk, GitilesAccess access,
+      final ObjectId id) throws IOException {
+    try {
+      return cache.get(
+          new Key(access.getUserKey(), access.getRepositoryName(), id),
+          new Callable<Boolean>() {
+            @Override
+            public Boolean call() throws IOException {
+              return isVisible(repo, walk, id);
+            }
+          });
+    } catch (ExecutionException e) {
+      Throwables.propagateIfInstanceOf(e.getCause(), IOException.class);
+      throw new IOException(e);
+    }
+  }
+
+  private boolean isVisible(Repository repo, RevWalk walk, ObjectId id) throws IOException {
+    RevCommit commit;
+    try {
+      commit = walk.parseCommit(id);
+    } catch (IncorrectObjectTypeException e) {
+      return false;
+    }
+
+    // If any reference directly points at the requested object, permit display.
+    // Common for displays of pending patch sets in Gerrit Code Review, or
+    // bookmarks to the commit a tag points at.
+    Collection<Ref> allRefs = repo.getRefDatabase().getRefs(RefDatabase.ALL).values();
+    for (Ref ref : allRefs) {
+      ref = repo.getRefDatabase().peel(ref);
+      if (id.equals(ref.getObjectId()) || id.equals(ref.getPeeledObjectId())) {
+        return true;
+      }
+    }
+
+    // Check heads first under the assumption that most requests are for refs
+    // close to a head. Tags tend to be much further back in history and just
+    // clutter up the priority queue in the common case.
+    return isReachableFrom(walk, commit, filter(allRefs, refStartsWith(Constants.R_HEADS)))
+        || isReachableFrom(walk, commit, filter(allRefs, refStartsWith(Constants.R_TAGS)))
+        || isReachableFrom(walk, commit, filter(allRefs, not(refStartsWith("refs/changes/"))));
+  }
+
+  private static Predicate<Ref> refStartsWith(final String prefix) {
+    return new Predicate<Ref>() {
+      @Override
+      public boolean apply(Ref ref) {
+        return ref.getName().startsWith(prefix);
+      }
+    };
+  }
+
+  private boolean isReachableFrom(RevWalk walk, RevCommit commit, Collection<Ref> refs)
+      throws IOException {
+    walk.reset();
+    if (topoSort) {
+      walk.sort(RevSort.TOPO);
+    }
+    walk.markStart(commit);
+    for (Ref ref : refs) {
+      if (ref.getPeeledObjectId() != null) {
+        markUninteresting(walk, ref.getPeeledObjectId());
+      } else {
+        markUninteresting(walk, ref.getObjectId());
+      }
+    }
+    // If the commit is reachable from any branch head, it will appear to be
+    // uninteresting to the RevWalk and no output will be produced.
+    return walk.next() == null;
+  }
+
+  private static void markUninteresting(RevWalk walk, ObjectId id) throws IOException {
+    if (id == null) {
+      return;
+    }
+    try {
+      walk.markUninteresting(walk.parseCommit(id));
+    } catch (IncorrectObjectTypeException e) {
+      // Do nothing, doesn't affect reachability.
+    } catch (MissingObjectException e) {
+      // Do nothing, doesn't affect reachability.
+    }
+  }
+}
