|
@@ -23,6 +23,7 @@ import java.net.URI;
|
|
|
import java.util.ArrayList;
|
|
|
import java.util.List;
|
|
|
|
|
|
+import javax.servlet.http.HttpServletRequest;
|
|
|
import javax.ws.rs.Consumes;
|
|
|
import javax.ws.rs.DELETE;
|
|
|
import javax.ws.rs.DefaultValue;
|
|
@@ -62,8 +63,23 @@ import com.sun.jersey.api.json.JSONWithPadding;
|
|
|
public class ZNodeResource {
|
|
|
private final ZooKeeper zk;
|
|
|
|
|
|
- public ZNodeResource(@Context UriInfo ui) throws IOException {
|
|
|
- zk = ZooKeeperService.getClient(ui.getBaseUri().toString());
|
|
|
+ public ZNodeResource(@DefaultValue("") @QueryParam("session") String session,
|
|
|
+ @Context UriInfo ui,
|
|
|
+ @Context HttpServletRequest request
|
|
|
+ )
|
|
|
+ throws IOException {
|
|
|
+
|
|
|
+ String contextPath = request.getContextPath();
|
|
|
+ if (contextPath.equals("")) {
|
|
|
+ contextPath = "/";
|
|
|
+ }
|
|
|
+ if (session.equals("")) {
|
|
|
+ session = null;
|
|
|
+ } else if (!ZooKeeperService.isConnected(contextPath, session)) {
|
|
|
+ throw new WebApplicationException(Response.status(
|
|
|
+ Response.Status.UNAUTHORIZED).build());
|
|
|
+ }
|
|
|
+ zk = ZooKeeperService.getClient(contextPath, session);
|
|
|
}
|
|
|
|
|
|
private void ensurePathNotNull(String path) {
|
|
@@ -73,12 +89,10 @@ public class ZNodeResource {
|
|
|
}
|
|
|
|
|
|
@HEAD
|
|
|
- @Produces({MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
- MediaType.APPLICATION_XML})
|
|
|
+ @Produces( { MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
+ MediaType.APPLICATION_XML })
|
|
|
public Response existsZNode(@PathParam("path") String path,
|
|
|
- @Context UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui) throws InterruptedException, KeeperException {
|
|
|
Stat stat = zk.exists(path, false);
|
|
|
if (stat == null) {
|
|
|
throwNotFound(path, ui);
|
|
@@ -87,11 +101,9 @@ public class ZNodeResource {
|
|
|
}
|
|
|
|
|
|
@HEAD
|
|
|
- @Produces({MediaType.APPLICATION_OCTET_STREAM})
|
|
|
+ @Produces( { MediaType.APPLICATION_OCTET_STREAM })
|
|
|
public Response existsZNodeAsOctet(@PathParam("path") String path,
|
|
|
- @Context UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui) throws InterruptedException, KeeperException {
|
|
|
Stat stat = zk.exists(path, false);
|
|
|
if (stat == null) {
|
|
|
throwNotFound(path, ui);
|
|
@@ -101,40 +113,37 @@ public class ZNodeResource {
|
|
|
|
|
|
/*
|
|
|
* getZNodeList and getZNodeListJSON are bogus - but necessary.
|
|
|
- * Unfortunately Jersey 1.0.3 is unable to render both xml and json
|
|
|
- * properly in the case where a object contains a list/array. It's
|
|
|
- * impossible to get it to render properly for both. As a result we
|
|
|
- * need to split into two jaxb classes.
|
|
|
+ * Unfortunately Jersey 1.0.3 is unable to render both xml and json properly
|
|
|
+ * in the case where a object contains a list/array. It's impossible to get
|
|
|
+ * it to render properly for both. As a result we need to split into two
|
|
|
+ * jaxb classes.
|
|
|
*/
|
|
|
|
|
|
@GET
|
|
|
- @Produces({MediaType.APPLICATION_JSON, "application/javascript"})
|
|
|
- public Response getZNodeListJSON(@PathParam("path") String path,
|
|
|
+ @Produces( { MediaType.APPLICATION_JSON, "application/javascript" })
|
|
|
+ public Response getZNodeListJSON(
|
|
|
+ @PathParam("path") String path,
|
|
|
@QueryParam("callback") String callback,
|
|
|
@DefaultValue("data") @QueryParam("view") String view,
|
|
|
@DefaultValue("base64") @QueryParam("dataformat") String dataformat,
|
|
|
- @Context UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
- return getZNodeList(true, path, callback, view, dataformat, ui);
|
|
|
+ @Context UriInfo ui) throws InterruptedException, KeeperException {
|
|
|
+ return getZNodeList(true, path, callback, view, dataformat, ui);
|
|
|
}
|
|
|
|
|
|
@GET
|
|
|
@Produces(MediaType.APPLICATION_XML)
|
|
|
- public Response getZNodeList(@PathParam("path") String path,
|
|
|
+ public Response getZNodeList(
|
|
|
+ @PathParam("path") String path,
|
|
|
@QueryParam("callback") String callback,
|
|
|
@DefaultValue("data") @QueryParam("view") String view,
|
|
|
@DefaultValue("base64") @QueryParam("dataformat") String dataformat,
|
|
|
- @Context UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui) throws InterruptedException, KeeperException {
|
|
|
return getZNodeList(false, path, callback, view, dataformat, ui);
|
|
|
}
|
|
|
|
|
|
private Response getZNodeList(boolean json, String path, String callback,
|
|
|
String view, String dataformat, UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ throws InterruptedException, KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
if (view.equals("children")) {
|
|
@@ -150,8 +159,9 @@ public class ZNodeResource {
|
|
|
}
|
|
|
childTemplate += "{child}";
|
|
|
if (json) {
|
|
|
- child = new ZChildrenJSON(path, ui.getAbsolutePath().toString(),
|
|
|
- childTemplate, children);
|
|
|
+ child = new ZChildrenJSON(path,
|
|
|
+ ui.getAbsolutePath().toString(), childTemplate,
|
|
|
+ children);
|
|
|
} else {
|
|
|
child = new ZChildren(path, ui.getAbsolutePath().toString(),
|
|
|
childTemplate, children);
|
|
@@ -167,7 +177,7 @@ public class ZNodeResource {
|
|
|
if (data == null) {
|
|
|
data64 = null;
|
|
|
dataUtf8 = null;
|
|
|
- } else if (!dataformat.equals("utf8")){
|
|
|
+ } else if (!dataformat.equals("utf8")) {
|
|
|
data64 = data;
|
|
|
dataUtf8 = null;
|
|
|
} else {
|
|
@@ -175,12 +185,11 @@ public class ZNodeResource {
|
|
|
dataUtf8 = new String(data);
|
|
|
}
|
|
|
ZStat zstat = new ZStat(path, ui.getAbsolutePath().toString(),
|
|
|
- data64, dataUtf8, stat.getCzxid(),
|
|
|
- stat.getMzxid(), stat.getCtime(), stat.getMtime(),
|
|
|
- stat.getVersion(), stat.getCversion(),
|
|
|
- stat.getAversion(), stat.getEphemeralOwner(),
|
|
|
- stat.getDataLength(), stat.getNumChildren(),
|
|
|
- stat.getPzxid());
|
|
|
+ data64, dataUtf8, stat.getCzxid(), stat.getMzxid(), stat
|
|
|
+ .getCtime(), stat.getMtime(), stat.getVersion(),
|
|
|
+ stat.getCversion(), stat.getAversion(), stat
|
|
|
+ .getEphemeralOwner(), stat.getDataLength(), stat
|
|
|
+ .getNumChildren(), stat.getPzxid());
|
|
|
|
|
|
return Response.status(Response.Status.OK).entity(
|
|
|
new JSONWithPadding(zstat, callback)).build();
|
|
@@ -190,8 +199,7 @@ public class ZNodeResource {
|
|
|
@GET
|
|
|
@Produces(MediaType.APPLICATION_OCTET_STREAM)
|
|
|
public Response getZNodeListAsOctet(@PathParam("path") String path)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ throws InterruptedException, KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
Stat stat = new Stat();
|
|
@@ -205,18 +213,17 @@ public class ZNodeResource {
|
|
|
}
|
|
|
|
|
|
@PUT
|
|
|
- @Produces({MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
- MediaType.APPLICATION_XML})
|
|
|
+ @Produces( { MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
+ MediaType.APPLICATION_XML })
|
|
|
@Consumes(MediaType.APPLICATION_OCTET_STREAM)
|
|
|
- public Response setZNode(@PathParam("path") String path,
|
|
|
+ public Response setZNode(
|
|
|
+ @PathParam("path") String path,
|
|
|
@QueryParam("callback") String callback,
|
|
|
@DefaultValue("-1") @QueryParam("version") String versionParam,
|
|
|
@DefaultValue("base64") @QueryParam("dataformat") String dataformat,
|
|
|
@DefaultValue("false") @QueryParam("null") String setNull,
|
|
|
- @Context UriInfo ui,
|
|
|
- byte[] data)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui, byte[] data) throws InterruptedException,
|
|
|
+ KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
int version;
|
|
@@ -225,8 +232,8 @@ public class ZNodeResource {
|
|
|
} catch (NumberFormatException e) {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.BAD_REQUEST).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " bad version " + versionParam)).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path
|
|
|
+ + " bad version " + versionParam)).build());
|
|
|
}
|
|
|
|
|
|
if (setNull.equals("true")) {
|
|
@@ -235,13 +242,12 @@ public class ZNodeResource {
|
|
|
|
|
|
Stat stat = zk.setData(path, data, version);
|
|
|
|
|
|
- ZStat zstat = new ZStat(path, ui.getAbsolutePath().toString(),
|
|
|
- null, null, stat.getCzxid(),
|
|
|
- stat.getMzxid(), stat.getCtime(), stat.getMtime(),
|
|
|
- stat.getVersion(), stat.getCversion(),
|
|
|
- stat.getAversion(), stat.getEphemeralOwner(),
|
|
|
- stat.getDataLength(), stat.getNumChildren(),
|
|
|
- stat.getPzxid());
|
|
|
+ ZStat zstat = new ZStat(path, ui.getAbsolutePath().toString(), null,
|
|
|
+ null, stat.getCzxid(), stat.getMzxid(), stat.getCtime(), stat
|
|
|
+ .getMtime(), stat.getVersion(), stat.getCversion(),
|
|
|
+ stat.getAversion(), stat.getEphemeralOwner(), stat
|
|
|
+ .getDataLength(), stat.getNumChildren(), stat
|
|
|
+ .getPzxid());
|
|
|
|
|
|
return Response.status(Response.Status.OK).entity(
|
|
|
new JSONWithPadding(zstat, callback)).build();
|
|
@@ -253,10 +259,8 @@ public class ZNodeResource {
|
|
|
public void setZNodeAsOctet(@PathParam("path") String path,
|
|
|
@DefaultValue("-1") @QueryParam("version") String versionParam,
|
|
|
@DefaultValue("false") @QueryParam("null") String setNull,
|
|
|
- @Context UriInfo ui,
|
|
|
- byte[] data)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui, byte[] data) throws InterruptedException,
|
|
|
+ KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
int version;
|
|
@@ -265,8 +269,8 @@ public class ZNodeResource {
|
|
|
} catch (NumberFormatException e) {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.BAD_REQUEST).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " bad version " + versionParam)).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path
|
|
|
+ + " bad version " + versionParam)).build());
|
|
|
}
|
|
|
|
|
|
if (setNull.equals("true")) {
|
|
@@ -277,20 +281,20 @@ public class ZNodeResource {
|
|
|
}
|
|
|
|
|
|
@POST
|
|
|
- @Produces({MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
- MediaType.APPLICATION_XML})
|
|
|
+ @Produces( { MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
+ MediaType.APPLICATION_XML })
|
|
|
@Consumes(MediaType.APPLICATION_OCTET_STREAM)
|
|
|
- public Response createZNode(@PathParam("path") String path,
|
|
|
+ public Response createZNode(
|
|
|
+ @PathParam("path") String path,
|
|
|
@QueryParam("callback") String callback,
|
|
|
@DefaultValue("create") @QueryParam("op") String op,
|
|
|
@QueryParam("name") String name,
|
|
|
@DefaultValue("base64") @QueryParam("dataformat") String dataformat,
|
|
|
@DefaultValue("false") @QueryParam("null") String setNull,
|
|
|
@DefaultValue("false") @QueryParam("sequence") String sequence,
|
|
|
- @Context UriInfo ui,
|
|
|
- byte[] data)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @DefaultValue("false") @QueryParam("ephemeral") String ephemeral,
|
|
|
+ @Context UriInfo ui, byte[] data) throws InterruptedException,
|
|
|
+ KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
if (path.equals("/")) {
|
|
@@ -302,8 +306,8 @@ public class ZNodeResource {
|
|
|
if (!op.equals("create")) {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.BAD_REQUEST).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " bad operaton " + op)).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path
|
|
|
+ + " bad operaton " + op)).build());
|
|
|
}
|
|
|
|
|
|
if (setNull.equals("true")) {
|
|
@@ -312,19 +316,24 @@ public class ZNodeResource {
|
|
|
|
|
|
CreateMode createMode;
|
|
|
if (sequence.equals("true")) {
|
|
|
- createMode = CreateMode.PERSISTENT_SEQUENTIAL;
|
|
|
- } else {
|
|
|
+ if (ephemeral.equals("false")) {
|
|
|
+ createMode = CreateMode.PERSISTENT_SEQUENTIAL;
|
|
|
+ } else {
|
|
|
+ createMode = CreateMode.EPHEMERAL_SEQUENTIAL;
|
|
|
+ }
|
|
|
+ } else if (ephemeral.equals("false")) {
|
|
|
createMode = CreateMode.PERSISTENT;
|
|
|
+ } else {
|
|
|
+ createMode = CreateMode.EPHEMERAL;
|
|
|
}
|
|
|
|
|
|
- String newPath = zk.create(path, data, Ids.OPEN_ACL_UNSAFE,
|
|
|
- createMode);
|
|
|
+ String newPath = zk.create(path, data, Ids.OPEN_ACL_UNSAFE, createMode);
|
|
|
|
|
|
URI uri = ui.getAbsolutePathBuilder().path(newPath).build();
|
|
|
|
|
|
return Response.created(uri).entity(
|
|
|
- new JSONWithPadding(new ZPath(newPath,
|
|
|
- ui.getAbsolutePath().toString()))).build();
|
|
|
+ new JSONWithPadding(new ZPath(newPath, ui.getAbsolutePath()
|
|
|
+ .toString()))).build();
|
|
|
}
|
|
|
|
|
|
@POST
|
|
@@ -335,10 +344,8 @@ public class ZNodeResource {
|
|
|
@QueryParam("name") String name,
|
|
|
@DefaultValue("false") @QueryParam("null") String setNull,
|
|
|
@DefaultValue("false") @QueryParam("sequence") String sequence,
|
|
|
- @Context UriInfo ui,
|
|
|
- byte[] data)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui, byte[] data) throws InterruptedException,
|
|
|
+ KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
if (path.equals("/")) {
|
|
@@ -350,8 +357,8 @@ public class ZNodeResource {
|
|
|
if (!op.equals("create")) {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.BAD_REQUEST).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " bad operaton " + op)).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path
|
|
|
+ + " bad operaton " + op)).build());
|
|
|
}
|
|
|
|
|
|
if (setNull.equals("true")) {
|
|
@@ -365,23 +372,20 @@ public class ZNodeResource {
|
|
|
createMode = CreateMode.PERSISTENT;
|
|
|
}
|
|
|
|
|
|
- String newPath = zk.create(path, data, Ids.OPEN_ACL_UNSAFE,
|
|
|
- createMode);
|
|
|
+ String newPath = zk.create(path, data, Ids.OPEN_ACL_UNSAFE, createMode);
|
|
|
|
|
|
URI uri = ui.getAbsolutePathBuilder().path(newPath).build();
|
|
|
|
|
|
- return Response.created(uri).entity(new ZPath(newPath,
|
|
|
- ui.getAbsolutePath().toString())).build();
|
|
|
+ return Response.created(uri).entity(
|
|
|
+ new ZPath(newPath, ui.getAbsolutePath().toString())).build();
|
|
|
}
|
|
|
|
|
|
@DELETE
|
|
|
- @Produces({MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
- MediaType.APPLICATION_XML, MediaType.APPLICATION_OCTET_STREAM})
|
|
|
+ @Produces( { MediaType.APPLICATION_JSON, "application/javascript",
|
|
|
+ MediaType.APPLICATION_XML, MediaType.APPLICATION_OCTET_STREAM })
|
|
|
public void deleteZNode(@PathParam("path") String path,
|
|
|
@DefaultValue("-1") @QueryParam("version") String versionParam,
|
|
|
- @Context UriInfo ui)
|
|
|
- throws InterruptedException, KeeperException
|
|
|
- {
|
|
|
+ @Context UriInfo ui) throws InterruptedException, KeeperException {
|
|
|
ensurePathNotNull(path);
|
|
|
|
|
|
int version;
|
|
@@ -390,20 +394,19 @@ public class ZNodeResource {
|
|
|
} catch (NumberFormatException e) {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.BAD_REQUEST).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " bad version " + versionParam)).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path
|
|
|
+ + " bad version " + versionParam)).build());
|
|
|
}
|
|
|
|
|
|
zk.delete(path, version);
|
|
|
}
|
|
|
|
|
|
private static void throwNotFound(String path, UriInfo ui)
|
|
|
- throws WebApplicationException
|
|
|
- {
|
|
|
+ throws WebApplicationException {
|
|
|
throw new WebApplicationException(Response.status(
|
|
|
Response.Status.NOT_FOUND).entity(
|
|
|
- new ZError(ui.getRequestUri().toString(),
|
|
|
- path + " not found")).build());
|
|
|
+ new ZError(ui.getRequestUri().toString(), path + " not found"))
|
|
|
+ .build());
|
|
|
}
|
|
|
|
|
|
}
|