/*
 * 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 com.google.common.collect.ImmutableSet;
import com.sun.jersey.api.client.UniformInterfaceException;
import com.sun.jersey.api.client.WebResource;
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.cfg.ComponentConfigAdapter;
import org.onosproject.cfg.ComponentConfigService;
import org.onosproject.cfg.ConfigProperty;

import java.util.Set;

import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.containsString;
import static org.hamcrest.Matchers.not;
import static org.junit.Assert.assertEquals;
import static org.onosproject.cfg.ConfigProperty.Type.INTEGER;
import static org.onosproject.cfg.ConfigProperty.Type.STRING;
import static org.onosproject.cfg.ConfigProperty.defineProperty;

/**
 * Test of the component config REST API.
 */
public class ComponentConfigWebResourceTest extends ResourceTest {

    private TestConfigManager service;

    @Before
    public void setUp() {
        service = new TestConfigManager();
        ServiceDirectory testDirectory =
                new TestServiceDirectory()
                        .add(ComponentConfigService.class, service);
        BaseResource.setServiceDirectory(testDirectory);
    }

    @Test
    public void getAllConfigs() {
        WebResource rs = resource();
        String response = rs.path("configuration").get(String.class);
        assertThat(response, containsString("\"foo\":"));
        assertThat(response, containsString("\"bar\":"));
    }

    @Test
    public void getConfigs() {
        WebResource rs = resource();
        String response = rs.path("configuration/foo").get(String.class);
        assertThat(response, containsString("{\"foo\":"));
        assertThat(response, not(containsString("{\"bar\":")));
    }

    @Test
    public void setConfigs() {
        WebResource rs = resource();
        try {
            rs.path("configuration/foo").post(String.class, "{ \"k\" : \"v\" }");
        } catch (UniformInterfaceException e) {
            assertEquals("incorrect key", "foo", service.component);
            assertEquals("incorrect key", "k", service.name);
            assertEquals("incorrect value", "v", service.value);
        }
    }

    @Test
    public void unsetConfigs() {
        WebResource rs = resource();
        try {
            rs.path("configuration/foo").delete(String.class, "{ \"k\" : \"v\" }");
        } catch (UniformInterfaceException e) {
            assertEquals("incorrect key", "foo", service.component);
            assertEquals("incorrect key", "k", service.name);
            assertEquals("incorrect value", null, service.value);
        }
    }


    private class TestConfigManager extends ComponentConfigAdapter {

        private String component;
        private String name;
        private String value;

        @Override
        public Set<String> getComponentNames() {
            return ImmutableSet.of("foo", "bar");
        }

        @Override
        public void setProperty(String componentName, String name, String value) {
            this.component = componentName;
            this.name = name;
            this.value = value;
        }

        @Override
        public void unsetProperty(String componentName, String name) {
            this.component = componentName;
            this.name = name;
            this.value = null;
        }

        @Override
        public Set<ConfigProperty> getProperties(String componentName) {
            return ImmutableSet.of(defineProperty("k1", STRING, "d1", "dv1"),
                                   defineProperty("k2", INTEGER, "d2", "321"));
        }
    }
}