/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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.apache.slider.server.appmaster.model.monkey

import groovy.transform.CompileStatic
import groovy.util.logging.Slf4j
import org.apache.hadoop.yarn.conf.YarnConfiguration
import org.apache.slider.server.appmaster.actions.ActionHalt
import org.apache.slider.server.appmaster.actions.ActionKillContainer
import org.apache.slider.server.appmaster.actions.QueueService
import org.apache.slider.server.appmaster.model.mock.BaseMockAppStateTest
import org.apache.slider.server.appmaster.model.mock.MockRMOperationHandler
import org.apache.slider.server.appmaster.monkey.ChaosKillAM
import org.apache.slider.server.appmaster.monkey.ChaosKillContainer
import org.apache.slider.server.appmaster.monkey.ChaosMonkeyService
import org.apache.slider.server.appmaster.monkey.ChaosTarget
import org.apache.slider.server.appmaster.operations.ContainerReleaseOperation
import org.apache.slider.server.appmaster.state.RoleInstance
import org.junit.Before
import org.junit.Test

@CompileStatic
@Slf4j
class TestMockMonkey extends BaseMockAppStateTest {

  /**
   * This queue service is NOT started; tests need to poll the queue
   * rather than expect them to execute
   */
  QueueService queues = new QueueService();
  ChaosMonkeyService monkey = new ChaosMonkeyService(metricRegistry,
  queues)

  @Before
  public void init() {
    def configuration = new YarnConfiguration()
    queues.init(configuration)
    monkey.init(configuration)
  }
  
  @Test
  public void testMonkeyStart() throws Throwable {
    monkey.start()
    monkey.stop()
  }


  @Test
  public void testMonkeyPlay() throws Throwable {
    ChaosCounter counter = new ChaosCounter()
    monkey.addTarget("target", counter, ChaosMonkeyService.PERCENT_100)
    
    monkey.play()
    assert counter.count == 1
  }

  @Test
  public void testMonkeyPlaySometimes() throws Throwable {
    ChaosCounter counter = new ChaosCounter()
    ChaosCounter counter2 = new ChaosCounter()
    monkey.addTarget("target1", counter, ChaosMonkeyService.PERCENT_1 * 50)
    monkey.addTarget("target2", counter2, ChaosMonkeyService.PERCENT_1 * 25)

    for (int i = 0; i < 100; i++) {
      monkey.play()
    }
    log.info("Counter1 = ${counter.count} counter2 = ${counter2.count}")
    /*
     * Relying on probability here to give approximate answers 
     */
    assert counter.count > 25 
    assert counter.count < 75 
    assert counter2.count < counter.count 
  }

  @Test
  public void testAMKiller() throws Throwable {

    def chaos = new ChaosKillAM(queues, -1)
    chaos.chaosAction();
    assert queues.scheduledActions.size() == 1
    def action = queues.scheduledActions.take()
    assert action instanceof ActionHalt
  }
  
  
  @Test
  public void testContainerKillerEmptyApp() throws Throwable {

    
    def chaos = new ChaosKillContainer(appState,
        queues,
        new MockRMOperationHandler())
    chaos.chaosAction();
    assert queues.scheduledActions.size() == 0
  }
  
   
  
  @Test
  public void testContainerKiller() throws Throwable {
    MockRMOperationHandler ops = new MockRMOperationHandler();
    role0Status.desired = 1
    List<RoleInstance> instances = createAndStartNodes()
    assert instances.size() == 1
    def instance = instances[0]
    
    def chaos = new ChaosKillContainer(appState, queues, ops)
    chaos.chaosAction();
    assert queues.scheduledActions.size() == 1
    def action = queues.scheduledActions.take()
    ActionKillContainer killer = (ActionKillContainer) action
    assert killer.containerId == instance.containerId;
    killer.execute(null, queues, appState)
    assert ops.releases == 1;

    ContainerReleaseOperation operation = (ContainerReleaseOperation) ops.operations[0]
    assert operation.containerId == instance.containerId
  }
  
  

  /**
   * Chaos target that just implement a counter
   */
  private static class ChaosCounter implements ChaosTarget {
    int count;
    
    @Override
    void chaosAction() {
      count++;
    }


    @Override
    public String toString() {
      final StringBuilder sb = new StringBuilder(
          "ChaosCounter{");
      sb.append("count=").append(count);
      sb.append('}');
      return sb.toString();
    }
  }
}
