/**
* @license
* Copyright Google LLC All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
///
import { logging } from '@angular-devkit/core';
import { Observable } from 'rxjs';
import { Url } from 'url';
import { FileEntry, MergeStrategy, Tree } from '../tree/interface';
import { Workflow } from '../workflow/interface';
export interface TaskConfiguration {
name: string;
dependencies?: Array;
options?: T;
}
export interface TaskConfigurationGenerator {
toConfiguration(): TaskConfiguration;
}
export declare type TaskExecutor = (options: T | undefined, context: SchematicContext) => Promise | Observable;
export interface TaskExecutorFactory {
readonly name: string;
create(options?: T): Promise | Observable;
}
export interface TaskId {
readonly id: number;
}
export interface TaskInfo {
readonly id: number;
readonly priority: number;
readonly configuration: TaskConfiguration;
readonly context: SchematicContext;
}
export interface ExecutionOptions {
scope: string;
interactive: boolean;
}
/**
* The description (metadata) of a collection. This type contains every information the engine
* needs to run. The CollectionMetadataT type parameter contains additional metadata that you
* want to store while remaining type-safe.
*/
export declare type CollectionDescription = CollectionMetadataT & {
readonly name: string;
readonly extends?: string[];
};
/**
* The description (metadata) of a schematic. This type contains every information the engine
* needs to run. The SchematicMetadataT and CollectionMetadataT type parameters contain additional
* metadata that you want to store while remaining type-safe.
*/
export declare type SchematicDescription = SchematicMetadataT & {
readonly collection: CollectionDescription;
readonly name: string;
readonly private?: boolean;
readonly hidden?: boolean;
};
/**
* The Host for the Engine. Specifically, the piece of the tooling responsible for resolving
* collections and schematics descriptions. The SchematicMetadataT and CollectionMetadataT type
* parameters contain additional metadata that you want to store while remaining type-safe.
*/
export interface EngineHost {
createCollectionDescription(name: string, requester?: CollectionDescription): CollectionDescription;
listSchematicNames(collection: CollectionDescription, includeHidden?: boolean): string[];
createSchematicDescription(name: string, collection: CollectionDescription): SchematicDescription | null;
getSchematicRuleFactory(schematic: SchematicDescription, collection: CollectionDescription): RuleFactory;
createSourceFromUrl(url: Url, context: TypedSchematicContext): Source | null;
transformOptions(schematic: SchematicDescription, options: OptionT, context?: TypedSchematicContext): Observable;
transformContext(context: TypedSchematicContext): TypedSchematicContext | void;
createTaskExecutor(name: string): Observable;
hasTaskExecutor(name: string): boolean;
readonly defaultMergeStrategy?: MergeStrategy;
}
/**
* The root Engine for creating and running schematics and collections. Everything related to
* a schematic execution starts from this interface.
*
* CollectionMetadataT is, by default, a generic Collection metadata type. This is used throughout
* the engine typings so that you can use a type that's merged into descriptions, while being
* type-safe.
*
* SchematicMetadataT is a type that contains additional typing for the Schematic Description.
*/
export interface Engine {
createCollection(name: string, requester?: Collection): Collection;
createContext(schematic: Schematic, parent?: Partial>, executionOptions?: Partial): TypedSchematicContext;
createSchematic(name: string, collection: Collection): Schematic;
createSourceFromUrl(url: Url, context: TypedSchematicContext): Source;
transformOptions(schematic: Schematic, options: OptionT, context?: TypedSchematicContext): Observable;
executePostTasks(): Observable;
readonly defaultMergeStrategy: MergeStrategy;
readonly workflow: Workflow | null;
}
/**
* A Collection as created by the Engine. This should be used by the tool to create schematics,
* or by rules to create other schematics as well.
*/
export interface Collection {
readonly description: CollectionDescription;
readonly baseDescriptions?: Array>;
createSchematic(name: string, allowPrivate?: boolean): Schematic;
listSchematicNames(includeHidden?: boolean): string[];
}
/**
* A Schematic as created by the Engine. This should be used by the tool to execute the main
* schematics, or by rules to execute other schematics as well.
*/
export interface Schematic {
readonly description: SchematicDescription;
readonly collection: Collection;
call(options: OptionT, host: Observable, parentContext?: Partial>, executionOptions?: Partial): Observable;
}
/**
* A SchematicContext. Contains information necessary for Schematics to execute some rules, for
* example when using another schematics, as we need the engine and collection.
*/
export interface TypedSchematicContext {
readonly debug: boolean;
readonly engine: Engine;
readonly logger: logging.LoggerApi;
readonly schematic: Schematic;
readonly strategy: MergeStrategy;
readonly interactive: boolean;
addTask(task: TaskConfigurationGenerator, dependencies?: Array): TaskId;
}
/**
* This is used by the Schematics implementations in order to avoid needing to have typing from
* the tooling. Schematics are not specific to a tool.
*/
export declare type SchematicContext = TypedSchematicContext<{}, {}>;
/**
* A rule factory, which is normally the way schematics are implemented. Returned by the tooling
* after loading a schematic description.
*/
export declare type RuleFactory = (options: T) => Rule;
/**
* A FileOperator applies changes synchronously to a FileEntry. An async operator returns
* asynchronously. We separate them so that the type system can catch early errors.
*/
export declare type FileOperator = (entry: FileEntry) => FileEntry | null;
export declare type AsyncFileOperator = (tree: FileEntry) => Observable;
/**
* A source is a function that generates a Tree from a specific context. A rule transforms a tree
* into another tree from a specific context. In both cases, an Observable can be returned if
* the source or the rule are asynchronous. Only the last Tree generated in the observable will
* be used though.
*
* We obfuscate the context of Source and Rule because the schematic implementation should not
* know which types is the schematic or collection metadata, as they are both tooling specific.
*/
export declare type Source = (context: SchematicContext) => Tree | Observable;
export declare type Rule = (tree: Tree, context: SchematicContext) => Tree | Observable | Rule | Promise | void;