/*
 * Copyright 2016-present 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.codec.impl;

import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.junit.Before;
import org.junit.Test;
import org.onlab.packet.VlanId;
import org.onosproject.codec.JsonCodec;
import org.onosproject.core.CoreService;
import org.onosproject.net.flow.DefaultTrafficSelector;
import org.onosproject.net.flow.TrafficSelector;
import org.onosproject.net.flow.criteria.Criteria;
import org.onosproject.net.flow.criteria.Criterion;
import org.onosproject.net.flowobjective.DefaultForwardingObjective;
import org.onosproject.net.flowobjective.ForwardingObjective;

import java.io.IOException;
import java.io.InputStream;

import static org.easymock.EasyMock.createMock;
import static org.easymock.EasyMock.expect;
import static org.easymock.EasyMock.replay;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.notNullValue;
import static org.onosproject.codec.impl.ForwardingObjectiveJsonMatcher.matchesForwardingObjective;
import static org.onosproject.net.NetTestTools.APP_ID;

/**
 * Unit tests for ForwardingObjective Codec.
 */
public class ForwardingObjectiveCodecTest {

    MockCodecContext context;
    JsonCodec<ForwardingObjective> forwardingObjectiveCodec;
    final CoreService mockCoreService = createMock(CoreService.class);

    /**
     * Sets up for each test.
     * Creates a context and fetches the ForwardingObjective codec.
     */
    @Before
    public void setUp() {
        context = new MockCodecContext();
        forwardingObjectiveCodec = context.codec(ForwardingObjective.class);
        assertThat(forwardingObjectiveCodec, notNullValue());

        expect(mockCoreService.registerApplication(ForwardingObjectiveCodec.REST_APP_ID))
                .andReturn(APP_ID).anyTimes();
        replay(mockCoreService);
        context.registerService(CoreService.class, mockCoreService);
    }

    /**
     * Tests encoding of a ForwardingObjective object.
     */
    @Test
    public void testForwardingObjectiveEncode() {

        Criterion criterion1 = Criteria.matchVlanId(VlanId.ANY);
        Criterion criterion2 = Criteria.matchEthType((short) 0x8844);
        TrafficSelector selector = DefaultTrafficSelector.builder()
                .add(criterion1)
                .add(criterion2)
                .build();

        ForwardingObjective forwardingObj = DefaultForwardingObjective.builder()
                .makePermanent()
                .fromApp(APP_ID)
                .withPriority(60)
                .withFlag(ForwardingObjective.Flag.SPECIFIC)
                .nextStep(1)
                .withSelector(selector)
                .add();

        ObjectNode forwardingObjJson = forwardingObjectiveCodec.encode(forwardingObj, context);
        assertThat(forwardingObjJson, matchesForwardingObjective(forwardingObj));
    }

    /**
     * Test decoding of a ForwardingObjective object.
     */
    @Test
    public void testForwardingObjectiveDecode() throws IOException {
        ForwardingObjective forwardingObjective = getForwardingObjective("ForwardingObjective.json");

        assertThat(forwardingObjective.flag(), is(ForwardingObjective.Flag.SPECIFIC));
        assertThat(forwardingObjective.priority(), is(60));
        assertThat(forwardingObjective.timeout(), is(1));
        assertThat(forwardingObjective.op(), is(ForwardingObjective.Operation.ADD));
        assertThat(forwardingObjective.permanent(), is(false));
    }

    /**
     * Reads in a forwardingObjectiveJsonCodec from the given resource and decodes it.
     *
     * @param resourceName resource to use to read the JSON for the rule
     * @return decoded forwardingObjectiveJsonCodec
     * @throws IOException if processing the resource fails
     */
    private ForwardingObjective getForwardingObjective(String resourceName) throws IOException {
        InputStream jsonStream = ForwardingObjectiveCodecTest.class.getResourceAsStream(resourceName);
        JsonNode json = context.mapper().readTree(jsonStream);
        assertThat(json, notNullValue());
        ForwardingObjective forwardingObjective = forwardingObjectiveCodec.decode((ObjectNode) json, context);
        assertThat(forwardingObjective, notNullValue());
        return forwardingObjective;
    }
}
