diff --git a/web/api/src/main/java/org/onosproject/rest/ApplicationsWebResource.java b/web/api/src/main/java/org/onosproject/rest/ApplicationsWebResource.java
index 6177bab..9d32090 100644
--- a/web/api/src/main/java/org/onosproject/rest/ApplicationsWebResource.java
+++ b/web/api/src/main/java/org/onosproject/rest/ApplicationsWebResource.java
@@ -46,7 +46,7 @@
 
     @GET
     @Path("{name}")
-    public Response getApplication(@PathParam("id") String name) {
+    public Response getApplication(@PathParam("name") String name) {
         ApplicationAdminService service = get(ApplicationAdminService.class);
         ApplicationId appId = service.getId(name);
         return response(service, appId);
diff --git a/web/api/src/test/java/org/onosproject/codec/impl/MockCodecContext.java b/web/api/src/test/java/org/onosproject/codec/impl/MockCodecContext.java
index f49e829..25a4fbb 100644
--- a/web/api/src/test/java/org/onosproject/codec/impl/MockCodecContext.java
+++ b/web/api/src/test/java/org/onosproject/codec/impl/MockCodecContext.java
@@ -23,7 +23,7 @@
 /**
  * Mock codec context for use in codec unit tests.
  */
-public final class MockCodecContext implements CodecContext {
+public class MockCodecContext implements CodecContext {
 
     private ObjectMapper mapper = new ObjectMapper();
     private CodecManager manager = new CodecManager();
diff --git a/web/api/src/test/java/org/onosproject/rest/ApplicationsResourceTest.java b/web/api/src/test/java/org/onosproject/rest/ApplicationsResourceTest.java
new file mode 100644
index 0000000..132a739
--- /dev/null
+++ b/web/api/src/test/java/org/onosproject/rest/ApplicationsResourceTest.java
@@ -0,0 +1,331 @@
+/*
+ * Copyright 2015 Open Networking Laboratory
+ *
+ * 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 org.onosproject.rest;
+
+import java.io.InputStream;
+import java.net.URI;
+import java.util.Optional;
+
+import org.hamcrest.Description;
+import org.hamcrest.TypeSafeMatcher;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+import org.onlab.osgi.ServiceDirectory;
+import org.onlab.osgi.TestServiceDirectory;
+import org.onlab.rest.BaseResource;
+import org.onosproject.app.ApplicationAdminService;
+import org.onosproject.app.ApplicationService;
+import org.onosproject.app.ApplicationState;
+import org.onosproject.codec.CodecService;
+import org.onosproject.codec.impl.ApplicationCodec;
+import org.onosproject.codec.impl.CodecManager;
+import org.onosproject.codec.impl.MockCodecContext;
+import org.onosproject.core.Application;
+import org.onosproject.core.ApplicationId;
+import org.onosproject.core.DefaultApplication;
+import org.onosproject.core.DefaultApplicationId;
+import org.onosproject.core.Version;
+
+import com.eclipsesource.json.JsonArray;
+import com.eclipsesource.json.JsonObject;
+import com.google.common.collect.ImmutableSet;
+import com.sun.jersey.api.client.WebResource;
+
+import static org.easymock.EasyMock.createMock;
+import static org.easymock.EasyMock.expect;
+import static org.easymock.EasyMock.expectLastCall;
+import static org.easymock.EasyMock.isA;
+import static org.easymock.EasyMock.replay;
+import static org.easymock.EasyMock.verify;
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.containsString;
+import static org.hamcrest.Matchers.hasSize;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+
+/**
+ * Unit tests for applications REST APIs.
+ */
+
+public class ApplicationsResourceTest extends ResourceTest {
+
+    private static class MockCodecContextWithService extends MockCodecContext {
+        private ApplicationAdminService service;
+
+        MockCodecContextWithService(ApplicationAdminService service) {
+            this.service = service;
+        }
+
+        @Override
+        @SuppressWarnings("unchecked")
+        public <T> T get(Class<T> serviceClass) {
+            return (T) service;
+        }
+    }
+
+    private ApplicationAdminService service;
+    private ApplicationId id1 = new DefaultApplicationId(1, "app1");
+    private ApplicationId id2 = new DefaultApplicationId(2, "app2");
+    private ApplicationId id3 = new DefaultApplicationId(3, "app3");
+    private ApplicationId id4 = new DefaultApplicationId(4, "app4");
+
+    private static final URI FURL = URI.create("mvn:org.foo-features/1.2a/xml/features");
+    private static final Version VER = Version.version(1, 2, "a", null);
+
+    private Application app1 =
+            new DefaultApplication(id1, VER,
+                    "app1", "origin1", ImmutableSet.of(), Optional.of(FURL),
+                    ImmutableSet.of("My Feature"));
+    private Application app2 =
+            new DefaultApplication(id2, VER,
+                    "app2", "origin2", ImmutableSet.of(), Optional.of(FURL),
+                    ImmutableSet.of("My Feature"));
+    private Application app3 =
+            new DefaultApplication(id3, VER,
+                    "app3", "origin3", ImmutableSet.of(), Optional.of(FURL),
+                    ImmutableSet.of("My Feature"));
+    private Application app4 =
+            new DefaultApplication(id4, VER,
+                    "app4", "origin4", ImmutableSet.of(), Optional.of(FURL),
+                    ImmutableSet.of("My Feature"));
+
+    /**
+     * Hamcrest matcher to check that an device representation in JSON matches
+     * the actual device.
+     */
+    private static class AppJsonMatcher extends TypeSafeMatcher<JsonObject> {
+        private final Application app;
+        private String reason = "";
+
+        public AppJsonMatcher(Application appValue) {
+            app = appValue;
+        }
+
+        @Override
+        public boolean matchesSafely(JsonObject jsonApp) {
+            // check id
+            short jsonId = (short) jsonApp.get("id").asInt();
+            if (jsonId != app.id().id()) {
+                reason = "id " + app.id().id();
+                return false;
+            }
+
+            // check name
+            String jsonName = jsonApp.get("name").asString();
+            if (!jsonName.equals(app.id().name())) {
+                reason = "name " + app.id().name();
+                return false;
+            }
+
+            // check origin
+            String jsonOrigin = jsonApp.get("origin").asString();
+            if (!jsonOrigin.equals(app.origin())) {
+                reason = "manufacturer " + app.origin();
+                return false;
+            }
+
+            return true;
+        }
+
+        @Override
+        public void describeTo(Description description) {
+            description.appendText(reason);
+        }
+    }
+
+    /**
+     * Factory to allocate an device matcher.
+     *
+     * @param app application object we are looking for
+     * @return matcher
+     */
+    private static AppJsonMatcher matchesApp(Application app) {
+        return new AppJsonMatcher(app);
+    }
+
+
+    @Before
+    public void setUp() {
+        service = createMock(ApplicationAdminService.class);
+
+        expect(service.getId("one"))
+                .andReturn(id1)
+                .anyTimes();
+        expect(service.getId("two"))
+                .andReturn(id2)
+                .anyTimes();
+        expect(service.getId("three"))
+                .andReturn(id3)
+                .anyTimes();
+        expect(service.getId("four"))
+                .andReturn(id4)
+                .anyTimes();
+
+        expect(service.getApplication(id3))
+                .andReturn(app3)
+                .anyTimes();
+        expect(service.getState(isA(ApplicationId.class)))
+                .andReturn(ApplicationState.ACTIVE)
+                .anyTimes();
+
+        // Register the services needed for the test
+        CodecManager codecService = new CodecManager();
+        codecService.activate();
+        ServiceDirectory testDirectory =
+                new TestServiceDirectory()
+                        .add(ApplicationAdminService.class, service)
+                        .add(ApplicationService.class, service)
+                        .add(CodecService.class, codecService);
+
+        BaseResource.setServiceDirectory(testDirectory);
+    }
+
+    @After
+    public void shutDown() {
+        verify(service);
+    }
+
+    /**
+     * Tests a GET of all applications when no applications are present.
+     */
+    @Test
+    public void getAllApplicationsEmpty() {
+        expect(service.getApplications())
+                .andReturn(ImmutableSet.of());
+        replay(service);
+
+        WebResource rs = resource();
+        String response = rs.path("applications").get(String.class);
+        assertThat(response, is("{\"applications\":[]}"));
+    }
+
+    /**
+     * Tests a GET of all applications with data.
+     */
+    @Test
+    public void getAllApplicationsPopulated() {
+        expect(service.getApplications())
+                .andReturn(ImmutableSet.of(app1, app2, app3, app4));
+        replay(service);
+
+        WebResource rs = resource();
+        String response = rs.path("applications").get(String.class);
+        assertThat(response, containsString("{\"applications\":["));
+
+        JsonObject result = JsonObject.readFrom(response);
+        assertThat(result, notNullValue());
+
+        assertThat(result.names(), hasSize(1));
+        assertThat(result.names().get(0), is("applications"));
+
+        JsonArray jsonApps = result.get("applications").asArray();
+        assertThat(jsonApps, notNullValue());
+        assertThat(jsonApps.size(), is(4));
+
+        assertThat(jsonApps.get(0).asObject(), matchesApp(app1));
+        assertThat(jsonApps.get(1).asObject(), matchesApp(app2));
+        assertThat(jsonApps.get(2).asObject(), matchesApp(app3));
+        assertThat(jsonApps.get(3).asObject(), matchesApp(app4));
+    }
+
+    /**
+     * Tests a GET of a single application.
+     */
+    @Test
+    public void getSingleApplication() {
+        replay(service);
+
+        WebResource rs = resource();
+        String response = rs.path("applications/three").get(String.class);
+
+        JsonObject result = JsonObject.readFrom(response);
+        assertThat(result, notNullValue());
+
+        assertThat(result, matchesApp(app3));
+    }
+
+    /**
+     * Tests a DELETE of a single application - this should
+     * attempt to uninstall it.
+     */
+    @Test
+    public void deleteApplication() {
+        service.uninstall(id3);
+        expectLastCall();
+
+        replay(service);
+
+        WebResource rs = resource();
+        rs.path("applications/three").delete();
+    }
+
+    /**
+     * Tests a DELETE of a single active application - this should
+     * attempt to uninstall it.
+     */
+    @Test
+    public void deleteActiveApplication() {
+        service.deactivate(id3);
+        expectLastCall();
+
+        replay(service);
+
+        WebResource rs = resource();
+        rs.path("applications/three/active").delete();
+    }
+
+    /**
+     * Tests a POST operation to the "active" URL.  This should attempt to
+     * activate the application.
+     */
+    @Test
+    public void postActiveApplication() {
+        service.activate(id3);
+        expectLastCall();
+
+        replay(service);
+
+        WebResource rs = resource();
+        rs.path("applications/three/active").post();
+    }
+
+    /**
+     * Tests a POST operation.  This should attempt to
+     * install the application.
+     */
+    @Test
+    public void postApplication() {
+        expect(service.install(isA(InputStream.class)))
+                .andReturn(app4)
+                .once();
+
+        replay(service);
+
+        ApplicationCodec codec = new ApplicationCodec();
+        String app4Json = codec.encode(app4,
+                                       new MockCodecContextWithService(service))
+                .asText();
+
+        WebResource rs = resource();
+        String response = rs.path("applications").post(String.class, app4Json);
+
+        JsonObject result = JsonObject.readFrom(response);
+        assertThat(result, notNullValue());
+
+        assertThat(result, matchesApp(app4));
+    }
+}
