@eagleoutice/flowr
Version:
Static Dataflow Analyzer and Program Slicer for the R Programming Language
128 lines (127 loc) • 5.67 kB
TypeScript
import { RType } from '../r-bridge/lang-4.x/ast/model/type';
import { VertexType } from '../dataflow/graph/vertex';
import type { ParentInformation } from '../r-bridge/lang-4.x/ast/model/processing/decorate';
import type { FlowrSearchElement } from './flowr-search';
import { Enrichment } from './search-executor/search-enrichers';
import type { DataflowInformation } from '../dataflow/info';
import type { BuiltInProcName } from '../dataflow/environments/built-in-proc-name';
export type FlowrFilterName = keyof typeof FlowrFilters;
interface FlowrFilterWithArgs<Filter extends FlowrFilterName, Args extends FlowrFilterArgs<Filter>> {
name: Filter;
args: Args;
}
export declare enum FlowrFilter {
/**
* Drops search elements that represent empty arguments. Specifically, all nodes that are arguments and have an undefined name are skipped.
* This filter does not accept any arguments.
*/
DropEmptyArguments = "drop-empty-arguments",
/**
* Only returns search elements whose enrichments' JSON representations match a given test regular expression.
* This filter accepts {@link MatchesEnrichmentArgs}, which includes the enrichment to match for, as well as the regular expression to test the enrichment's (non-pretty-printed) JSON representation for.
* To test for included function names in an enrichment like {@link Enrichment.CallTargets}, the helper function {@link testFunctionsIgnoringPackage} can be used.
*/
MatchesEnrichment = "matches-enrichment",
/**
* Only returns search elements whose {@link FunctionOriginInformation} match a given pattern or value.
* This filter accepts {@link OriginKindArgs}, which includes the {@link DataflowGraphVertexFunctionCall.origin} to match for, whether to match for every or some origins, and whether to include non-function-calls in the filtered query.
*/
OriginKind = "origin-kind"
}
export type FlowrFilterFunction<T> = (e: FlowrSearchElement<ParentInformation>, args: T, data: {
dataflow: DataflowInformation;
}) => boolean;
export declare const ValidFlowrFilters: Set<string>;
export declare const ValidFlowrFiltersReverse: {
[k: string]: string;
};
export declare const FlowrFilters: {
readonly "drop-empty-arguments": (e: FlowrSearchElement<ParentInformation>, _args: never) => boolean;
readonly "matches-enrichment": (e: FlowrSearchElement<ParentInformation>, args: MatchesEnrichmentArgs<Enrichment>) => boolean;
readonly "origin-kind": (e: FlowrSearchElement<ParentInformation>, args: OriginKindArgs, data: {
dataflow: DataflowInformation;
}) => boolean;
};
export type FlowrFilterArgs<F extends FlowrFilter> = typeof FlowrFilters[F] extends FlowrFilterFunction<infer Args> ? Args : never;
export interface MatchesEnrichmentArgs<E extends Enrichment> {
enrichment: E;
test: RegExp;
}
export interface OriginKindArgs {
origin: BuiltInProcName | RegExp;
matchType?: 'some' | 'every';
keepNonFunctionCalls?: boolean;
}
/**
* Helper to create a regular expression that matches function names, ignoring their package.
*/
export declare function testFunctionsIgnoringPackage(functions: readonly string[]): RegExp;
type ValidFilterTypes<F extends FlowrFilter = FlowrFilter> = FlowrFilterName | FlowrFilterWithArgs<F, FlowrFilterArgs<F>> | RType | VertexType;
/**
* By default, we provide filter for every {@link RType} and {@link VertexType}.
*/
export type FlowrFilterExpression<F extends FlowrFilter = FlowrFilter> = FlowrFilterCombinator | ValidFilterTypes<F>;
interface BooleanBinaryNode<Composite> {
readonly type: 'and' | 'or' | 'xor';
readonly left: Composite;
readonly right: Composite;
}
interface BooleanUnaryNode<Composite> {
readonly type: 'not';
readonly operand: Composite;
}
type LeafRType = {
readonly type: 'r-type';
readonly value: RType;
};
type LeafVertexType = {
readonly type: 'vertex-type';
readonly value: VertexType;
};
type LeafSpecial = {
readonly type: 'special';
readonly value: FlowrFilterName | FlowrFilterWithArgs<FlowrFilter, FlowrFilterArgs<FlowrFilter>>;
};
type Leaf = LeafRType | LeafVertexType | LeafSpecial;
type BooleanNode = BooleanBinaryNode<BooleanNode> | BooleanUnaryNode<BooleanNode> | Leaf;
type BooleanNodeOrCombinator = BooleanNode | FlowrFilterCombinator;
/**
* @see {@link FlowrFilterCombinator.is}
* @see {@link evalFilter}
* @see {@link binaryTreeToString}
*/
export declare class FlowrFilterCombinator {
private tree;
protected constructor(init: BooleanNodeOrCombinator);
static is(value: BooleanNodeOrCombinator | ValidFilterTypes): FlowrFilterCombinator;
and(right: BooleanNodeOrCombinator | ValidFilterTypes): this;
or(right: BooleanNodeOrCombinator | ValidFilterTypes): this;
xor(right: BooleanNodeOrCombinator | ValidFilterTypes): this;
private binaryRight;
not(): this;
private unary;
private unpack;
get(): BooleanNode;
}
/**
* Converts the given binary tree to a string representation.
*/
export declare function binaryTreeToString(tree: BooleanNode): string;
/**
* Checks whether the given value is a binary tree combinator.
* @see {@link FlowrFilterCombinator}
*/
export declare function isBinaryTree(tree: unknown): tree is {
tree: BooleanNode;
};
interface FilterData {
readonly element: FlowrSearchElement<ParentInformation>;
readonly data: {
dataflow: DataflowInformation;
};
}
/**
* Evaluates the given filter expression against the provided data.
*/
export declare function evalFilter<Filter extends FlowrFilter>(filter: FlowrFilterExpression<Filter>, data: FilterData): boolean;
export {};