Socket
Socket
Sign inDemoInstall

@polymer/gen-typescript-declarations

Package Overview
Dependencies
127
Maintainers
8
Versions
25
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

Comparing version 1.4.0 to 1.5.0

lib/verify.d.ts

24

CHANGELOG.md

@@ -8,3 +8,27 @@ # Changelog

<!-- ## [Unreleased] -->
<!-- Add new, unreleased changes here. -->
## [1.5.0] - 2018-08-15
* Legacy Polymer function components will no longer have a `_template`
property.
* Functions defined within exported Polymer function calls or exported objects
are no longer themselves emitted as top-level functions.
* `FooBehaviorImpl` style behavior objects (that have been merged into a main
`FooBehavior` array) will no longer have a broken `import` or `export`
statements emitted for them.
* Update the URL for this repo put in generated file headers, since it has moved
into the Polymer tools monorepo.
* Added `--verify` command-line flag which will run the generated typings
through the TypeScript compiler (3.0) and fail with the log if it fails.
* The `--deleteExisting` flag will no longer delete `.d.ts` files that are
referenced as keys in the `autoImport` config option.
* Do not `import` or `export` features with `private` visibility.
* Display warnings generated during the analysis phase.
* `autoImport` now supports bare-module specifiers. Local files must now
begin with `.`.
* `excludeIdentifiers` option now applies to properties and methods.
* The pattern `import * as foo from 'foo'; export {foo as bar};` is now
supported.
* Exit with a non-zero code when an analysis error is encountered.
## [1.4.0] - 2018-07-25

@@ -11,0 +35,0 @@ - Support for ES module imports and exports.

50

lib/cli.js

@@ -25,2 +25,3 @@ "use strict";

const gen_ts_1 = require("./gen-ts");
const verify_1 = require("./verify");
const commandLineArgs = require("command-line-args");

@@ -60,4 +61,11 @@ const commandLineUsage = require("command-line-usage");

'writing new typings, excluding node_modules/, bower_components/, ' +
'or any file added using the <addReferences> config option.',
'or any file added using the <addReferences> or <autoImport> config ' +
'options.',
},
{
name: 'verify',
type: Boolean,
description: 'Compile the generated types with TypeScript 3.0 and fail ' +
'if they are invalid.',
},
];

@@ -71,3 +79,4 @@ function run(argv) {

header: `gen-typescript-declarations`,
content: 'https://github.com/Polymer/gen-typescript-declarations',
content: 'https://github.com/Polymer/tools/tree/master/packages/' +
'gen-typescript-declarations',
},

@@ -88,2 +97,3 @@ {

}
const outDir = path.resolve(args.outDir);
if (!args.config) {

@@ -103,3 +113,3 @@ const p = path.join(args.root, 'gen-tsd.json');

let dtsFiles = glob.sync('**/*.d.ts', {
cwd: args.outDir,
cwd: outDir,
absolute: true,

@@ -112,18 +122,34 @@ nodir: true,

});
// If the addReferences option is being used, it's probably to add some
// manually written typings. Since manually written typing files won't get
// re-generated, we shouldn't delete them.
// If the addReferences or autoImport options are used, it's probably to add
// some manually written typings. Since manually written typing files won't
// get re-generated, we shouldn't delete them.
const dontDelete = new Set();
for (const refs of Object.values(config.addReferences || {})) {
for (const ref of refs) {
dontDelete.add(path.resolve(args.root, ref));
for (const dtsFilePaths of Object.values(config.addReferences || {})) {
for (const dtsFilePath of dtsFilePaths) {
dontDelete.add(path.resolve(args.root, dtsFilePath));
}
}
for (const localModuleSpecifier of Object.keys(config.autoImport || {})) {
const dtsFilePath = localModuleSpecifier.replace(/\.js$/, '') + '.d.ts';
dontDelete.add(path.resolve(args.root, dtsFilePath));
}
dtsFiles = dtsFiles.filter((filepath) => !dontDelete.has(filepath));
console.log(`Deleting ${dtsFiles.length} existing d.ts files from ` +
`${path.resolve(args.outDir)}`);
console.log(`Deleting ${dtsFiles.length} existing d.ts files from ${outDir}`);
yield Promise.all(dtsFiles.map((filepath) => fsExtra.remove(filepath)));
}
console.log('Writing type declarations to', path.resolve(args.outDir));
console.log(`Writing type declarations to ${outDir}`);
yield writeFileMap(args.outDir, fileMap);
if (args.verify) {
console.log('Verifying type declarations');
const declarationFiles = [...fileMap.keys()].map((filePath) => path.join(outDir, filePath));
const result = verify_1.verifyTypings(declarationFiles);
if (result.success === true) {
console.log('Compilation successful');
}
else {
console.log('Compilation failed');
console.log(result.errorLog);
process.exit(1);
}
}
});

