Allow REST APIs to return HTTP redirects

Eventually we can expose avatar links under /accounts/{id}/avatar
instead of /avatar/{id}. This better fits with the path space of
the server.

Change-Id: I461ea540310622b5d769bf1951a72cf34ad60a0e
This commit is contained in:
Shawn Pearce
2013-01-16 19:37:40 -08:00
parent 0a8969410f
commit c375647875
2 changed files with 38 additions and 1 deletions

View File

@@ -35,6 +35,11 @@ public abstract class Response<T> {
return NONE; return NONE;
} }
/** HTTP 302 Found: temporary redirect to another URL. */
public static Redirect redirect(String location) {
return new Redirect(location);
}
@SuppressWarnings({"unchecked", "rawtypes"}) @SuppressWarnings({"unchecked", "rawtypes"})
public static <T> T unwrap(T obj) { public static <T> T unwrap(T obj) {
while (obj instanceof Response) { while (obj instanceof Response) {
@@ -90,4 +95,33 @@ public abstract class Response<T> {
return "[204 No Content] None"; return "[204 No Content] None";
} }
} }
/** An HTTP redirect to another location. */
public static final class Redirect {
private final String location;
private Redirect(String url) {
this.location = url;
}
public String location() {
return location;
}
@Override
public int hashCode() {
return location.hashCode();
}
@Override
public boolean equals(Object o) {
return o instanceof Redirect
&& ((Redirect) o).location.equals(location);
}
@Override
public String toString() {
return String.format("[302 Redirect] %s", location);
}
}
} }

View File

@@ -43,12 +43,12 @@ import com.google.gerrit.extensions.restapi.AcceptsCreate;
import com.google.gerrit.extensions.restapi.AuthException; import com.google.gerrit.extensions.restapi.AuthException;
import com.google.gerrit.extensions.restapi.BadRequestException; import com.google.gerrit.extensions.restapi.BadRequestException;
import com.google.gerrit.extensions.restapi.BinaryResult; import com.google.gerrit.extensions.restapi.BinaryResult;
import com.google.gerrit.extensions.restapi.Response;
import com.google.gerrit.extensions.restapi.DefaultInput; import com.google.gerrit.extensions.restapi.DefaultInput;
import com.google.gerrit.extensions.restapi.MethodNotAllowedException; import com.google.gerrit.extensions.restapi.MethodNotAllowedException;
import com.google.gerrit.extensions.restapi.PutInput; import com.google.gerrit.extensions.restapi.PutInput;
import com.google.gerrit.extensions.restapi.ResourceConflictException; import com.google.gerrit.extensions.restapi.ResourceConflictException;
import com.google.gerrit.extensions.restapi.ResourceNotFoundException; import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
import com.google.gerrit.extensions.restapi.Response;
import com.google.gerrit.extensions.restapi.RestCollection; import com.google.gerrit.extensions.restapi.RestCollection;
import com.google.gerrit.extensions.restapi.RestModifyView; import com.google.gerrit.extensions.restapi.RestModifyView;
import com.google.gerrit.extensions.restapi.RestReadView; import com.google.gerrit.extensions.restapi.RestReadView;
@@ -258,6 +258,9 @@ public class RestApiServlet extends HttpServlet {
@SuppressWarnings("rawtypes") @SuppressWarnings("rawtypes")
Response r = (Response) result; Response r = (Response) result;
status = r.statusCode(); status = r.statusCode();
} else if (result instanceof Response.Redirect) {
res.sendRedirect(((Response.Redirect) result).location());
return;
} }
res.setStatus(status); res.setStatus(status);