Skip to content
Merged
Show file tree
Hide file tree
Changes from 9 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,15 @@
import type { Document, YAMLMap } from 'yaml';
import { isMap, isPair, isScalar, visit } from 'yaml';

export function isStepLikeMap(item: unknown): item is YAMLMap {
if (!item || !isMap(item)) return false;
const items = (item as YAMLMap).items;
if (!items) return false;
const hasName = items.some((p) => isPair(p) && isScalar(p.key) && p.key.value === 'name');
const hasType = items.some((p) => isPair(p) && isScalar(p.key) && p.key.value === 'type');
return hasName && hasType;
}

export function getStepNodesWithType(yamlDocument: Document): YAMLMap[] {
const stepNodes: YAMLMap[] = [];

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
/*
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
* or more contributor license agreements. Licensed under the "Elastic License
* 2.0", the "GNU Affero General Public License v3.0 only", and the "Server Side
* Public License v 1"; you may not use this file except in compliance with, at
* your election, the "Elastic License 2.0", the "GNU Affero General Public
* License v3.0 only", or the "Server Side Public License, v 1".
*/

import type { Document, Node } from 'yaml';
import { isScalar, isSeq, visit } from 'yaml';

export interface StepsElseKeyOffsets {
stepsKeyStartOffsets: number[];
elseKeyStartOffsets: number[];
}

export function getStepsAndElseKeyOffsets(document: Document): StepsElseKeyOffsets {
const stepsKeyStartOffsets: number[] = [];
const elseKeyStartOffsets: number[] = [];

visit(document, {
Pair(_key, pair) {
if (!pair.key || !isScalar(pair.key)) return;
const keyVal = pair.key.value;
if (keyVal !== 'steps' && keyVal !== 'else') return;
const keyNode = pair.key as Node;
if (!keyNode.range) return;
const startOffset = keyNode.range[0];
if (keyVal === 'steps') {
stepsKeyStartOffsets.push(startOffset);
} else {
elseKeyStartOffsets.push(startOffset);
}
},
});

return { stepsKeyStartOffsets, elseKeyStartOffsets };
}

export interface BlockKeyInfo {
keyStartOffset: number;
rangeStart: number;
rangeEnd: number;
}

export function getInnermostBlockContainingOffset(
document: Document,
cursorOffset: number
): BlockKeyInfo | null {
const candidates: BlockKeyInfo[] = [];

visit(document, {
Pair(_key, pair) {
if (!pair.key || !isScalar(pair.key)) return;
const keyVal = pair.key.value;
if (keyVal !== 'steps' && keyVal !== 'else') return;
const seq = pair.value;
if (!isSeq(seq) || !seq.range) return;
const keyNode = pair.key as Node;
if (!keyNode.range) return;
const [rangeStart, , rangeEnd] = seq.range as number[];
if (cursorOffset >= rangeStart && cursorOffset <= rangeEnd) {
candidates.push({
keyStartOffset: keyNode.range[0],
rangeStart,
rangeEnd,
});
}
},
});

if (candidates.length === 0) return null;
candidates.sort((a, b) => a.rangeEnd - a.rangeStart - (b.rangeEnd - b.rangeStart));
return candidates[0];
}
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,15 @@
*/

export { getPathAtOffset, getPathFromAncestors } from '@kbn/workflows/common/utils/yaml';
export {
getInnermostBlockContainingOffset,
getStepsAndElseKeyOffsets,
type BlockKeyInfo,
type StepsElseKeyOffsets,
} from './get_steps_else_key_offsets';
export { getStepNodeAtPosition } from './get_step_node_at_position';
export { getStepNode } from './get_step_node';
export { getStepNodesWithType } from './get_step_nodes_with_type';
export { getStepNodesWithType, isStepLikeMap } from './get_step_nodes_with_type';
export { getTriggerNodes, getTriggersPair } from './get_trigger_nodes';
export { getTriggerNodesWithType } from './get_trigger_nodes_with_type';
export { parseWorkflowYamlToJSON } from './parse_workflow_yaml_to_json';
Expand Down
Loading
Loading