// Copyright (C) 2019 The Android Open Source Project
//
// 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 com.googlesource.gerrit.plugins.websession.broker;

import static com.google.common.truth.Truth.assertThat;
import static org.mockito.Mockito.any;
import static org.mockito.Mockito.anyString;
import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.verifyZeroInteractions;
import static org.mockito.Mockito.when;

import com.gerritforge.gerrit.eventbroker.BrokerApi;
import com.gerritforge.gerrit.eventbroker.EventMessage;
import com.gerritforge.gerrit.eventbroker.EventMessage.Header;
import com.google.common.cache.Cache;
import com.google.common.collect.Maps;
import com.google.common.util.concurrent.MoreExecutors;
import com.google.gerrit.extensions.registration.DynamicItem;
import com.google.gerrit.httpd.WebSessionManager.Val;
import com.google.gerrit.server.config.PluginConfig;
import com.google.gerrit.server.config.PluginConfigFactory;
import com.google.gerrit.server.events.Event;
import com.googlesource.gerrit.plugins.websession.broker.BrokerBasedWebSessionCache.WebSessionEvent;
import com.googlesource.gerrit.plugins.websession.broker.BrokerBasedWebSessionCache.WebSessionEvent.Operation;
import com.googlesource.gerrit.plugins.websession.broker.log.WebSessionLogger;
import com.googlesource.gerrit.plugins.websession.broker.util.TimeMachine;
import java.time.Instant;
import java.util.UUID;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.ExecutorService;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.ArgumentCaptor;
import org.mockito.Captor;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnitRunner;

@RunWith(MockitoJUnitRunner.class)
public class BrokerBasedWebSessionCacheTest {

  private static final int DEFAULT_ACCOUNT_ID = 1000000;
  private static final String KEY = "aSceprtma6B0qZ0hKxXHvQ5iyfUhCcFXxG";
  private static final String PLUGIN_NAME = "websession-broker";

  private byte[] emptyPayload = new byte[] {-84, -19, 0, 5, 112};
  byte[] defaultPayload =
      new byte[] {
        -84, -19, 0, 5, 115, 114, 0, 45, 99, 111, 109, 46, 103, 111, 111, 103, 108, 101, 46, 103,
        101, 114, 114, 105, 116, 46, 104, 116, 116, 112, 100, 46, 87, 101, 98, 83, 101, 115, 115,
        105, 111, 110, 77, 97, 110, 97, 103, 101, 114, 36, 86, 97, 108, 0, 0, 0, 0, 0, 0, 0, 2, 3,
        0, 0, 120, 112, 119, 97, 1, -64, -124, 61, 2, 0, 0, 1, 111, 13, -8, 90, 7, 3, 0, 5, 34, 97,
        83, 99, 101, 112, 114, 113, 86, 87, 54, 85, 79, 45, 88, 51, 107, 51, 116, 102, 85, 109, 86,
        103, 82, 73, 90, 56, 53, 99, 99, 52, 71, 114, 87, 6, 0, 0, 1, 111, 16, 84, -103, -121, 7,
        34, 97, 83, 99, 101, 112, 114, 114, 82, 103, 119, 49, 71, 110, 90, 56, 122, 54, 49, 49, 86,
        52, 121, 110, 65, 100, 110, 113, 99, 68, 45, 105, 99, 75, 97, 0, 120
      };

  ExecutorService executorServce = MoreExecutors.newDirectExecutorService();

  @Mock BrokerApi brokerApi;
  @Mock Cache<String, Val> cache;
  @Mock TimeMachine timeMachine;
  @Mock PluginConfigFactory cfg;
  @Mock PluginConfig pluginConfig;
  @Mock WebSessionLogger webSessionLogger;
  @Captor ArgumentCaptor<EventMessage> eventCaptor;
  @Captor ArgumentCaptor<Val> valCaptor;

  BrokerBasedWebSessionCache objectUnderTest;

  @Before
  public void setup() {
    when(pluginConfig.getString("webSessionTopic", "gerrit_web_session"))
        .thenReturn("gerrit_web_session");
    when(cfg.getFromGerritConfig(PLUGIN_NAME)).thenReturn(pluginConfig);
    when(timeMachine.now()).thenReturn(Instant.EPOCH);
    DynamicItem<BrokerApi> item = DynamicItem.itemOf(BrokerApi.class, brokerApi);
    objectUnderTest =
        new BrokerBasedWebSessionCache(
            cache, item, timeMachine, cfg, PLUGIN_NAME, webSessionLogger, executorServce);
  }

