import {
  E_BLIND_INDEX_PURPOSE_REQUIRED,
  E_INSECURE_ENCRYPTER_KEY,
  E_INVALID_ENCRYPTER_ID,
  E_MISSING_ENCRYPTER_KEY
} from "./chunk-2UOFQLYL.js";
import {
  base64UrlEncode
} from "./chunk-OD6CXVQX.js";

// src/drivers/base_driver.ts
import { createHash, createHmac, hkdfSync } from "crypto";
import { MessageBuilder } from "@poppinss/utils";
var BaseDriver = class {
  /**
   * The key for encrypting values. It is derived
   * from the user provided secret.
   */
  cryptoKey;
  #blindIndexKey;
  /**
   * Use `dot` as a separator for joining encrypted value, iv and the
   * hmac hash. The idea is borrowed from JWTs.
   */
  separator = ".";
  constructor(config) {
    const key = this.#validateAndGetSecret(config.key);
    this.#validateId(config.id);
    this.cryptoKey = createHash("sha256").update(key).digest();
    const rawBlindIndexKey = hkdfSync(
      "sha256",
      this.cryptoKey,
      Buffer.alloc(0),
      Buffer.from(`blind-index:${config.id || "default"}`),
      32
    );
    this.#blindIndexKey = Buffer.isBuffer(rawBlindIndexKey) ? rawBlindIndexKey : Buffer.from(rawBlindIndexKey);
  }
  /**
   * Validates the app secret and returns it back as a string
   */
  #validateAndGetSecret(secret) {
    if (!secret) {
      throw new E_MISSING_ENCRYPTER_KEY();
    }
    const revealedSecret = typeof secret === "string" ? secret : secret.release();
    if (revealedSecret.length < 16) {
      throw new E_INSECURE_ENCRYPTER_KEY();
    }
    return revealedSecret;
  }
  /**
   * Validates encrypter id format when provided.
   */
  #validateId(id) {
    if (typeof id !== "string") {
      return;
    }
    if (id.trim().length === 0 || id.includes(this.separator)) {
      throw new E_INVALID_ENCRYPTER_ID();
    }
  }
  computeReturns(values) {
    return values.join(this.separator);
  }
  blindIndex(payload, purpose) {
    if (typeof purpose !== "string" || purpose.trim().length === 0) {
      throw new E_BLIND_INDEX_PURPOSE_REQUIRED();
    }
    const rawPayload = new MessageBuilder().build(payload);
    const payloadBuffer = Buffer.isBuffer(rawPayload) ? rawPayload : Buffer.from(rawPayload);
    const indexPayload = Buffer.concat([
      Buffer.from(purpose),
      Buffer.from(this.separator),
      payloadBuffer
    ]);
    return base64UrlEncode(createHmac("sha256", this.#blindIndexKey).update(indexPayload).digest());
  }
  blindIndexes(payload, purpose) {
    return [this.blindIndex(payload, purpose)];
  }
};

export {
  BaseDriver
};
/*
 * @boringnode/encryption
 *
 * @license MIT
 * @copyright Boring Node
 */
//# sourceMappingURL=chunk-GF3GWB6X.js.map