@@ -130,0 +156,0 @@ }

@@ -115,3 +115,3 @@ "use strict";

const tsDocs = [];
const warningPrinter = new analyzer.WarningPrinter(process.stderr, { maxCodeLines: 1 });
const warnings = [...analysis.getWarnings()];
for (const [declarationsFilename, analyzerDocs] of declarationDocs) {

@@ -131,3 +131,3 @@ const tsDoc = new ts.Document({

generator.handleDocument();
yield warningPrinter.printWarnings(generator.warnings);
warnings.push(...generator.warnings);
}

@@ -158,2 +158,12 @@ for (const ref of tsDoc.referencePaths) {

}
const filteredWarnings = warnings.filter((warning) => {
const sourcePath = analyzerUrlToRelativePath(warning.sourceRange.file, rootDir);
return sourcePath !== undefined &&
!excludeFiles.some((pattern) => pattern.match(sourcePath));
});
const warningPrinter = new analyzer.WarningPrinter(process.stderr, { maxCodeLines: 1 });
yield warningPrinter.printWarnings(filteredWarnings);
if (filteredWarnings.some((warning) => warning.severity === analyzer.Severity.ERROR)) {
throw new Error('Encountered error generating types.');
}
return tsDocs;

@@ -169,23 +179,27 @@ });

for (const node of tsDoc.traverse()) {
if (node.kind !== 'name') {
continue;
if (node.kind === 'name') {
let importSpecifier = autoImport.get(node.name);
if (importSpecifier === undefined) {
continue;
}
if (alreadyImported.has(node.name)) {
continue;
}
if (importSpecifier.startsWith('.')) {
if (makeDeclarationsFilename(importSpecifier) === tsDoc.path) {
// Don't import from yourself.
continue;
}
importSpecifier =
path.relative(path.dirname(tsDoc.path), importSpecifier);
if (!importSpecifier.startsWith('.')) {
importSpecifier = './' + importSpecifier;
}
}
tsDoc.members.push(new ts.Import({
identifiers: [{ identifier: node.name }],
fromModuleSpecifier: importSpecifier,
}));
alreadyImported.add(node.name);
}
const importPath = autoImport.get(node.name);
if (importPath === undefined) {
continue;
}
if (alreadyImported.has(node.name)) {
continue;
}
if (makeDeclarationsFilename(importPath) === tsDoc.path) {
// Don't import from yourself.
continue;
}
const fileRelative = path.relative(path.dirname(tsDoc.path), importPath);
const fromModuleSpecifier = fileRelative.startsWith('.') ? fileRelative : './' + fileRelative;
tsDoc.members.push(new ts.Import({
identifiers: [{ identifier: node.name }],
fromModuleSpecifier,
}));
alreadyImported.add(node.name);
}

@@ -236,3 +250,3 @@ }

This file was automatically generated by
https://github.com/Polymer/gen-typescript-declarations
https://github.com/Polymer/tools/tree/master/packages/gen-typescript-declarations

@@ -248,4 +262,9 @@ To modify these typings, edit the source file(s):

this.rootDir = rootDir;
this.excludeIdentifiers = excludeIdentifiers;
this.warnings = [];
/**
* Identifiers in this set will always be considered resolvable, e.g.
* for when determining what identifiers should be exported.
*/
this.forceResolvable = new Set();
this.excludeIdentifiers = new Set(excludeIdentifiers);
}