  @Test
  public void shouldPublishMessageWhenLoginEvent() {
    EventMessage eventMessage = createEventMessage();
    Val value = createVal(eventMessage);
    when(brokerApi.newMessage(any(UUID.class), any(Event.class))).thenReturn(eventMessage);

    objectUnderTest.put(KEY, value);
    verify(brokerApi, times(1)).send(anyString(), eventCaptor.capture());

    assertThat(eventCaptor.getValue().getEvent()).isNotNull();
    WebSessionEvent event = (WebSessionEvent) eventCaptor.getValue().getEvent();
    assertThat(event.operation).isEqualTo(WebSessionEvent.Operation.ADD);
    assertThat(event.key).isEqualTo(KEY);
    assertThat(event.payload).isEqualTo(defaultPayload);
  }

  @Test
  public void shouldPublishMessageWhenLogoutEvent() {
    EventMessage eventMessage = createEventMessage(emptyPayload, Operation.REMOVE);
    when(brokerApi.newMessage(any(UUID.class), any(Event.class))).thenReturn(eventMessage);

    objectUnderTest.invalidate(KEY);

    verify(brokerApi, times(1)).send(anyString(), eventCaptor.capture());

    assertThat(eventCaptor.getValue().getEvent()).isNotNull();
    WebSessionEvent event = (WebSessionEvent) eventCaptor.getValue().getEvent();
    assertThat(event.operation).isEqualTo(WebSessionEvent.Operation.REMOVE);
    assertThat(event.key).isEqualTo(KEY);
    assertThat(event.payload).isEqualTo(emptyPayload);
  }

  @Test
  public void shouldUpdateCacheWhenLoginMessageReceived() {
    EventMessage eventMessage = createEventMessage();

    objectUnderTest.processMessage(eventMessage);

    verify(cache, times(1)).put(anyString(), valCaptor.capture());

    assertThat(valCaptor.getValue()).isNotNull();
    Val val = valCaptor.getValue();
    assertThat(val.getAccountId().get()).isEqualTo(DEFAULT_ACCOUNT_ID);
  }

  @Test
  public void shouldUpdateCacheWhenLogoutMessageReceived() {
    EventMessage eventMessage = createEventMessage(emptyPayload, Operation.REMOVE);

    objectUnderTest.processMessage(eventMessage);

    verify(cache, times(1)).invalidate(KEY);
  }

  @Test
  public void shouldSkipCacheUpdateWhenUnknownEventType() {
    Header header =
        new Header(
            UUID.fromString("7cb80dbe-65c4-4f2c-84de-580d98199d4a"),
            UUID.fromString("97711495-1013-414e-bfd2-44776787520d"));
    Event event = new Event("sample-event") {};
    EventMessage eventMessage = new EventMessage(header, event);
    objectUnderTest.processMessage(eventMessage);

    verifyZeroInteractions(cache);
  }

  @Test
  public void shouldSkipCacheUpdateWhenInvalidPayload() {
    EventMessage eventMessage = createEventMessage(new byte[] {1, 2, 3, 4}, Operation.ADD);
    objectUnderTest.processMessage(eventMessage);

    verifyZeroInteractions(cache);
  }

  @Test
  public void shouldSkipCacheUpdateWhenSessionExpired() {
    when(timeMachine.now()).thenReturn(Instant.MAX);
    EventMessage eventMessage = createEventMessage();
    objectUnderTest.processMessage(eventMessage);

    verifyZeroInteractions(cache);
  }

  @Test
  public void shouldCleanupExpiredSessions() {
    when(timeMachine.now()).thenReturn(Instant.MIN, Instant.MAX);

    EventMessage eventMessage = createEventMessage();

    objectUnderTest.processMessage(eventMessage);
    verify(cache, times(1)).put(anyString(), valCaptor.capture());
    assertThat(valCaptor.getValue()).isNotNull();

    ConcurrentMap<String, Val> cacheMap = Maps.newConcurrentMap();
    cacheMap.put(KEY, valCaptor.getValue());
    when(cache.asMap()).thenReturn(cacheMap);

    objectUnderTest.cleanUp();

    verify(cache, times(1)).invalidate(KEY);
  }

  @SuppressWarnings("unchecked")
  private Val createVal(EventMessage message) {
    ArgumentCaptor<Val> valArgumentCaptor = ArgumentCaptor.forClass(Val.class);

    objectUnderTest.processMessage(message);
    verify(cache).put(anyString(), valArgumentCaptor.capture());
    reset(cache);
    return valArgumentCaptor.getValue();
  }

  private EventMessage createEventMessage() {

    return createEventMessage(defaultPayload, Operation.ADD);
  }

  private EventMessage createEventMessage(byte[] payload, Operation operation) {

    Header header =
        new Header(
            UUID.fromString("7cb80dbe-65c4-4f2c-84de-580d98199d4a"),
            UUID.fromString("97711495-1013-414e-bfd2-44776787520d"));
    WebSessionEvent event = new WebSessionEvent(KEY, payload, operation);
    return new EventMessage(header, event);
  }
}
