UNPKG

3.99 kBPlain TextView Raw
1/*
2 * Copyright © 2019 Atomist, Inc.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17import { SeedDrivenGeneratorParameters } from "@atomist/automation-client";
18import {
19 CachingProjectLoader,
20 chainTransforms,
21 CommandListenerInvocation,
22 computeStartingPoint,
23 GeneratorRegistration,
24 ParametersObject,
25 projectLoaderRepoLoader,
26 SoftwareDeliveryMachine,
27 toMachineOptions,
28} from "@atomist/sdm";
29import * as _ from "lodash";
30import { toArray } from "../../util/misc/array";
31import { UniversalTransform } from "./generatorSupport";
32
33/**
34 * Wrap provided generator to execute additional transformsAndParameters
35 */
36export function universalGenerator<P extends SeedDrivenGeneratorParameters = any>(
37 sdm: SoftwareDeliveryMachine,
38 generator: GeneratorRegistration<any>,
39 transforms: Array<UniversalTransform<any>>): GeneratorRegistration<P> {
40 return {
41 ...generator,
42 startingPoint: async pi => {
43 const repoLoader = (p: SeedDrivenGeneratorParameters) =>
44 projectLoaderRepoLoader(
45 sdm.configuration.sdm.projectLoader || new CachingProjectLoader(),
46 p.target.credentials,
47 true);
48
49 const project = await computeStartingPoint(
50 pi.parameters as any,
51 pi.context,
52 repoLoader(pi.parameters as any),
53 { ...generator as any, redirecter: () => undefined },
54 generator.startingPoint,
55 generator,
56 toMachineOptions(sdm));
57
58 const transformsToApply = [];
59 for (const transform of transforms) {
60 if (!!transform.test) {
61 if (await transform.test(project)) {
62 transformsToApply.push(transform);
63 }
64 } else {
65 transformsToApply.push(transform);
66 }
67 }
68
69 await enhanceWithSpecificParameters(transformsToApply, pi as any);
70
71 // Safe the transformsAndParameters to invoke on the invocation to re-use later
72 (pi as any).parameters.__transforms = transformsToApply;
73 return project;
74 },
75 transform: async (p, pi) => {
76 const universalTransforms = (pi.parameters as any).__transforms as Array<UniversalTransform<any>>;
77 const computedTransforms = _.flatten(universalTransforms.map(t => toArray(t.transforms)));
78
79 // tslint:disable-next-line:deprecation
80 const trans = chainTransforms(...toArray(generator.transform || []), ...computedTransforms);
81 return trans(p, pi, pi.parameters);
82 },
83 };
84}
85
86/**
87 * Enrich parameters with the extras if needed
88 */
89async function enhanceWithSpecificParameters<P>(universalTransforms: Array<UniversalTransform<any>>,
90 ctx: CommandListenerInvocation<any>): Promise<void> {
91
92 const unsatisfiedParameters: ParametersObject<any> = {};
93 for (const universalTransform of universalTransforms) {
94 _.forEach(universalTransform.parameters, (v, k) => {
95 if (ctx.parameters[k] === undefined) {
96 unsatisfiedParameters[k] = v;
97 }
98 });
99 }
100
101 const newParams: any = await ctx.promptFor<P>(unsatisfiedParameters);
102
103 for (const name of Object.getOwnPropertyNames(newParams)) {
104 ctx.parameters[name] = newParams[name];
105 }
106}