/* Copyright (c) 2013-2014 Boundless and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Distribution License v1.0 * which accompanies this distribution, and is available at * https://www.eclipse.org/org/documents/edl-v10.html * * Contributors: * Gabriel Roldan (Boundless) - initial implementation */ package org.locationtech.geogig.web; import java.io.File; import java.util.Arrays; import java.util.LinkedList; import java.util.Map; import org.locationtech.geogig.api.Context; import org.locationtech.geogig.api.DefaultPlatform; import org.locationtech.geogig.api.GeoGIG; import org.locationtech.geogig.api.GlobalContextBuilder; import org.locationtech.geogig.api.Platform; import org.locationtech.geogig.api.plumbing.ResolveGeogigDir; import org.locationtech.geogig.cli.CLIContextBuilder; import org.locationtech.geogig.rest.TaskStatusResource; import org.locationtech.geogig.rest.osm.OSMRouter; import org.locationtech.geogig.rest.repository.CommandResource; import org.locationtech.geogig.rest.repository.FixedEncoder; import org.locationtech.geogig.rest.repository.RepositoryProvider; import org.locationtech.geogig.rest.repository.RepositoryRouter; import org.restlet.Application; import org.restlet.Component; import org.restlet.Restlet; import org.restlet.Router; import org.restlet.data.Protocol; import org.restlet.data.Request; import org.restlet.data.Response; import com.noelios.restlet.application.Decoder; /** * Both an embedded jetty launcher */ public class Main extends Application { static { setup(); } private RepositoryProvider repoProvider; public Main() { super(); } public Main(GeoGIG geogig) { super(); this.repoProvider = new SingleRepositoryProvider(geogig); } @Override public void setContext(org.restlet.Context context) { super.setContext(context); assert context != null; Map<String, Object> attributes = context.getAttributes(); GeoGIG geogig; if (attributes.containsKey("geogig")) { geogig = (GeoGIG) attributes.get("geogig"); } else { // revisit, not used at all // ServletContext sc = (ServletContext) dispatcher.getContext() // .getAttributes().get("org.restlet.ext.servlet.ServletContext"); // String repo = sc.getInitParameter("repository"); String repo = null; if (repo == null) { repo = System.getProperty("org.locationtech.geogig.web.repository"); } if (repo == null) { return; // throw new IllegalStateException( // "Cannot launch geogig servlet without `repository` parameter"); } geogig = loadGeoGIG(repo); } repoProvider = new SingleRepositoryProvider(geogig); } @Override public Restlet createRoot() { Router router = new Router() { @Override protected synchronized void init(Request request, Response response) { super.init(request, response); if (!isStarted()) { return; } request.getAttributes().put(RepositoryProvider.KEY, repoProvider); } }; Router repo = new RepositoryRouter(); Router osm = new OSMRouter(); router.attach("/tasks", TaskStatusResource.class); router.attach("/tasks/{taskId}.{extension}", TaskStatusResource.class); router.attach("/tasks/{taskId}", TaskStatusResource.class); router.attach("/osm", osm); router.attach("/repo", repo); router.attach("/{command}.{extension}", CommandResource.class); router.attach("/{command}", CommandResource.class); org.restlet.Context context = getContext(); // enable support for compressing responses if the client supports it. // NOTE: restlet 1.0.8 leaves a dangling thread on each request (see // EncodeRepresentation.getStream() // This problem is fixed in latest versions (2.x) of restlet. See the javadocs for // FixedEncoder for further detail // Encoder responseEncoder = new com.noelios.restlet.application.Encoder(context); FixedEncoder encoder = new FixedEncoder(context); encoder.setEncodeRequest(false); encoder.setEncodeResponse(true); encoder.setNext(router); Decoder decoder = new Decoder(context); decoder.setDecodeRequest(true); decoder.setDecodeResponse(false); decoder.setNext(encoder); return decoder; } static GeoGIG loadGeoGIG(String repo) { Platform platform = new DefaultPlatform(); platform.setWorkingDir(new File(repo)); Context inj = GlobalContextBuilder.builder.build(); GeoGIG geogig = new GeoGIG(inj, platform.pwd()); if (geogig.command(ResolveGeogigDir.class).call().isPresent()) { geogig.getRepository(); return geogig; } return geogig; } static void startServer(String repo) throws Exception { GeoGIG geogig = loadGeoGIG(repo); org.restlet.Context context = new org.restlet.Context(); Application application = new Main(geogig); application.setContext(context); Component comp = new Component(); comp.getDefaultHost().attach(application); comp.getServers().add(Protocol.HTTP, 8182); comp.start(); } static void setup() { GlobalContextBuilder.builder = new CLIContextBuilder(); } public static void main(String[] args) throws Exception { LinkedList<String> argList = new LinkedList<String>(Arrays.asList(args)); if (argList.size() == 0) { System.out.println("provide geogig repo path"); System.exit(1); } String repo = argList.pop(); startServer(repo); } }