/*
 * 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
 */
cryptolib.modules.symmetric = cryptolib.modules.symmetric || {};

/**
 * Defines the symmetric service.
 * @namespace symmetric/service
 */
cryptolib.modules.symmetric.service = function(box) {
  'use strict';

  box.symmetric = box.symmetric || {};
  /**
   * A module that provides symmetric cryptographic services.
   * @exports symmetric/service
   */
  box.symmetric.service = {};

  var cipherFactory, secretKeyFactory, macFactory;

  cryptolib(
      'symmetric.cipher', 'symmetric.secretkey', 'symmetric.mac',
      'commons.exceptions', function(box) {
        cipherFactory =
            new box.symmetric.cipher.factory.SymmetricCipherFactory();
        secretKeyFactory =
            new box.symmetric.secretkey.factory.SecretKeyFactory();
        macFactory = new box.symmetric.mac.factory.MacFactory();
      });

  /**
   * @function getSecretKeyForEncryption
   * @returns {string} a secret key as a string encoded in Base64.
   */
  box.symmetric.service.getSecretKeyForEncryption = function() {
    var secretKeyGenerator =
        secretKeyFactory.getCryptoSecretKeyGeneratorForEncryption();
    return secretKeyGenerator.generate();
  };

  /**
   * @function getSecretKeyForMac
   * @returns {string} a MAC as a string encoded in Base64.
   */
  box.symmetric.service.getSecretKeyForMac = function() {
    var secretKeyGenerator =
        secretKeyFactory.getCryptoSecretKeyGeneratorForMac();
    return secretKeyGenerator.generate();
  };


  /**
   * @function encrypt
   * @returns {string} the initialization vector concatenated with the encrypted data,
   * as string in Base64 encoded format.
   */
  box.symmetric.service.encrypt = function(secretKeyBase64, dataBase64) {
    var cipher = cipherFactory.getCryptoSymmetricCipher();
    return cipher.encrypt(secretKeyBase64, dataBase64);
  };

  /**
   * @function decrypt
   * @returns {string} the decrypted data, as a String in Base64 encoded format.
   */
  box.symmetric.service.decrypt = function(
      secretKeyBase64, initVectorAndEncryptedDataBase64) {
    var cipher = cipherFactory.getCryptoSymmetricCipher();
    return cipher.decrypt(secretKeyBase64, initVectorAndEncryptedDataBase64);
  };

  /**
   * @function getMac
   * @returns {string} a string in Base64 encoded format.
   */
  box.symmetric.service.getMac = function(secretKeyBase64, arrayDataBase64) {
    var cryptoMac = macFactory.create();
    return cryptoMac.generate(secretKeyBase64, arrayDataBase64);
  };

  /**
   * @function verifyMac
   * @returns {boolean} true if the data has been verified.
   */
  box.symmetric.service.verifyMac = function(
      macBase64, secretKeyBase64, arrayDataBase64) {
    var cryptoMac = macFactory.create();
    return cryptoMac.verify(macBase64, secretKeyBase64, arrayDataBase64);
  };
};
