import { Mutex, MutexInterface, withTimeout } from 'async-mutex';

import { getOptions } from '../../../common/options/optionsUtils';
import {
  OptionCodename,
  OptionsValues,
} from '../../../common/options/optionsPrototype';
import { OptionsConfiguration } from '../../../common/options/OptionsConfiguration';
import {
  OptionsChangeListener,
  OptionsProviderPort,
} from '../../../services/options/OptionsProvider';

// Prioritize reads before writes.
const kReadPriority = 10;
const kWritePriority = 0;

/**
 * Class which provides option values and a way to listen to option changes.
 */
export default class OptionsProviderAdapter implements OptionsProviderPort {
  private optionsConfiguration: OptionsConfiguration;
  private mutex: MutexInterface = withTimeout(new Mutex(), 60 * 1000);
  private listeners: Set<OptionsChangeListener> = new Set();
  private isSetUp = false;

  async getOptionValue<O extends OptionCodename>(
    option: O,
  ): Promise<OptionsValues[O]> {
    this.setUp();
    return this.mutex.runExclusive(
      () => this.optionsConfiguration.getOptionValue(option),
      kReadPriority,
    );
  }

  async isEnabled(option: OptionCodename): Promise<boolean> {
    return (await this.getOptionsConfiguration()).isEnabled(option);
  }

  async getOptionsConfiguration(): Promise<OptionsConfiguration> {
    this.setUp();
    return this.mutex.runExclusive(
      () => this.optionsConfiguration,
      kReadPriority,
    );
  }

  async getOptionsValues(): Promise<OptionsValues> {
    return (await this.getOptionsConfiguration()).optionsValues;
  }

  addListener(listener: OptionsChangeListener) {
    this.setUp();
    this.listeners.add(listener);
  }

  private setUp() {
    if (this.isSetUp) return;

    this.isSetUp = true;
    this.listenForStorageChanges();
    this.updateValues();
  }

  /**
   * Sets up a listener to update the current cached configuration when there
   * are changes to the underlying storage where options are persisted.
   *
   * We could try only doing this only when we're sure it has changed, but
   * there are many factors (if the user has changed it manually, if a kill
   * switch was activated, etc.) so we do it every time there is any change in
   * the underlying storage.
   */
  private listenForStorageChanges() {
    chrome.storage.onChanged.addListener((_, areaName) => {
      if (areaName !== 'sync') return;
      console.debug('[OptionsProvider] Retrieving updated options.');
      this.updateValues();
    });
  }

  private async updateValues() {
    await this.mutex.runExclusive(async () => {
      await this.nonSafeUpdateValues();
    }, kWritePriority);
  }

  private async nonSafeUpdateValues() {
    const previousConfiguration = this.optionsConfiguration;
    const currentOptionsValues = await getOptions(null);
    this.optionsConfiguration = new OptionsConfiguration(currentOptionsValues);

    this.notifyListenersIfApplicable(previousConfiguration);
  }

  private async notifyListenersIfApplicable(
    previousOptionsConfiguration: OptionsConfiguration,
  ) {
    if (
      !previousOptionsConfiguration ||
      this.optionsConfiguration.isEqualTo(previousOptionsConfiguration)
    ) {
      return;
    }

    for (const listener of this.listeners) {
      listener(previousOptionsConfiguration, this.optionsConfiguration);
    }
  }
}
