import FragmentBase from '../FragmentBase.js';
import SequenceFragment from './SequenceFragment.js';
import { DestructuredFragment } from '../@types';
/**
 * TimestampFragment class for timestamp IDs.
 * @public
 */
export default class TimestampFragment extends FragmentBase {
  /**
   * Reference to the SequenceFragment instance.
   * This is used to check for sequence collisions,
   * and to reset the sequence when necessary.
   */
  private sequenceFragmentRef;
  /**
   * Value of the last timestamp.
   */
  private lastTimestamp;
  /**
   * Epoch timestamp used to calculate the fragment's timestamps.
   * @readonly
   */
  private readonly epoch;
  /**
   * Time unit used to convert the nanosecond timestamp to.
   * - `1`: nanosecond
   * - `10 ** 3`: microsecond
   * - `10 ** 6`: millisecond
   * @readonly
   */
  private readonly timeUnit;
  /**
   * Nanosecond time reference.
   *
   * @remarks
   * Date.now() returns the number of milliseconds since the Unix epoch.
   * hrtime.bigint() returns a high-resolution time value in nanoseconds,
   * however it is relative to an arbitrary time in the past and not the Unix epoch.
   *
   * If `x` hrtime was taken at `y` Unix timestamp, then when we recapture a
   * hrttime at `x'` we can calculate the time with the following formula:
   *
   * `y + (x' - x)` or `(y - x) + x'`
   * @readonly
   */
  private readonly nanoTimeAnchor;
  /**
   * @param bits - The number of bits for the fragment.
   * @param epoch - A custom epoch timestamp.
   *
   * Defaults to `1420070400000` (2015-01-01 00:00:00) if omitted.
   *
   * @throws `[TIMESTAMP_BITS_INVALID_RANGE]` If bits is less than 38
   * @throws `[EPOCH_INVALID_TYPE]` If epoch is not a number
   * @throws `[EPOCH_INVALID_RANGE]` If epoch is not within 0 and Date.now()
   */
  constructor(bits: number, epoch?: number);
  /**
   * @internal
   */
  set sequenceFragmentReference(sequenceFragment: SequenceFragment);
  getValue(): bigint;
  destructure(snowflake: number | bigint | string): DestructuredFragment;
  /**
   * Returns a Unix timestamp.
   *
   * @remarks
   * The number of the fragment's bits defines the time unit.
   * This is done to avoid overflow when left shifting.
   *
   * @returns A Unix timestamp in the fragment's time unit.
   * @internal
   */
  private unixNow;
  /**
   * Wait for the next timestamp.
   * @internal
   */
  private waitForNextTimestamp;
  /**
   * Check for sequence collision.
   *
   * @remarks
   * If a sequence completes its cycle, and the timestamp
   * is still the same, an already generated snowflake will
   * be re-generated.
   * @internal
   */
  private checkForSequenceCollision;
}
