/*!
 * Copyright (c) Microsoft Corporation and contributors. All rights reserved.
 * Licensed under the MIT License.
 */
import { SequenceField as SF } from "../../../feature-libraries/index.js";
import { ChangesetLocalId, DeltaFieldChanges, RevisionInfo, RevisionMetadataSource, RevisionTag, TaggedChange } from "../../../core/index.js";
import { TestChange } from "../../testChange.js";
import { IdAllocator } from "../../../util/index.js";
import { RebaseRevisionMetadata } from "../../../feature-libraries/modular-schema/index.js";
import { CellOrderingMethod, SequenceConfig } from "../../../feature-libraries/sequence-field/config.js";
import { Changeset } from "../../../feature-libraries/sequence-field/index.js";
import { TestChangeset } from "./testEdits.js";
export declare function assertChangesetsEqual<T>(actual: SF.Changeset<T>, expected: SF.Changeset<T>): void;
export declare function purgeUnusedCellOrderingInfo<T>(change: SF.Changeset<T>): SF.Changeset<T>;
export declare function skipOnLineageMethod(config: SequenceConfig, title: string, fn: () => void): void;
export declare function onlyOnLineageMethod(config: SequenceConfig, title: string, fn: () => void): void;
export declare function skipOnTombstoneMethod(config: SequenceConfig, title: string, fn: () => void): void;
export declare function onlyOnTombstoneMethod(config: SequenceConfig, title: string, fn: () => void): void;
export declare function describeForBothConfigs(title: string, fn: (config: SequenceConfig) => void): void;
export declare function withOrderingMethod(method: CellOrderingMethod, fn: (config: SequenceConfig) => void): void;
export declare function composeNoVerify(changes: TaggedChange<TestChangeset>[], revInfos?: RevisionInfo[]): TestChangeset;
export declare function compose(changes: TaggedChange<TestChangeset>[], revInfos?: RevisionInfo[] | RevisionMetadataSource, childComposer?: (change1: TestChange | undefined, change2: TestChange | undefined) => TestChange): TestChangeset;
export declare function prune(change: TestChangeset, childPruner?: (child: TestChange) => TestChange | undefined): TestChangeset;
export declare function shallowCompose<T>(changes: TaggedChange<SF.Changeset<T>>[], revInfos?: RevisionInfo[]): SF.Changeset<T>;
export interface RebaseConfig {
    readonly metadata?: RebaseRevisionMetadata;
    readonly childRebaser?: (child: TestChange | undefined, base: TestChange | undefined) => TestChange | undefined;
}
export declare function rebase(change: TestChangeset, base: TaggedChange<TestChangeset>, config?: RebaseConfig): TestChangeset;
export declare function rebaseTagged(change: TaggedChange<TestChangeset>, baseChange: TaggedChange<TestChangeset>): TaggedChange<TestChangeset>;
export declare function rebaseOverChanges(change: TaggedChange<TestChangeset>, baseChanges: TaggedChange<TestChangeset>[], revInfos?: RevisionInfo[]): TaggedChange<TestChangeset>;
export declare function rebaseOverComposition(change: TestChangeset, base: TestChangeset, metadata: RebaseRevisionMetadata): TestChangeset;
export declare function invert(change: TaggedChange<TestChangeset>): TestChangeset;
export declare function checkDeltaEquality(actual: TestChangeset, expected: TestChangeset): void;
export declare function toDelta(change: TestChangeset, revision?: RevisionTag): DeltaFieldChanges;
export declare function getMaxId(...changes: SF.Changeset<unknown>[]): ChangesetLocalId | undefined;
export declare function getMaxIdTagged(changes: TaggedChange<SF.Changeset<unknown>>[]): ChangesetLocalId | undefined;
export declare function continuingAllocator(changes: TaggedChange<SF.Changeset<unknown>>[]): IdAllocator;
export declare function withoutLineage<T>(changeset: SF.Changeset<T>): SF.Changeset<T>;
export declare function withoutTombstones<T>(changeset: SF.Changeset<T>): SF.Changeset<T>;
export declare function withNormalizedLineage<T>(changeset: SF.Changeset<T>): SF.Changeset<T>;
/**
 * Keeps track of the different ways detached nodes may be referred to.
 * Allows updating changesets so they refer to a detached node by the details
 * of the last detach that affected them.
 *
 * WARNING: this code consumes O(N) space and time for marks that affect N nodes.
 * This is code is currently meant for usage in tests.
 * It should be tested and made more efficient before production use.
 */
export declare class DetachedNodeTracker {
    private nodes;
    private readonly equivalences;
    constructor();
    /**
     * Updates the internals of this instance to account for `change` having been applied.
     * @param change - The change that is being applied. Not mutated.
     * Must be applicable (i.e., `isApplicable(change)` must be true).
     */
    apply(change: TaggedChange<Changeset<unknown>>): void;
    /**
     * Checks whether the given `change` is applicable based on previous changes.
     * @param change - The change to verify the applicability of. Not mutated.
     * @returns false iff `change`'s description of detached nodes is inconsistent with that of changes applied
     * earlier. Returns true otherwise.
     */
    isApplicable(change: Changeset<unknown>): boolean;
    /**
     * Creates an updated representation of the given `change` so that it refers to detached nodes using the revision
     * that last detached them.
     * @param change - The change to update. Not mutated.
     * Must be applicable (i.e., `isApplicable(change)` must be true).
     * @param genId - An ID allocator that produces ID unique within this changeset.
     * @returns A change equivalent to `change` that refers to detached nodes using the revision that last detached
     * them. May reuse parts of the input `change` structure.
     */
    update<T>(change: TaggedChange<Changeset<T>>): TaggedChange<Changeset<T>>;
    private updateMark;
    private getUpdatedDetach;
}
/**
 * Checks whether `branch` changeset is consistent with a `target` changeset that is may be rebased over.
 *
 * WARNING: this code consumes O(N) space and time for marks that affect N nodes.
 * This is code is currently meant for usage in tests.
 * It should be tested and made more efficient before production use.
 *
 * @param branch - The changeset that would be rebased over `target`.
 * @param target - The changeset that `branch` would be rebased over.
 * @returns false iff `branch`'s description of detached nodes is inconsistent with that of `target`.
 * Returns true otherwise.
 */
export declare function areRebasable(branch: Changeset<unknown>, target: Changeset<unknown>): boolean;
/**
 * Checks whether sequential changesets are consistent.
 *
 * WARNING: this code consumes O(N) space and time for marks that affect N nodes.
 * This is code is currently meant for usage in tests.
 * It should be tested and made more efficient before production use.
 *
 * @param changes - The changesets that would be composed together.
 * @returns false iff the changesets in `changes` are inconsistent/incompatible in their description of detached nodes.
 * Returns true otherwise.
 */
export declare function areComposable(changes: TaggedChange<Changeset<unknown>>[]): boolean;
//# sourceMappingURL=utils.d.ts.map