"use strict";
/*!
 * Copyright (c) Microsoft Corporation and contributors. All rights reserved.
 * Licensed under the MIT License.
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.nodeApi = void 0;
const core_utils_1 = require("@fluidframework/core-utils");
const feature_libraries_1 = require("../feature-libraries");
// eslint-disable-next-line import/no-internal-modules
const flexNode_1 = require("../simple-tree/flexNode");
// eslint-disable-next-line import/no-internal-modules
const proxies_1 = require("../simple-tree/proxies");
const schemaFactory_1 = require("./schemaFactory");
const toFlexSchema_1 = require("./toFlexSchema");
/**
 * The `Tree` object holds various functions for analyzing {@link TreeNode}s.
 * @public
 */
exports.nodeApi = {
    parent: (node) => {
        const editNode = (0, flexNode_1.getFlexNode)(node).parentField.parent.parent;
        if (editNode === undefined) {
            return undefined;
        }
        const output = (0, proxies_1.getOrCreateNodeProxy)(editNode);
        (0, core_utils_1.assert)(!(0, feature_libraries_1.isTreeValue)(output), 0x87f /* Parent can't be a leaf, so it should be a node not a value */);
        return output;
    },
    key: (node) => {
        const parentField = (0, flexNode_1.getFlexNode)(node).parentField;
        if (parentField.parent.schema.kind.multiplicity === feature_libraries_1.Multiplicity.Sequence) {
            // The parent of `node` is a list
            return parentField.index;
        }
        // The parent of `node` is an object, a map, or undefined (and therefore `node` is a root/detached node).
        return parentField.parent.key;
    },
    on: (node, eventName, listener) => {
        return (0, flexNode_1.getFlexNode)(node).on(eventName, listener);
    },
    status: (node) => {
        return (0, flexNode_1.getFlexNode)(node).treeStatus();
    },
    is: (value, schema) => {
        const flexSchema = (0, toFlexSchema_1.getFlexSchema)(schema);
        if ((0, feature_libraries_1.isTreeValue)(value)) {
            return (flexSchema instanceof feature_libraries_1.LeafNodeSchema && (0, feature_libraries_1.valueSchemaAllows)(flexSchema.info, value));
        }
        return (0, flexNode_1.tryGetFlexNode)(value)?.is(flexSchema) ?? false;
    },
    schema(node) {
        if ((0, feature_libraries_1.isTreeValue)(node)) {
            return (0, schemaFactory_1.schemaFromValue)(node);
        }
        return (0, proxies_1.getClassSchema)((0, flexNode_1.getFlexNode)(node).schema);
    },
};
//# sourceMappingURL=treeApi.js.map