Skip to content

Commit

Permalink
feat(core): schematic for adding npm package #5
Browse files Browse the repository at this point in the history
#6 still needs to be implemented. The base sync schematic has been added, but is not implemented.
  • Loading branch information
AgentEnder committed Apr 29, 2021
1 parent dea86e3 commit b97c097
Show file tree
Hide file tree
Showing 16 changed files with 312 additions and 3 deletions.
10 changes: 10 additions & 0 deletions packages/core/generators.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,16 @@
"description": "init generator",
"alias": ["ng-add"],
"hidden": true
},
"sync": {
"factory": "./src/generators/sync/generator",
"schema": "./src/generators/sync/schema.json",
"description": "sync generator"
},
"nuget-reference": {
"factory": "./src/generators/nuget-reference/generator",
"schema": "./src/generators/nuget-reference/schema.json",
"description": "nuget-reference generator"
}
}
}
22 changes: 22 additions & 0 deletions packages/core/src/generators/nuget-reference/generator.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { createTreeWithEmptyWorkspace } from '@nrwl/devkit/testing';
import { Tree, readProjectConfiguration } from '@nrwl/devkit';

import generator from './generator';
import { NugetReferenceGeneratorSchema } from './schema';

describe('nuget-reference generator', () => {
let appTree: Tree;
const options: NugetReferenceGeneratorSchema = {
packageName: 'test',
project: 'test',
};

beforeEach(() => {
appTree = createTreeWithEmptyWorkspace();
});

it('should run successfully', async () => {
// await generator(appTree, options);
expect(true).toBeTruthy();
});
});
34 changes: 34 additions & 0 deletions packages/core/src/generators/nuget-reference/generator.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { readProjectConfiguration, Tree } from '@nrwl/devkit';

import {
dotnetAddPackageFlags,
DotNetClient,
dotnetFactory,
} from '@nx-dotnet/dotnet';
import { getProjectFileForNxProject } from '@nx-dotnet/utils';

import { NugetReferenceGeneratorSchema } from './schema';

export default async function (
host: Tree,
options: NugetReferenceGeneratorSchema,
dotnetClient = new DotNetClient(dotnetFactory())
) {
const project = readProjectConfiguration(host, options.project);
const projectFilePath = await getProjectFileForNxProject(project);

dotnetClient.addPackageReference(
projectFilePath,
options.packageName,
Object.keys(options)
.filter((x) => x !== 'packageName' && x !== 'project')
.map((x) => ({
flag: x as dotnetAddPackageFlags,
value: options[x as keyof NugetReferenceGeneratorSchema],
}))
);

return {
success: true,
};
}
10 changes: 10 additions & 0 deletions packages/core/src/generators/nuget-reference/schema.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
export interface NugetReferenceGeneratorSchema {
project: string;
packageName: string;
version?: string;
framework?: string;
packageDirectory?: string;
prerelease?: boolean;
source?: string;
noRestore?: boolean;
}
55 changes: 55 additions & 0 deletions packages/core/src/generators/nuget-reference/schema.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
{
"$schema": "http://json-schema.org/schema",
"cli": "nx",
"id": "NugetReference",
"title": "",
"type": "object",
"properties": {
"project": {
"type": "string",
"description": "",
"$default": {
"$source": "argv",
"index": 0
},
"x-prompt": "What project should the package be added to?"
},
"packageName": {
"type": "string",
"description": "Which package should be added?",
"$default": {
"$source": "argv",
"index": 1
}
},
"version": {
"type": "string",
"description": "A directory where the project is placed",
"$default": {
"$source": "argv",
"index": 2
}
},
"framework": {
"type": "string",
"description": "Adds a package reference only when targeting a specific framework."
},
"packageDirectory": {
"type": "string",
"description": "The directory where to restore the packages. The default package restore location is %userprofile%\\.nuget\\packages on Windows and ~/.nuget/packages on macOS and Linux. For more information, see [Managing the global packages, cache, and temp folders in NuGet](https://docs.microsoft.com/en-us/nuget/consume-packages/managing-the-global-packages-and-cache-folders)."
},
"prerelease": {
"type": "boolean",
"description": "Allows prerelease packages to be installed. Available since .NET Core 5 SDK"
},
"source": {
"type": "string",
"description": "The URI of the NuGet package source to use during the restore operation."
},
"noRestore": {
"type": "boolean",
"description": "Adds a package reference without performing a restore preview and compatibility check."
}
},
"required": ["packageName", "project"]
}
4 changes: 1 addition & 3 deletions packages/core/src/generators/project-reference/generator.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { formatFiles, readProjectConfiguration, Tree } from '@nrwl/devkit';
import { readProjectConfiguration, Tree } from '@nrwl/devkit';

import { DotNetClient, dotnetFactory } from '@nx-dotnet/dotnet';
import { getProjectFileForNxProject } from '@nx-dotnet/utils';
Expand All @@ -24,6 +24,4 @@ export default async function (
}

client.addProjectReference(hostProjectFile, sourceProjectFile);

await formatFiles(host);
}
19 changes: 19 additions & 0 deletions packages/core/src/generators/sync/generator.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import { createTreeWithEmptyWorkspace } from '@nrwl/devkit/testing';
import { Tree, readProjectConfiguration } from '@nrwl/devkit';

import generator from './generator';
import { SyncGeneratorSchema } from './schema';

