/*
 * Copyright 2018 Scytl Secure Electronic Voting SA
 *
 * All rights reserved
 *
 * See our extended copyright notice in *file 'Copyright.txt'
 * which is part of this source code package
 */

package com.scytl.slogger.processor.signature;

import com.scytl.slogger.event.SecureLoggingEvent;
import com.scytl.slogger.event.SecureMessage;
import com.scytl.slogger.event.SecureMessageProperties;
import com.scytl.slogger.event.SecurePatternLayout;
import com.scytl.slogger.processor.EventProcessorException;
import com.scytl.slogger.processor.LoggingEventProcessor;
import com.scytl.slogger.processor.ProcessorTester;
import com.scytl.slogger.validator.LoggingEventValidator;
import com.scytl.slogger.validator.signature.SignatureEventValidator;

import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.LinkedList;
import java.util.List;

/**
 *
 */
public class SignatureEventProcessorTest extends ProcessorTester {

  /**
   * @throws Exception
   */
  public void testProcessor() throws Exception {
    _logger.info(LOG_TRACE);

    SecureMessage firstLog = SecureMessage.newRenderedInstance(_logFileReader.readLine());

    getCryptographyProvider().verify(
        (firstLog.text() + LINE_SEPARATOR).getBytes(StandardCharsets.UTF_8),
        Base64.getDecoder().decode(firstLog.properties().get(SecureMessageProperties.SIGNATURE)
            .getBytes(StandardCharsets.UTF_8)),
        getSignaturePublicKey());

  }

  /**
   * @see com.scytl.slogger.processor.ProcessorTester#getLoggingEventProcessor()
   */
  @Override
  protected LoggingEventProcessor getLoggingEventProcessor() throws Exception {
    return new EventProcessorTest(
        new SignatureEventProcessor(getSignaturePrivateKey(), _cryptographyProvider));
  }

  @Override
  protected LoggingEventValidator getLoggingEventValidator() throws Exception {
    return new SignatureEventValidator(getSignaturePublicKey(), getCryptographyProvider());
  }

  private static final class EventProcessorTest implements LoggingEventProcessor {

    private final SignatureEventProcessor _signatureEventProcessor;

    public EventProcessorTest(final SignatureEventProcessor signatureEventProcessor) {
      super();
      _signatureEventProcessor = signatureEventProcessor;
    }

    @Override
    public void killProcessor() throws EventProcessorException {}

    @Override
    public List<SecureLoggingEvent> processEvent(final SecureLoggingEvent loggingEvent,
        final SecurePatternLayout layout) throws EventProcessorException {
      return _signatureEventProcessor.processEvent(loggingEvent.addProperty("TEST", "TEST_VALUE"),
          layout);
    }

    @Override
    public List<SecureLoggingEvent> startProcessor(final SecurePatternLayout layout)
        throws EventProcessorException {
      return new LinkedList<>();
    }

    @Override
    public List<SecureLoggingEvent> stopProcessor(final SecurePatternLayout layout)
        throws EventProcessorException {
      return _signatureEventProcessor.stopProcessor(layout);
    }
  }
}
