如何在npm上发布angular 2 typescript库

时间:2016-09-15 17:29:27

标签: angular typescript npm webpack bundler

我为angular 2创建了一个打字稿库,便于访问我的后端服务。

到目前为止,它是一个私人仓库,但我想将它作为开源库上传到github并在npm上注册。

我现在不确定该怎么做,因为这个主题的文档不容易找到。

文件夹结构如下所示:

src
|--sdk.ts // entry point
|--services
   |--auth.ts
   |--database.ts
   |--5 more ts files
|--utils
   |--utils.ts
   |--interfaces.ts
|--tests (8 ..spec.ts files)

我的入口点(sdk.ts)看起来像这样

import { NgModule, ModuleWithProviders } from '@angular/core';
import { Injectable } from '@angular/core';
import { SelfbitsDatabase } from './services/database';
import { SelfbitsAuth } from './services/auth';
import { SelfbitsAppConfig } from './utils/interfaces';
import { SelfbitsFile } from './services/file';
import { SelfbitsUser } from './services/user';
import { SelfbitsDevice } from './services/device';
import { SelfbitsPush } from './services/push';
import { HttpModule } from '@angular/http';

@Injectable()
export class SelfbitsAngular {
    constructor(
        public auth : SelfbitsAuth,
        public database : SelfbitsDatabase,
        public file : SelfbitsFile,
        public user : SelfbitsUser,
        public device: SelfbitsDevice,
        public push : SelfbitsPush
    ){}
}

export const SELFBITS_PROVIDERS:any[] = [
    SelfbitsAngular,
    SelfbitsAuth,
    SelfbitsDatabase,
    SelfbitsFile,
    SelfbitsUser,
    SelfbitsDevice,
    SelfbitsPush
];

@NgModule({
    providers:SELFBITS_PROVIDERS,
    imports:[ HttpModule ]
})

export class SelfbitsAngularModule{
    static initializeApp(config:SelfbitsAppConfig):ModuleWithProviders{
        return {
            ngModule:SelfbitsAngularModule,
            providers:[
                { provide: 'SelfbitsConfig', useValue: config }
            ]
        }
    }
}

这里的webpack.config.js并没有真正做到我想要的......

module.exports = {
    entry:'./src/sdk.ts',
    output:{
        path: helpers.root('dist'),
        filename:'selfbitsangular2sdk.js'
    },
    resolve: {
        extensions: ['', '.js', '.ts']
    },

    module: {
        loaders: [
            {
                test: /\.ts$/,
                exclude:'/test/',
                loaders: ['ts-loader']
            }
        ]
    }
};

我不确定webpack是否是正确的选择..或者应该捆绑和缩小或不缩小。欢迎任何提示和tipp!

干杯

4 个答案:

答案 0 :(得分:3)

发布过程非常简单:

# Login with your existing npm user
npm login

# Bump library version
npm version --patch

# Publish your library
npm publish

最难的部分是正确准备package.json的内容以及保存构建库的文件夹(将其命名为dist的常用方法之一)。

您的dist文件夹应包含可供Angular JIT项目以及Angular AOT项目使用的文件。它也应该包含您的库包,它可以直接被浏览器使用(让我们通过SystemJS说)。

结果您的dist文件夹应包含以下文件:

  • index.umd.js - 已准备好进行SystemJS消费的UMD捆绑包
  • index.umd.min.js - 用于保存用户流量的捆绑包的缩小版本
  • index.umd.js.map index.umd.min.js.map - 用于调试目的
  • *。js - [由tsc制作,请记住ngc是一个包装器]编译了库的组件或服务* .ts文件的JavaScript表示。
  • *。d.ts - [由tsc制作,记住ngc是一个包装器]声明文件。由于具有类型的* .ts文件被转换为不支持打字的* .js文件,因此TypeScript编译器需要将所有类型信息放入单独的* .d.ts文件中,以便能够使用这些* .js文件稍后在TypeScript项目中。顺便说一句,有一个DefinitelyTyped项目,它有很多类型定义,已经为很多JS非TypeScript库做出了贡献。
  • * .metanet.json - 与当前组件(或NgModule)关联的元数据。它是我们传递给@Component,@ NgModule装饰器的对象的JSON表示。此文件包含项目(而不是库)NGC将需要的信息,该信息位于原始库* .ts文件中,但未包含在* .d.ts文件中。

在这种情况下,您的package.json应通过mainmoduletypings字段通知您的构建文件:

 {
   ...
   "main": "./dist/index.umd.js",
   "module": "./dist/index.js",
   "typings": "./dist/index.d.ts",
   ...
 }

您可以在dist文件夹中找到有关哪些文件的更详细说明以及如何在How to create AOT/JIT compatible Angular 4 library with external SCSS/HTML templates文章中编译它们

答案 1 :(得分:2)

