revy
revy

Reputation: 4707

Generate import statement programmatically using typescript compiler API

I would like to generate the following import statement:

import { Something } from 'a-module';

To do so I am using typescript compiler API:

import * as ts from 'typescript';

const sourceFile = ts.createSourceFile(
    `source.ts`,
    ``,
    ts.ScriptTarget.Latest,
    false,
    ts.ScriptKind.TS
);

const printer = ts.createPrinter({ newLine: ts.NewLineKind.LineFeed });

const importNode = ts.createImportDeclaration(
    /* decorators */ undefined,
    /* modifiers */ undefined,
    ts.createImportClause(
        ts.createIdentifier('Something'),
        /* namedBindings */ undefined
    ),
    ts.createLiteral('a-module')
);

const result = printer.printNode(ts.EmitHint.Unspecified, importNode, sourceFile);

console.log(result);
// prints --> import Something from "a-module";

How can I add the curly braces syntax to the import statement? Could be something related to namedBindings parameter in createImportClause but I'm not sure how to use it.

Upvotes: 4

Views: 1509

Answers (2)

low_ghost
low_ghost

Reputation: 590

slightly updated version of @revy's answer in case anyone finds this

const { factory } = ts; // or context
const importNode = factory.createImportDeclaration(
    /* modifiers */ undefined,
    factory.createImportClause(
        /* isTypeOnly */ false,
        /* name (default import) */ undefined,
        factory.createNamedImports([
            /* isTypeOnly */ false,
            /* propertyName, inclusion would lead to 'Something as ' */ undefined,
            factory.createImportSpecifier(undefined, ts.createIdentifier('Something')),
        ])
    ),
    factory.createLiteral('a-module')
);

results in

import { Something } from "a-module";

and note that to get a file path import, you'll want createStringLiteral e.g.

factory.createStringLiteral('some/file/path')

becomes

import { Something } from "some/file/path";

Upvotes: 0

revy
revy

Reputation: 4707

Ok found it (as I guessed one must use namedBindings):

// [...]

const importNode = ts.createImportDeclaration(
    /* decorators */ undefined,
    /* modifiers */ undefined,
    ts.createImportClause(
        undefined,
        ts.createNamedImports(
            [
                ts.createImportSpecifier(undefined, ts.createIdentifier('Something')),
            ]
        )
    ),
    ts.createLiteral('a-module')
);

// [...]

Upvotes: 2

Related Questions