4

In my Monorepo, there are two types of components that i am using.

  1. Is a standard component for applications, and nx g c foo works fine here.
  2. Is a library component for a library. Here, I exclusively use secondary entry points. So a component always has an index.ts, a public_api.ts, a bar.module.ts and a package.json file.

My question is, how could I extend the standard functionality of the nx g c foo, so that it automatically creates these files?

Harrys Kavan
  • 741
  • 9
  • 28

1 Answers1

3

You probably want to write your own schematics collection.
Please check documentation, some nice articles and sources.
Basically your extending code from new component schematic will look like this:

import { chain, externalSchematic, Rule } from '@angular-devkit/schematics';

export default function(schema: any): Rule {
    // add your custom code here

    return chain([
        externalSchematic('@nrwl/schematics', 'module', {
          ...module options
        }),
        externalSchematic('@nrwl/schematics', 'component', {
          ...component options
        }),

        // and here
    ]);
}

UPD

The same written using nx generators API:

import { wrapAngularDevkitSchematic } from '@nrwl/devkit/ngcli-adapter';
import {
  Tree,
  formatFiles,
  generateFiles,
  joinPathFragments,
  names,
} from '@nrwl/devkit';
// this is your custom generator schema
import { Schema } from './models/schema.model';

export default async function (tree: Tree, schema: Schema) {
  const moduleGenerator = wrapAngularDevkitSchematic(
    '@schematics/angular',
    'module'
  );
  const componentGenerator = wrapAngularDevkitSchematic(
    '@schematics/angular',
    'component'
  );

  // it will create a custom module for you
  await moduleGenerator(tree, {
    name: ...module name,
    project: ...project to add module,
    path: ...path to add module file,
  });

  // it will create a custom component for you
  await componentGenerator(tree, {
    name: ...your name,
    project: ...project to add component,
  });

  // it's a branch where you can add your package.json and index.ts
  // you should create template files for them in ./files folder
  generateFiles(
    tree, // the virtual file system
    joinPathFragments(__dirname, './files'), // path to the file templates
    joinPathFragments('libs/'), // destination path of the files
    {
      ...schema,
      ...names(schema.name),
      tmpl: '',
    } // config object to replace variable in file templates
  );


  return tree;
}

See their tests for more examples.

nickbullock
  • 6,424
  • 9
  • 27
  • Thx for answering. Just to clarify. Your solution would solely work with angular schematics, right? I might misunderstand nx, but I thought that nx would enable someone me to write schematics that can be used anywhere in the project. I'm not sure, but I think this is what @nrwl/nx-plugins is used for. – Harrys Kavan Jun 29 '21 at 21:00
  • 1
    See this link https://nx.dev/latest/angular/generators/using-schematics. No, angular schematics (like nx generators) are just code generation tools so it will work for any js/ts based project. But yes, API for nx plugins is slightly different. Updated the answer – nickbullock Jul 01 '21 at 04:34
  • Thank you very much for the excellent answer. I was able to solve my problem and generally understand the whole topic a lot better. – Harrys Kavan Jul 02 '21 at 18:30
  • Posting a link to a paid article? Is this allowed? – code Dec 16 '21 at 09:19
  • 1
    @code I believe it wasn't under paywall when I posted it. Removed the link. – nickbullock Dec 16 '21 at 13:10