对于那些仍在试图弄清楚如何做的人:

  1. 使用@ jvandemo' s Angular Lib Yeoman generator

  2. 创建您的图书馆
  3. 之后您只需运行:import { Injectable } from '@angular/core'; import { RandomService } from '../random.service'; @Injectable() export class SavedPostsService { private _state: string; public get state(): string { return this._state; } public constructor(private _randomService: RandomService) { this._state = this._randomService.generateStateString(20); } public getRedditAuthorizationUrl(): string { reurn `https://www.reddit.com/api/v1/authorize?client_id=upw3i_YafZpoXw&response_type=code` + `&state=${this.__state}` + `&redirect_uri=http://localhost:4200/saved-posts&duration=temporary&scope=history`; } } npm adduser

答案 2 :(得分:1)

Angular大学有一个很好的,一步一步的教程,即向npm发布一个Angular 2库,解决您的疑虑/问题。

如果您愿意,可以提供捆绑和非捆绑版本,但我总是提供非捆绑版本。在我的库中,我没有提供捆绑版本,而是让消费者进行捆绑和缩小。

http://blog.angular-university.io/how-to-create-an-angular-2-library-and-how-to-consume-it-jspm-vs-webpack/

更新回答

以下步骤将完成创建,测试和发布非捆绑角度模块的过程,供消费者使用捆绑器(webpack,angular cli等)消费。有关包括捆绑在内的更完整答案,请参阅@ OleksiiTrekhleb的答案。

发布一个角度2库可能会令人生畏,但是当它出现故障时,它与在NPM上发布任何其他软件包没有什么不同。以下信息将使用文件夹结构:

  • 包根
    • SRC
    • DIST

1。设置tsconfig.json

与任何打字稿库一样,您希望declaration下的tsconfig.json设置为compilerOptions,以确保我们的消费者可以利用我们的包中的类型:

"declaration": true

compilerOptions中,我们还要指定我们的outDir,以便将已编译的代码与源代码分开:

"outDir": "./dist"

我们希望include选项指向我们的源文件夹(注意include是与compilerOptions相关的兄弟):

"include": [
  "./src"
]

启用compilerOptions下的实验装饰器选项:

"experimentalDecorators": true,
"emitDecoratorMetadata": true 

为了避免在转换时出现一些错误,您还需要启用skipLibCheck

"skipLibCheck": true

<强>结果

{
  "compilerOptions": {
    "target": "es5",                          /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', or 'ESNEXT'. */
    "module": "commonjs",                     /* Specify module code generation: 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */
    "skipLibCheck": true,
    "declaration": true,                   /* Generates corresponding '.d.ts' file. */
    "outDir": "./dist",                        /* Redirect output structure to the directory. */
    "strict": true,                            /* Enable all strict type-checking options. */
    "experimentalDecorators": true,        /* Enables experimental support for ES7 decorators. */
    "emitDecoratorMetadata": true         /* Enables experimental support for emitting type metadata for decorators. */
  },
  "include": [
    "./src"
  ]
}

2。模块

此示例将使用具有单个组件的模块。该组件非常直接:

./src/helloWorld/helloWorld.component.ts

import { Component } from "@angular/core";

@Component({
    selector: 'hello-world',
    template: '<div>Hello, world</div>'
})
export class HelloWorldComponent {

}

模块应将可消耗组件添加到declarationsexports。我们需要添加导出,因此当消费者导入我们的模块时,他们也可以使用我们的组件。

./src/helloWorld/helloWorld.module.ts

import { NgModule } from '@angular/core'
import { HelloWorldComponent } from './helloWorld.component';

const components: any[] = [
    HelloWorldComponent
];

@NgModule({
    declarations: components,
    exports: components // Don't forget to export!
})
export class HelloWorldModule {

}

3。桶

为了简化我们模块的导入,我们使用一个桶,该文件导出我们的消费者要消费的所有东西。

./src/index.ts

export { HelloWorldModule } from './helloWorld/helloWorld.module';
export { HelloWorldComponent } from './helloWorld/helloWorld.component';

4。设置NPM

<强>的package.json

package.json中,将main属性更改为指向已转换的桶./dist/index.js。同时添加typings属性以指向我们的桶定义文件./dist/index.d.ts

prepublish

的脚本下添加属性package.json
"scripts": {
    "prepublish": "tsc"
}

另请注意,您的角度和相关依赖关系应位于peerDependencies而不是dependencies

NPM忽略

在软件包的根目录中创建一个.npmignore文件,忽略src文件夹以及您不希望随软件包发布的任何其他文件

src/
*.log

5。测试

您可以使用npm link在本地轻松测试您的npm包。在模块包文件夹中,运行命令npm link

然后在您的测试项目中,运行命令npm link <my package name>

现在您可以导入模块并将其添加到测试项目导入中,而无需发布。

6。出版

现在可以使用简单的npm publish

发布您的包

答案 3 :(得分:0)

我一直在和/写一些Angular(2+)库并且捆绑和发布过程总是很痛苦,我发现this tool完成所有工作并使库准备好发货使用ES5,ES6和CommonJS格式。

它非常容易使用,您只需在tsconfig中放入一个文件(入口文件),我将抓取您的所有文件并捆绑您的Angular库,它的内联样式和组件模板!

我认为这对其他人有用。

祝你好运。