describe('sync generator', () => {
let appTree: Tree;
const options: SyncGeneratorSchema = { name: 'test' };

beforeEach(() => {
appTree = createTreeWithEmptyWorkspace();
});

it('should run successfully', async () => {
// await generator(appTree, options);
expect(true).toBeTruthy();
});
});
73 changes: 73 additions & 0 deletions packages/core/src/generators/sync/generator.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import {
addProjectConfiguration,
formatFiles,
generateFiles,
getWorkspaceLayout,
names,
offsetFromRoot,
Tree,
} from '@nrwl/devkit';
import * as path from 'path';
import { SyncGeneratorSchema } from './schema';

interface NormalizedSchema extends SyncGeneratorSchema {
projectName: string;
projectRoot: string;
projectDirectory: string;
parsedTags: string[];
}

function normalizeOptions(
host: Tree,
options: SyncGeneratorSchema
): NormalizedSchema {
const name = names(options.name).fileName;
const projectDirectory = options.directory
? `${names(options.directory).fileName}/${name}`
: name;
const projectName = projectDirectory.replace(new RegExp('/', 'g'), '-');
const projectRoot = `${getWorkspaceLayout(host).libsDir}/${projectDirectory}`;
const parsedTags = options.tags
? options.tags.split(',').map((s) => s.trim())
: [];

return {
...options,
projectName,
projectRoot,
projectDirectory,
parsedTags,
};
}

function addFiles(host: Tree, options: NormalizedSchema) {
const templateOptions = {
...options,
...names(options.name),
offsetFromRoot: offsetFromRoot(options.projectRoot),
template: '',
};
generateFiles(
host,
path.join(__dirname, 'files'),
options.projectRoot,
templateOptions
);
}

export default async function (host: Tree, options: SyncGeneratorSchema) {
const normalizedOptions = normalizeOptions(host, options);
addProjectConfiguration(host, normalizedOptions.projectName, {
root: normalizedOptions.projectRoot,
projectType: 'library',
sourceRoot: `${normalizedOptions.projectRoot}/src`,
targets: {
build: {
executor: '@nx-dotnet/core:build',
},
},
tags: normalizedOptions.parsedTags,
});
addFiles(host, normalizedOptions);
await formatFiles(host);
}
5 changes: 5 additions & 0 deletions packages/core/src/generators/sync/schema.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export interface SyncGeneratorSchema {
name: string;
tags?: string;
directory?: string;
}
29 changes: 29 additions & 0 deletions packages/core/src/generators/sync/schema.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
{
"$schema": "http://json-schema.org/schema",
"cli": "nx",
"id": "Sync",
"title": "",
"type": "object",
"properties": {
"name": {
"type": "string",
"description": "",
"$default": {
"$source": "argv",
"index": 0
},
"x-prompt": "What name would you like to use?"
},
"tags": {
"type": "string",
"description": "Add tags to the project (used for linting)",
"alias": "t"
},
"directory": {
"type": "string",
"description": "A directory where the project is placed",
"alias": "d"
}
},
"required": ["name"]
}
21 changes: 21 additions & 0 deletions packages/dotnet/src/lib/core/dotnet.client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,9 @@ import {
} from '@nx-dotnet/utils';

import {
addPackageKeyMap,
buildKeyMap,
dotnetAddPackageOptions,
dotnetBuildOptions,
dotnetNewOptions,
dotnetRunOptions,
Expand Down Expand Up @@ -61,6 +63,25 @@ export class DotNetClient {
return this.logAndExecute(cmd);
}

addPackageReference(
project: string,
pkg: string,
parameters?: dotnetAddPackageOptions
): Buffer {
let cmd = `${this.cliCommand.command} add ${project} package ${pkg}`;
if (parameters) {
parameters = swapArrayFieldValueUsingMap(
parameters,
'flag',
addPackageKeyMap
);
const paramString = parameters ? getParameterString(parameters) : '';
cmd = `${cmd} ${paramString}`;
}
console.log(`Executing Command: ${cmd}`);
return this.logAndExecute(cmd);
}

addProjectReference(hostCsProj: string, targetCsProj: string): Buffer {
return this.logAndExecute(
`${this.cliCommand.command} add ${hostCsProj} reference ${targetCsProj}`
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
export type dotnetAddPackageFlags =
| 'version'
| 'framework'
| 'packageDirectory'
| 'prerelease'
| 'noRestore'
| 'source';

export const addPackageKeyMap: Partial<
{ [key in dotnetAddPackageFlags]: string }
> = {
packageDirectory: 'package-directory',
noRestore: 'no-restore',
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { dotnetAddPackageFlags } from './dotnet-add-package-flags';

export type dotnetAddPackageOptions = {
flag: dotnetAddPackageFlags;
value?: string | boolean;
}[];
2 changes: 2 additions & 0 deletions packages/dotnet/src/lib/models/dotnet-add-package/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export * from './dotnet-add-package-flags';
export * from './dotnet-add-package-options';
1 change: 1 addition & 0 deletions packages/dotnet/src/lib/models/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,4 @@ export * from './dotnet-new';
export * from './dotnet-build';
export * from './dotnet-run';
export * from './dotnet-test';
export * from './dotnet-add-package';
10 changes: 10 additions & 0 deletions tools/scripts/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
{
"extends": "../../tsconfig.base.json",
"compilerOptions": {
"module": "commonjs",
"declaration": true,
"types": ["node"]
},
"exclude": ["**/*.spec.ts"],
"include": ["**/*.ts"]
}

0 comments on commit b97c097

Please sign in to comment.