// Copyright (C) 2013 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.google.gerrit.server.securestore;

import com.google.common.collect.Lists;
import java.util.List;

/**
 * Abstract class for providing new SecureStore implementation for Gerrit.
 *
 * <p>SecureStore is responsible for storing sensitive data like passwords in a secure manner.
 *
 * <p>It is implementator's responsibility to encrypt and store values.
 *
 * <p>To deploy new SecureStore one needs to provide a jar file with explicitly one class that
 * extends {@code SecureStore} and put it in Gerrit server. Then run:
 *
 * <p>`java -jar gerrit.war SwitchSecureStore -d $gerrit_site --new-secure-store-lib
 * $path_to_new_secure_store.jar`
 *
 * <p>on stopped Gerrit instance.
 */
public abstract class SecureStore {
  /** Describes {@link SecureStore} entry */
  public static class EntryKey {
    public final String name;
    public final String section;
    public final String subsection;

    /** Creates EntryKey */
    public EntryKey(String section, String subsection, String name) {
      this.name = name;
      this.section = section;
      this.subsection = subsection;
    }
  }

  /**
   * Extract decrypted value of stored property from SecureStore or {@code null} when property was
   * not found.
   *
   * @return decrypted String value or {@code null} if not found
   */
  public final String get(String section, String subsection, String name) {
    String[] values = getList(section, subsection, name);
    if (values != null && values.length > 0) {
      return values[0];
    }
    return null;
  }

  /**
   * Extract decrypted value of stored plugin config property from SecureStore or {@code null} when
   * property was not found.
   *
   * @return decrypted String value or {@code null} if not found
   */
  public final String getForPlugin(
      String pluginName, String section, String subsection, String name) {
    String[] values = getListForPlugin(pluginName, section, subsection, name);
    if (values != null && values.length > 0) {
      return values[0];
    }
    return null;
  }

  /**
   * Extract list of plugin config values from SecureStore and decrypt every value in that list, or
   * {@code null} when property was not found.
   *
   * @return decrypted list of string values or {@code null}
   */
  public abstract String[] getListForPlugin(
      String pluginName, String section, String subsection, String name);

  /**
   * Extract list of values from SecureStore and decrypt every value in that list or {@code null}
   * when property was not found.
   *
   * @return decrypted list of string values or {@code null}
   */
  public abstract String[] getList(String section, String subsection, String name);

  /**
   * Store single value in SecureStore.
   *
   * <p>This method is responsible for encrypting value and storing it.
   *
   * @param value plain text value
   */
  public final void set(String section, String subsection, String name, String value) {
    setList(section, subsection, name, Lists.newArrayList(value));
  }

  /**
   * Store list of values in SecureStore.
   *
   * <p>This method is responsible for encrypting all values in the list and storing them.
   *
   * @param values list of plain text values
   */
  public abstract void setList(String section, String subsection, String name, List<String> values);

  /**
   * Remove value for given {@code section}, {@code subsection} and {@code name} from SecureStore.
   */
  public abstract void unset(String section, String subsection, String name);

  /** Returns list of stored entries. */
  public abstract Iterable<EntryKey> list();

  /** Returns <code>true</code> if currently loaded values are outdated */
  public abstract boolean isOutdated();

  /** Reload the values */
  public abstract void reload();
}
