diff --git a/hackernews-async-ts/.autod.conf.js b/hackernews-async-ts/.autod.conf.js index 96fdfa1..44bb3fb 100644 --- a/hackernews-async-ts/.autod.conf.js +++ b/hackernews-async-ts/.autod.conf.js @@ -7,23 +7,23 @@ module.exports = { devprefix: '^', exclude: [ 'test/fixtures', + 'coverage', ], dep: [ 'egg', 'egg-scripts', 'egg-view-nunjucks', 'moment', - 'source-map-support', ], devdep: [ 'autod', 'autod-egg', 'egg-bin', - ], - keep: [ 'tslib', 'typescript', ], + keep: [ + ], semver: [ ], test: 'scripts', diff --git a/hackernews-async-ts/README.md b/hackernews-async-ts/README.md index dded0eb..b5946f5 100644 --- a/hackernews-async-ts/README.md +++ b/hackernews-async-ts/README.md @@ -1,38 +1,33 @@ -# egg-example-hackernews-async +# hackernews-async-ts -[Hacker News](https://news.ycombinator.com/) showcase using async/await for egg +[Hacker News](https://news.ycombinator.com/) showcase using typescript && egg ## QuickStart ### Development -```shell -$ npm install -$ npm run tsc:w + +```bash +$ npm i $ npm run dev $ open http://localhost:7001/ ``` -### Deploy +Don't tsc compile at development mode, if you had run `tsc` then you need to `npm run clean` before `npm run dev`. -Use `EGG_SERVER_ENV=prod` to enable prod mode +### Deploy -```shell -$ EGG_SERVER_ENV=prod npm start +```bash +$ npm run tsc +$ npm start ``` ### Npm Scripts -- Use `npm run autod` to auto detect dependencies upgrade - Use `npm run lint` to check code style - Use `npm test` to run unit test +- se `npm run clean` to clean compiled js at development mode once ### Requirement -Please ensure your node version is `>=7.6.0` for async await support without flag. If your node version is `>=7.0.0 < 7.6.0`, you can run npm scripts with harmony flag - -```shell -# start server -npm run dev -- --harmony-async-await -# run test cases -npm run test-local -- --harmony-async-await -``` +- Node.js 8.x +- Typescript 2.8+ diff --git a/hackernews-async-ts/app/controller/news.ts b/hackernews-async-ts/app/controller/news.ts index 1fe7734..851f8fe 100644 --- a/hackernews-async-ts/app/controller/news.ts +++ b/hackernews-async-ts/app/controller/news.ts @@ -6,26 +6,26 @@ export default class NewsController extends Controller { const pageSize = app.config.news.pageSize; const page = parseInt(ctx.query.page, 10) || 1; - const idList = await ctx.service.hackerNews.getTopStories(page); + const idList = await ctx.service.news.getTopStories(page); // get itemInfo parallel - const newsList = await Promise.all(idList.map((id) => ctx.service.hackerNews.getItem(id))); + const newsList = await Promise.all(idList.map((id) => ctx.service.news.getItem(id))); await ctx.render('news/list.tpl', { list: newsList, page, pageSize }); } public async detail() { const { ctx } = this; const id = ctx.params.id; - const newsInfo = await ctx.service.hackerNews.getItem(id); + const newsInfo = await ctx.service.news.getItem(id); // get comment parallel - const commentList = await Promise.all(newsInfo.kids.map((_id) => ctx.service.hackerNews.getItem(_id))); + const commentList = await Promise.all(newsInfo.kids.map((_id) => ctx.service.news.getItem(_id))); await ctx.render('news/detail.tpl', { item: newsInfo, comments: commentList }); } public async user() { const { ctx } = this; const id = ctx.params.id; - const userInfo = await ctx.service.hackerNews.getUser(id); + const userInfo = await ctx.service.news.getUser(id); await ctx.render('news/user.tpl', { user: userInfo }); } } diff --git a/hackernews-async-ts/app/extend/filter.ts b/hackernews-async-ts/app/extend/filter.ts index e74123e..7c22c89 100644 --- a/hackernews-async-ts/app/extend/filter.ts +++ b/hackernews-async-ts/app/extend/filter.ts @@ -2,6 +2,10 @@ import * as moment from 'moment'; -exports.relativeTime = (time) => moment(new Date(time * 1000)).fromNow(); +export function relativeTime(time) { + return moment(new Date(time * 1000)).fromNow(); +}; -exports.domain = (url) => url && url.split('/')[2]; +export function domain (url) { + return url && url.split('/')[2]; +}; diff --git a/hackernews-async-ts/app/router.ts b/hackernews-async-ts/app/router.ts index 50a9d49..cead0f3 100644 --- a/hackernews-async-ts/app/router.ts +++ b/hackernews-async-ts/app/router.ts @@ -3,7 +3,7 @@ import { Application } from 'egg'; export default (app: Application) => { const { controller, router } = app; - // router.redirect('/', '/news'); + router.redirect('/', '/news'); router.get('/news', controller.news.list); router.get('/news/item/:id', controller.news.detail); router.get('/news/user/:id', controller.news.user); diff --git a/hackernews-async-ts/app/service/HackerNews.ts b/hackernews-async-ts/app/service/News.ts similarity index 100% rename from hackernews-async-ts/app/service/HackerNews.ts rename to hackernews-async-ts/app/service/News.ts diff --git a/hackernews-async-ts/app/view/layout/layout.tpl b/hackernews-async-ts/app/view/layout/layout.tpl index d9fcc3d..aae4fb2 100644 --- a/hackernews-async-ts/app/view/layout/layout.tpl +++ b/hackernews-async-ts/app/view/layout/layout.tpl @@ -13,7 +13,7 @@

Hacker News

- Built with egg | Source + Built with Egg | Source {% block content %}{% endblock %} diff --git a/hackernews-async-ts/config/config.default.ts b/hackernews-async-ts/config/config.default.ts index 7265d53..5cb0b04 100644 --- a/hackernews-async-ts/config/config.default.ts +++ b/hackernews-async-ts/config/config.default.ts @@ -1,12 +1,15 @@ 'use strict'; + import { EggAppConfig, PowerPartial } from 'egg'; import * as fs from 'fs'; import * as path from 'path'; +// for config.{env}.ts export type DefaultConfig = PowerPartial; -// 本应用的自定义配置的定义 +// app special config scheme export interface BizConfig { + sourceUrl: string; news: { pageSize: number; serverUrl: string; @@ -16,10 +19,17 @@ export interface BizConfig { export default (appInfo: EggAppConfig) => { const config = {} as PowerPartial & BizConfig; + // app special config + config.sourceUrl = `https://github.com/eggjs/examples/tree/master/${appInfo.name}`; + config.news = { + pageSize: 30, + serverUrl: 'https://hacker-news.firebaseio.com/v0', + }; + + // override config from framework / plugin config.keys = appInfo.name + '123456'; config.view = { - root: path.join(appInfo.baseDir, 'app/view'), defaultViewEngine: 'nunjucks', mapping: { '.tpl': 'nunjucks', @@ -30,10 +40,5 @@ export default (appInfo: EggAppConfig) => { '/favicon.ico': fs.readFileSync(path.join(appInfo.baseDir, 'app/public/favicon.png')), }; - config.news = { - pageSize: 30, - serverUrl: 'https://hacker-news.firebaseio.com/v0', - }; - return config; }; diff --git a/hackernews-async-ts/config/plugin.ts b/hackernews-async-ts/config/plugin.ts index 31c3046..99c3979 100644 --- a/hackernews-async-ts/config/plugin.ts +++ b/hackernews-async-ts/config/plugin.ts @@ -1,7 +1,8 @@ -exports.static = true; +'use strict'; -exports.nunjucks = { - enable: true, - package: 'egg-view-nunjucks', +export default { + nunjucks: { + enable: true, + package: 'egg-view-nunjucks', + }, }; - diff --git a/hackernews-async-ts/package.json b/hackernews-async-ts/package.json index 1845c04..62b092d 100644 --- a/hackernews-async-ts/package.json +++ b/hackernews-async-ts/package.json @@ -1,17 +1,29 @@ { - "name": "egg-example-hackernews-async-ts", + "name": "hackernews-async-ts", "version": "1.0.0", - "description": "hackernews showcase using async/await for egg", + "description": "hackernews showcase using typescript && egg", "private": true, "egg": { "typescript": true }, + "scripts": { + "start": "egg-scripts start", + "dev": "egg-bin dev -r egg-ts-helper/register", + "debug": "egg-bin debug -r egg-ts-helper/register", + "test-local": "egg-bin test -r egg-ts-helper/register", + "test": "npm run lint -- --fix && npm run test-local", + "cov": "egg-bin cov", + "tsc": "ets && tsc -p tsconfig.json", + "ci": "npm run lint && npm run tsc && egg-bin cov --no-ts", + "autod": "autod", + "lint": "tslint .", + "clean": "ets clean" + }, "dependencies": { - "egg": "^2.5.0", - "egg-scripts": "^2.5.1", + "egg": "^2.6.0", + "egg-scripts": "^2.6.0", "egg-view-nunjucks": "^2.2.0", - "moment": "^2.21.0", - "source-map-support": "^0.5.4" + "moment": "^2.22.0" }, "devDependencies": { "@types/cheerio": "^0.22.1", @@ -21,7 +33,7 @@ "autod": "^3.0.1", "autod-egg": "^1.1.0", "cheerio": "^1.0.0-rc.2", - "egg-bin": "^4.6.0", + "egg-bin": "^4.6.2", "egg-mock": "^3.16.0", "egg-ts-helper": "^1.4.2", "rimraf": "^2.6.1", @@ -31,18 +43,5 @@ }, "engines": { "node": ">=8.9.0" - }, - "scripts": { - "start": "egg-scripts start", - "dev": "egg-bin dev -r egg-ts-helper/register", - "tsc": "ets && tsc -p tsconfig.json", - "clean": "ets clean", - "test": "npm run lint -- --fix && npm run test-local", - "test-local": "egg-bin test -r egg-ts-helper/register", - "cov": "egg-bin cov", - "lint": "tslint .", - "ci": "npm run lint && npm run cov", - "debug": "egg-bin debug", - "autod": "autod" } } diff --git a/hackernews-async-ts/test/app/service/HackerNews.test.ts b/hackernews-async-ts/test/app/service/News.test.ts similarity index 65% rename from hackernews-async-ts/test/app/service/HackerNews.test.ts rename to hackernews-async-ts/test/app/service/News.test.ts index 2d6bf27..804235c 100644 --- a/hackernews-async-ts/test/app/service/HackerNews.test.ts +++ b/hackernews-async-ts/test/app/service/News.test.ts @@ -3,7 +3,7 @@ import { Context } from 'egg'; import { app, assert } from 'egg-mock/bootstrap'; -describe('test/app/service/HackerNews.test.js', () => { +describe('test/app/service/News.test.js', () => { let ctx: Context; before(async () => { @@ -11,12 +11,12 @@ describe('test/app/service/HackerNews.test.js', () => { }); it('getTopStories', async () => { - const list = await ctx.service.hackerNews.getTopStories(); + const list = await ctx.service.news.getTopStories(); assert(list.length === 30); }); it('getItem', async () => { - const item = await ctx.service.hackerNews.getItem(1); + const item = await ctx.service.news.getItem(1); assert(item.id && item.title && item.url); }); }); diff --git a/hackernews-async-ts/typings/app/service/index.d.ts b/hackernews-async-ts/typings/app/service/index.d.ts index d51448b..2f6ba7f 100644 --- a/hackernews-async-ts/typings/app/service/index.d.ts +++ b/hackernews-async-ts/typings/app/service/index.d.ts @@ -1,10 +1,10 @@ // This file was auto created by egg-ts-helper // Do not modify this file!!!!!!!!! -import HackerNews from '../../../app/service/HackerNews'; +import News from '../../../app/service/News'; declare module 'egg' { interface IService { - hackerNews: HackerNews; + news: News; } } diff --git a/hackernews-async-ts/typings/index.d.ts b/hackernews-async-ts/typings/index.d.ts index ae2f559..57f2414 100644 --- a/hackernews-async-ts/typings/index.d.ts +++ b/hackernews-async-ts/typings/index.d.ts @@ -1,8 +1,3 @@ -// extend egg declare module 'egg' { - type PowerPartial = { - [U in keyof T]?: T[U] extends {} - ? { [V in keyof T[U]]?: T[U][V] extends {} ? Partial : T[U][V] } - : T[U] - }; + } \ No newline at end of file