@@ -268,6 +287,6 @@ warn(feature, message) {

for (const feature of this.analyzerDoc.getFeatures()) {
if (this.excludeIdentifiers.some((id) => feature.identifiers.has(id))) {
if ([...feature.identifiers].some((id) => this.excludeIdentifiers.has(id))) {
continue;
}
if (feature.privacy === 'private') {
if (isPrivate(feature)) {
continue;

@@ -306,6 +325,6 @@ }

else if (feature.kinds.has('js-import')) {
this.handleJsImport(feature, this.analyzerDoc);
this.handleJsImport(feature);
}
else if (feature.kinds.has('export')) {
this.handleJsExport(feature, this.analyzerDoc);
this.handleJsExport(feature);
}

@@ -590,3 +609,4 @@ }

for (const property of analyzerProperties) {
if (property.inheritedFrom || property.privacy === 'private') {
if (property.inheritedFrom || property.privacy === 'private' ||
this.excludeIdentifiers.has(property.name)) {
continue;

@@ -613,3 +633,4 @@ }

for (const method of analyzerMethods) {
if (method.inheritedFrom || method.privacy === 'private') {
if (method.inheritedFrom || method.privacy === 'private' ||
this.excludeIdentifiers.has(method.name)) {
continue;

@@ -692,5 +713,4 @@ }

*/
handleJsImport(feature, doc) {
handleJsImport(feature) {
const node = feature.astNode.node;
const isResolvable = (identifier) => es_modules_1.resolveImportExportFeature(feature, identifier, doc) !== undefined;
if (babel.isImportDeclaration(node)) {

@@ -701,3 +721,3 @@ const identifiers = [];

// E.g. import {Foo, Bar as Baz} from './foo.js'
if (isResolvable(specifier.imported.name)) {
if (this.isResolvable(specifier.imported.name, feature)) {
identifiers.push({

@@ -711,3 +731,3 @@ identifier: specifier.imported.name,

// E.g. import foo from './foo.js'
if (isResolvable('default')) {
if (this.isResolvable('default', feature)) {
identifiers.push({

@@ -725,2 +745,3 @@ identifier: 'default',

});
this.forceResolvable.add(specifier.local.name);
}

@@ -746,5 +767,4 @@ }

*/
handleJsExport(feature, doc) {
handleJsExport(feature) {
const node = feature.astNode.node;
const isResolvable = (identifier) => es_modules_1.resolveImportExportFeature(feature, identifier, doc) !== undefined;
if (babel.isExportAllDeclaration(node)) {

@@ -762,3 +782,3 @@ // E.g. export * from './foo.js'

for (const identifier of feature.identifiers) {
if (isResolvable(identifier)) {
if (this.isResolvable(identifier, feature)) {
identifiers.push({ identifier });

@@ -771,3 +791,4 @@ }

for (const specifier of node.specifiers) {
if (isResolvable(specifier.exported.name)) {
if (this.isResolvable(specifier.exported.name, feature) ||
this.isResolvable(specifier.local.name, feature)) {
identifiers.push({

@@ -792,2 +813,14 @@ identifier: specifier.local.name,

/**
* True if the given identifier can be resolved to a feature that will be
* exported as a TypeScript type.
*/
isResolvable(identifier, fromFeature) {
if (this.forceResolvable.has(identifier)) {
return true;
}
const resolved = es_modules_1.resolveImportExportFeature(fromFeature, identifier, this.analyzerDoc);
return resolved !== undefined && resolved.feature !== undefined &&
!isPrivate(resolved.feature) && !isBehaviorImpl(resolved);
}
/**
* Add an HTML import to a TypeScript declarations file. For a given HTML

@@ -892,2 +925,30 @@ * import, we assume there is a corresponding declarations file that was

/**
* Return whether a reference looks like it is a FooBehaviorImpl style behavior
* object, which we want to ignore.
*
* Polymer behavior libraries are often written like:
*
* /** @polymerBehavior FooBehavior *\/
* export const FooBehaviorImpl = {};
*
* /** @polymerBehavior *\/
* export const FooBehavior = [FooBehaviorImpl, OtherBehavior];
*
* In this case, Analyzer merges FooBehaviorImpl into FooBehavior and does not
* emit a behavior feature for FooBehaviorImpl. However, there is still an
* export feature for FooBehaviorImpl, so we exclude it here.
*/
function isBehaviorImpl(reference) {
return reference.feature !== undefined &&
reference.feature.kinds.has('behavior') &&
reference.feature.name !==
reference.identifier;
}
/**
* Return whether the given Analyzer feature has "private" visibility.
*/
function isPrivate(feature) {
return feature.privacy === 'private';
}
/**
* Convert kebab-case to CamelCase.

@@ -894,0 +955,0 @@ */

{
"name": "@polymer/gen-typescript-declarations",
"version": "1.4.0",
"version": "1.5.0",
"description": "Generate TypeScript type declarations for Polymer components.",

@@ -36,2 +36,3 @@ "homepage": "https://github.com/Polymer/tools/tree/master/packages/gen-typescript-declarations",

"polymer-analyzer": "^3.0.2",
"typescript": "^3.0.1",
"vscode-uri": "^1.0.3"

@@ -41,3 +42,2 @@ },

"bower": "^1.8.2",
"clang-format": "^1.1.0",
"rimraf": "^2.6.2",

@@ -49,3 +49,3 @@ "source-map-support": "^0.5.0",

"clean": "rimraf lib",
"format": "find src -name '*.ts' -not -path 'src/test/fixtures/*' -not -path 'src/test/goldens/*' | xargs clang-format --style=file -i",
"format": "find src -name \"*.ts\" -not -path \"src/test/fixtures/*\" -not -path \"src/test/goldens/*\" | xargs clang-format --style=file -i",
"lint": "tslint --project . --format stylish",

@@ -52,0 +52,0 @@ "build": "npm run clean && tsc",

@@ -10,6 +10,20 @@ # gen-typescript-declarations

### Polymer
### Polymer 3
To use the typings, install Polymer normally from Bower (versions 2.4 and
above), and add a [triple-slash
Typings for Polymer 3 are included starting from version 3.0.5. To use them,
install `@polymer/polymer` from npm, and use standard ES module import
specifiers:
```ts
import {PolymerElement} from '@polymer/polymer';
class MyElement extends PolymerElement {
...
}
```
### Polymer 2
Typings for Polymer 2 are included starting from version 2.4.0. To use them,
install Polymer from Bower and add a [triple-slash
directive](https://www.typescriptlang.org/docs/handbook/triple-slash-directives.html)

@@ -28,3 +42,4 @@ anywhere in your TypeScript project for the typings you require. Each HTML

Alternatively, you can add the dependency to `tsconfig.json` in the root of your project:
Alternatively, you can add the dependency to `tsconfig.json` in the root of your
project:

@@ -41,5 +56,2 @@ ```javascript

Typings for Polymer 3 are planned but not yet available (see
[#18](https://github.com/Polymer/gen-typescript-declarations/issues/18)).
You may also be interested in the [Polymer

@@ -50,4 +62,5 @@ decorators](https://github.com/Polymer/polymer-decorators).

You can run this package from the command line with `gen-tsd`, or as a library
with the `generateDeclarations` function.
You can run this package from the command line with
`gen-typescript-declarations`, or as a library with the `generateDeclarations`
function.

@@ -61,3 +74,3 @@ It is recommended to integrate typings generation as part of your build/release

Add a `gen-tsd` script to your `package.json`:
Add a `generate-typings` script to your `package.json`:

@@ -68,3 +81,3 @@ ```js

"scripts": {
"gen-tsd": "gen-tsd"
"generate-typings": "gen-typescript-declarations"
}

@@ -74,13 +87,17 @@ }

If you're using Bower, ensure you run `npm run gen-tsd` to generate the latest
typings and commit them to your repository before tagging each release.
If you're using NPM, you can add this script to the NPM `prepack` script to
generate and include typings in your NPM package every time you publish. Most
users will want to configure their `.gitignore` so that the generated typings
are not committed to their Git repository. In this case, take care to configure
your `.npmignore` and/or `package.json` to ensure that they are included when
you publish to NPM (run `npm pack` to check before publishing).
If you're using NPM, you can instead add this script to the NPM `prepack`
script to generate and include typings in your NPM package every time you
publish.
If you are still using Bower, ensure you run `npm run generate-typings` to
generate the latest typings and commit them to your repository before tagging
each release.
## Config options
By default the `gen-tsd` command will read a file called `gen-tsd.json` in
your root directory. It has the following options:
By default the `gen-typescript-declarations` command will read a file called
`gen-tsd.json` in your root directory. It has the following options:

@@ -114,2 +131,10 @@ * **`excludeFiles`**`: string[]`

* **`autoImport`**`: {[modulePath: string]: string[]}`
A map from an ES module path (relative to the analysis root directory) to
an array of identifiers exported by that module. If any of those
identifiers are encountered in a generated typings file, an import for that
identifier from the specified module will be inserted into the typings
file.
## Using as a module

@@ -116,0 +141,0 @@

@@ -17,2 +17,3 @@ /**

import {Config, generateDeclarations} from './gen-ts';
import {verifyTypings} from './verify';

@@ -55,4 +56,11 @@ import commandLineArgs = require('command-line-args');

'writing new typings, excluding node_modules/, bower_components/, ' +
'or any file added using the <addReferences> config option.',
'or any file added using the <addReferences> or <autoImport> config ' +
'options.',
},
{
name: 'verify',
type: Boolean,
description: 'Compile the generated types with TypeScript 3.0 and fail ' +
'if they are invalid.',
},
];

@@ -67,2 +75,3 @@

deleteExisting?: boolean;
verify?: boolean;
}

@@ -77,3 +86,4 @@

header: `gen-typescript-declarations`,
content: 'https://github.com/Polymer/gen-typescript-declarations',
content: 'https://github.com/Polymer/tools/tree/master/packages/' +
'gen-typescript-declarations',
},

@@ -96,2 +106,3 @@ {

}
const outDir = path.resolve(args.outDir);

@@ -114,3 +125,3 @@ if (!args.config) {

let dtsFiles = glob.sync('**/*.d.ts', {
cwd: args.outDir,
cwd: outDir,
absolute: true,

@@ -124,21 +135,38 @@ nodir: true,

// If the addReferences option is being used, it's probably to add some
// manually written typings. Since manually written typing files won't get
// re-generated, we shouldn't delete them.
// If the addReferences or autoImport options are used, it's probably to add
// some manually written typings. Since manually written typing files won't
// get re-generated, we shouldn't delete them.
const dontDelete = new Set<string>();
for (const refs of Object.values(config.addReferences || {})) {
for (const ref of refs) {
dontDelete.add(path.resolve(args.root, ref));
for (const dtsFilePaths of Object.values(config.addReferences || {})) {
for (const dtsFilePath of dtsFilePaths) {
dontDelete.add(path.resolve(args.root, dtsFilePath));
}
}
for (const localModuleSpecifier of Object.keys(config.autoImport || {})) {
const dtsFilePath = localModuleSpecifier.replace(/\.js$/, '') + '.d.ts';
dontDelete.add(path.resolve(args.root, dtsFilePath));
}
dtsFiles = dtsFiles.filter((filepath) => !dontDelete.has(filepath));
console.log(
`Deleting ${dtsFiles.length} existing d.ts files from ` +
`${path.resolve(args.outDir)}`);
`Deleting ${dtsFiles.length} existing d.ts files from ${outDir}`);
await Promise.all(dtsFiles.map((filepath) => fsExtra.remove(filepath)));
}
console.log('Writing type declarations to', path.resolve(args.outDir));
console.log(`Writing type declarations to ${outDir}`);
await writeFileMap(args.outDir, fileMap);
if (args.verify) {
console.log('Verifying type declarations');
const declarationFiles =
[...fileMap.keys()].map((filePath) => path.join(outDir, filePath));
const result = verifyTypings(declarationFiles);
if (result.success === true) {
console.log('Compilation successful');
} else {
console.log('Compilation failed');
console.log(result.errorLog);
process.exit(1);
}
}
}

@@ -145,0 +173,0 @@

@@ -172,5 +172,3 @@ /**

const tsDocs = [];
const warningPrinter =
new analyzer.WarningPrinter(process.stderr, {maxCodeLines: 1});
const warnings = [...analysis.getWarnings()];
for (const [declarationsFilename, analyzerDocs] of declarationDocs) {

@@ -197,3 +195,3 @@ const tsDoc = new ts.Document({

generator.handleDocument();
await warningPrinter.printWarnings(generator.warnings);
warnings.push(...generator.warnings);
}

@@ -225,2 +223,17 @@

}
const filteredWarnings = warnings.filter((warning) => {
const sourcePath =
analyzerUrlToRelativePath(warning.sourceRange.file, rootDir);
return sourcePath !== undefined &&
!excludeFiles.some((pattern) => pattern.match(sourcePath));
});
const warningPrinter =
new analyzer.WarningPrinter(process.stderr, {maxCodeLines: 1});
await warningPrinter.printWarnings(filteredWarnings);
if (filteredWarnings.some(
(warning) => warning.severity === analyzer.Severity.ERROR)) {
throw new Error('Encountered error generating types.');
}
return tsDocs;

@@ -237,24 +250,27 @@ }

for (const node of tsDoc.traverse()) {
if (node.kind !== 'name') {
continue;
if (node.kind === 'name') {
let importSpecifier = autoImport.get(node.name);
if (importSpecifier === undefined) {
continue;
}
if (alreadyImported.has(node.name)) {
continue;
}
if (importSpecifier.startsWith('.')) {
if (makeDeclarationsFilename(importSpecifier) === tsDoc.path) {
// Don't import from yourself.
continue;
}
importSpecifier =
path.relative(path.dirname(tsDoc.path), importSpecifier);
if (!importSpecifier.startsWith('.')) {
importSpecifier = './' + importSpecifier;
}
}
tsDoc.members.push(new ts.Import({
identifiers: [{identifier: node.name}],
fromModuleSpecifier: importSpecifier,
}));
alreadyImported.add(node.name);
}
const importPath = autoImport.get(node.name);
if (importPath === undefined) {
continue;
}
if (alreadyImported.has(node.name)) {
continue;
}
if (makeDeclarationsFilename(importPath) === tsDoc.path) {
// Don't import from yourself.
continue;
}
const fileRelative = path.relative(path.dirname(tsDoc.path), importPath);
const fromModuleSpecifier =
fileRelative.startsWith('.') ? fileRelative : './' + fileRelative;
tsDoc.members.push(new ts.Import({
identifiers: [{identifier: node.name}],
fromModuleSpecifier,
}));
alreadyImported.add(node.name);
}

@@ -310,3 +326,3 @@ }

This file was automatically generated by
https://github.com/Polymer/gen-typescript-declarations
https://github.com/Polymer/tools/tree/master/packages/gen-typescript-declarations

@@ -317,15 +333,17 @@ To modify these typings, edit the source file(s):

interface MaybePrivate {
privacy?: 'public'|'private'|'protected';
}
class TypeGenerator {
public warnings: analyzer.Warning[] = [];
private excludeIdentifiers: Set<String>;
/**
* Identifiers in this set will always be considered resolvable, e.g.
* for when determining what identifiers should be exported.
*/
private forceResolvable = new Set<string>();
constructor(
private root: ts.Document,
private analysis: analyzer.Analysis,
private analyzerDoc: analyzer.Document,
private rootDir: string,
private excludeIdentifiers: string[]) {
private root: ts.Document, private analysis: analyzer.Analysis,
private analyzerDoc: analyzer.Document, private rootDir: string,
excludeIdentifiers: string[]) {
this.excludeIdentifiers = new Set(excludeIdentifiers);
}

@@ -350,6 +368,7 @@

for (const feature of this.analyzerDoc.getFeatures()) {
if (this.excludeIdentifiers.some((id) => feature.identifiers.has(id))) {
if ([...feature.identifiers].some(
(id) => this.excludeIdentifiers.has(id))) {
continue;
}
if ((feature as MaybePrivate).privacy === 'private') {
if (isPrivate(feature)) {
continue;

@@ -381,6 +400,5 @@ }

} else if (feature.kinds.has('js-import')) {
this.handleJsImport(
feature as analyzer.JavascriptImport, this.analyzerDoc);
this.handleJsImport(feature as analyzer.JavascriptImport);
} else if (feature.kinds.has('export')) {
this.handleJsExport(feature as analyzer.Export, this.analyzerDoc);
this.handleJsExport(feature as analyzer.Export);
}

@@ -710,3 +728,4 @@ }

for (const property of analyzerProperties) {
if (property.inheritedFrom || property.privacy === 'private') {
if (property.inheritedFrom || property.privacy === 'private' ||
this.excludeIdentifiers.has(property.name)) {
continue;

@@ -737,3 +756,4 @@ }

for (const method of analyzerMethods) {
if (method.inheritedFrom || method.privacy === 'private') {
if (method.inheritedFrom || method.privacy === 'private' ||
this.excludeIdentifiers.has(method.name)) {
continue;

@@ -828,10 +848,5 @@ }

*/
private handleJsImport(
feature: analyzer.JavascriptImport,
doc: analyzer.Document) {
private handleJsImport(feature: analyzer.JavascriptImport) {
const node = feature.astNode.node;
const isResolvable = (identifier: string) =>
resolveImportExportFeature(feature, identifier, doc) !== undefined;
if (babel.isImportDeclaration(node)) {

@@ -842,3 +857,3 @@ const identifiers: ts.ImportSpecifier[] = [];

// E.g. import {Foo, Bar as Baz} from './foo.js'
if (isResolvable(specifier.imported.name)) {
if (this.isResolvable(specifier.imported.name, feature)) {
identifiers.push({

@@ -852,3 +867,3 @@ identifier: specifier.imported.name,

// E.g. import foo from './foo.js'
if (isResolvable('default')) {
if (this.isResolvable('default', feature)) {
identifiers.push({

@@ -866,2 +881,3 @@ identifier: 'default',

});
this.forceResolvable.add(specifier.local.name);
}

@@ -889,8 +905,5 @@ }

*/
private handleJsExport(feature: analyzer.Export, doc: analyzer.Document) {
private handleJsExport(feature: analyzer.Export) {
const node = feature.astNode.node;
const isResolvable = (identifier: string) =>
resolveImportExportFeature(feature, identifier, doc) !== undefined;
if (babel.isExportAllDeclaration(node)) {

@@ -909,3 +922,3 @@ // E.g. export * from './foo.js'

for (const identifier of feature.identifiers) {
if (isResolvable(identifier)) {
if (this.isResolvable(identifier, feature)) {
identifiers.push({identifier});

@@ -918,3 +931,4 @@ }

for (const specifier of node.specifiers) {
if (isResolvable(specifier.exported.name)) {
if (this.isResolvable(specifier.exported.name, feature) ||
this.isResolvable(specifier.local.name, feature)) {
identifiers.push({

@@ -943,2 +957,18 @@ identifier: specifier.local.name,

/**
* True if the given identifier can be resolved to a feature that will be
* exported as a TypeScript type.
*/
private isResolvable(
identifier: string,
fromFeature: analyzer.JavascriptImport|analyzer.Export) {
if (this.forceResolvable.has(identifier)) {
return true;
}
const resolved =
resolveImportExportFeature(fromFeature, identifier, this.analyzerDoc);
return resolved !== undefined && resolved.feature !== undefined &&
!isPrivate(resolved.feature) && !isBehaviorImpl(resolved);
}
/**
* Add an HTML import to a TypeScript declarations file. For a given HTML

@@ -1059,2 +1089,36 @@ * import, we assume there is a corresponding declarations file that was

/**
* Return whether a reference looks like it is a FooBehaviorImpl style behavior
* object, which we want to ignore.
*
* Polymer behavior libraries are often written like:
*
* /** @polymerBehavior FooBehavior *\/
* export const FooBehaviorImpl = {};
*
* /** @polymerBehavior *\/
* export const FooBehavior = [FooBehaviorImpl, OtherBehavior];
*
* In this case, Analyzer merges FooBehaviorImpl into FooBehavior and does not
* emit a behavior feature for FooBehaviorImpl. However, there is still an
* export feature for FooBehaviorImpl, so we exclude it here.
*/
function isBehaviorImpl(reference: analyzer.Reference<analyzer.Feature>) {
return reference.feature !== undefined &&
reference.feature.kinds.has('behavior') &&
(reference.feature as analyzer.PolymerBehavior).name !==
reference.identifier;
}
interface MaybePrivate {
privacy?: 'public'|'private'|'protected';
}
/**
* Return whether the given Analyzer feature has "private" visibility.
*/
function isPrivate(feature: analyzer.Feature&MaybePrivate): boolean {
return feature.privacy === 'private';
}
/**
* Convert kebab-case to CamelCase.

@@ -1061,0 +1125,0 @@ */

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Packages

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc