├── .editorconfig ├── .eslintrc.js ├── .gitattributes ├── .github └── workflows │ └── nodejs.yml ├── .gitignore ├── .media └── demo.gif ├── .prettierrc.js ├── CHANGELOG.md ├── DEPCOST.md ├── LICENSE ├── README.md ├── __tests__ └── index.test.js ├── docs └── .vuepress │ ├── config.js │ └── schemas │ ├── schema.json │ └── schema.md ├── lib └── index.js └── package.json /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | indent_style = space 5 | indent_size = 2 6 | end_of_line = lf 7 | charset = utf-8 8 | trim_trailing_whitespace = true 9 | insert_final_newline = true 10 | 11 | [*.md] 12 | trim_trailing_whitespace = false -------------------------------------------------------------------------------- /.eslintrc.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | extends: [ 3 | 'lab' 4 | ] 5 | }; 6 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | * text=auto 2 | -------------------------------------------------------------------------------- /.github/workflows/nodejs.yml: -------------------------------------------------------------------------------- 1 | # This workflow will do a clean install of node dependencies, build the source code and run tests across different versions of node 2 | # For more information see: https://help.github.com/actions/language-and-framework-guides/using-nodejs-with-github-actions 3 | 4 | name: Node.js CI 5 | 6 | on: 7 | push: 8 | branches: [ master ] 9 | pull_request: 10 | branches: [ master ] 11 | 12 | jobs: 13 | build: 14 | 15 | runs-on: ubuntu-latest 16 | 17 | strategy: 18 | matrix: 19 | node-version: [8.x, 10.x, 12.x] 20 | 21 | steps: 22 | - uses: actions/checkout@v2 23 | - name: Use Node.js ${{ matrix.node-version }} 24 | uses: actions/setup-node@v1 25 | with: 26 | node-version: ${{ matrix.node-version }} 27 | - run: npm install 28 | - run: npm run build --if-present 29 | - run: npm run lint --if-present 30 | - run: npm run cov 31 | env: 32 | CI: true 33 | - uses: codecov/codecov-action@v1 34 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | coverage 3 | .temp 4 | -------------------------------------------------------------------------------- /.media/demo.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vuepress/vuepress-plugin-schema2md/5d999e30548a862e248e16a090214223c496528d/.media/demo.gif -------------------------------------------------------------------------------- /.prettierrc.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | trailingComma: 'es5', 3 | semi: false, 4 | singleQuote: true, 5 | bracketSpacing: true 6 | }; 7 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | 2 | ## [0.2.2](https://github.com/rich-lab/json-schema-2-markdown/compare/v0.2.1...v0.2.2) (2020-03-09) 3 | 4 | 5 | ### Bug Fixes 6 | 7 | * process should exit after build. ([7e77f2d](https://github.com/rich-lab/json-schema-2-markdown/commit/7e77f2d)) 8 | 9 | 10 | 11 | ## [0.2.1](https://github.com/rich-lab/json-schema-2-markdown/compare/v0.2.0...v0.2.1) (2020-03-07) 12 | 13 | 14 | 15 | # [0.2.0](https://github.com/rich-lab/json-schema-2-markdown/compare/9ef86aa4a12f09a0ee8010db62494380b329d5ad...v0.2.0) (2020-03-07) 16 | 17 | 18 | ### Features 19 | 20 | * init ([9ef86aa](https://github.com/rich-lab/json-schema-2-markdown/commit/9ef86aa4a12f09a0ee8010db62494380b329d5ad)) 21 | 22 | 23 | 24 | -------------------------------------------------------------------------------- /DEPCOST.md: -------------------------------------------------------------------------------- 1 | ## 0.2.2 2 | 3 | | name | install size | reuqire time | 4 | | --- | --- | --- | 5 | | vuepress-plugin-schema2md@0.2.2 | 1.0M | 27.973ms | 6 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) ULIVZ (https://github.com/ulivz) 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # vuepress-plugin-schema2md 2 | 3 | [![NPM version](https://img.shields.io/npm/v/vuepress-plugin-schema2md.svg?style=flat)](https://npmjs.com/package/vuepress-plugin-schema2md) [![NPM downloads](https://img.shields.io/npm/dm/vuepress-plugin-schema2md.svg?style=flat)](https://npmjs.com/package/vuepress-plugin-schema2md) ![Node.js CI](https://github.com/rich-lab/vuepress-plugin-schema2md/workflows/Node.js%20CI/badge.svg) 4 | 5 | ## Feature 6 | 7 | - 📄 Generate dynamic VuePress pages from JSON Schemas. 8 | - ❤️ HMR Support! 9 | - 🎁 Support extra markdown file to be merged into final content. 10 | 11 | ## Example 12 | 13 | ![](./.media/demo.gif) 14 | 15 |

16 | Tip. you can execute npm run docs:dev on thie repo to check out this example. 17 |

18 | 19 | 20 | ## Install 21 | 22 | ```bash 23 | yarn add vuepress-plugin-schema2md -D 24 | # OR npm install vuepress-plugin-schema2md -D 25 | ``` 26 | 27 | ## Usage 28 | 29 | ```js 30 | // .vuepress/config.js 31 | module.exports = { 32 | plugins: [ 33 | [ 34 | 'schema2md', { 35 | // Options 36 | } 37 | ] 38 | ] 39 | } 40 | ``` 41 | 42 | ## Options 43 | 44 | ### pages 45 | 46 | - Type: `Record` 47 | - Description: describe the generated pages. 48 | 49 | e.g. 50 | 51 | ```js 52 | // .vuepress/config.js 53 | module.exports = { 54 | plugins: ['schema2md', { 55 | pages: { 56 | '/config/': { 57 | schemaPath: '/path/to/your/schema.json' 58 | } 59 | } 60 | }] 61 | } 62 | ``` 63 | 64 | Then you will get a dynamic page with route `/config/`, whose content is generated by [schema2md](https://github.com/rich-lab/schema2md) from `'/path/to/your/schema.json'`, 65 | 66 | For typings of interface `ITransformOptions`, plead head [schema2md](https://github.com/rich-lab/schema2md). 67 | 68 | ### cwd 69 | 70 | - Type: `string` 71 | - Description: Current working directory, used to calcaulate absolute path for "schemaPath" and "outputPath" with relative path, defaults to `process.cwd()`. 72 | 73 | ### locale 74 | 75 | - Type: `string` 76 | - Description: Global locale. 77 | 78 | ### write 79 | 80 | - Type: `boolean` 81 | - Description: whether to generate the markdown content to disk. 82 | 83 | If you want to check out the generated markdown, you could do like this: 84 | 85 | ```diff 86 | // .vuepress/config.js 87 | module.exports = { 88 | plugins: ['schema2md', { 89 | + write: true, 90 | pages: { 91 | '/config/': { 92 | schemaPath: '/path/to/your/schema.json' 93 | + outputPath: 'docs/config/README.md', // You shouldn't commit this file. 94 | } 95 | } 96 | }] 97 | } 98 | ``` 99 | 100 | ## Contributing 101 | 102 | 1. Fork it! 103 | 2. Create your feature branch: `git checkout -b my-new-feature` 104 | 3. Commit your changes: `git commit -am 'Add some feature'` 105 | 4. Push to the branch: `git push origin my-new-feature` 106 | 5. Submit a pull request :D 107 | 108 | 109 | ## Author 110 | 111 | **vuepress-plugin-schema2md** © [ULIVZ](https://github.com/ulivz), Released under the [MIT](./LICENSE) License.
112 | 113 | 114 | > [github.com/ulivz](https://github.com/ulivz) · GitHub [@ULIVZ](https://github.com/ulivz) · Twitter [@_ulivz](https://twitter.com/_ulivz) 115 | 116 | 117 | -------------------------------------------------------------------------------- /__tests__/index.test.js: -------------------------------------------------------------------------------- 1 | const plugin = require('../lib') 2 | 3 | it('simple', async () => { 4 | expect(typeof plugin).toBe('function') 5 | }) 6 | 7 | -------------------------------------------------------------------------------- /docs/.vuepress/config.js: -------------------------------------------------------------------------------- 1 | const { join, resolve } = require('path') 2 | const pkg = require('../../package') 3 | 4 | module.exports = { 5 | title: pkg.name, 6 | description: pkg.description, 7 | additionalPages: [ 8 | { 9 | path: '/', 10 | filePath: resolve(__dirname, '../../README.md') 11 | }, 12 | ], 13 | themeConfig: { 14 | nav: [ 15 | { text: 'foo.config.js', link: '/config/' }, 16 | ], 17 | }, 18 | plugins: [ 19 | [require('../../lib'), { 20 | cwd: __dirname, 21 | pages: { 22 | '/config/': { 23 | schemaPath: 'schemas/schema.json' 24 | } 25 | } 26 | }] 27 | ], 28 | } 29 | -------------------------------------------------------------------------------- /docs/.vuepress/schemas/schema.json: -------------------------------------------------------------------------------- 1 | { 2 | "title": "foo.config.js", 3 | "description": "Description of foo.config.js", 4 | "properties": { 5 | "type": { 6 | "description": "TYPE's description", 7 | "type": "string", 8 | "enum": [ 9 | "foo", 10 | "bar" 11 | ] 12 | }, 13 | "env": { 14 | "description": "ENV's description", 15 | "type": "string" 16 | }, 17 | "name": { 18 | "description": "ENV's description", 19 | "type": "string" 20 | } 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /docs/.vuepress/schemas/schema.md: -------------------------------------------------------------------------------- 1 | ## type 2 | 3 | extra content of type. 4 | 5 | ::: warning WARN 6 | This is a warning of type's usage. 7 | ::: 8 | 9 | ## env 10 | 11 | extra content of env. 12 | 13 | ::: tip TIP 14 | This is a env of env's usage. 15 | ::: 16 | 17 | ## env 18 | 19 | extra content of name. 20 | 21 | 22 | -------------------------------------------------------------------------------- /lib/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | * Vuepress-plugin-schema2md © 2016-present. 3 | * @author ulivz 4 | * @date March.7th, 2020 5 | */ 6 | 7 | const { watch } = require('chokidar') 8 | const { 9 | logger, 10 | fs, 11 | chalk: { cyan }, 12 | } = require('@vuepress/shared-utils') 13 | const { 14 | resolveSchemaMarkdownPath, 15 | batchTransform, 16 | normalizePath, 17 | transform, 18 | } = require('schema2md') 19 | 20 | let watcher 21 | 22 | module.exports = (options, ctx) => { 23 | /** 24 | * Watch scheme file and emit the temp markdown file when it's changed. 25 | * 26 | * @param {object} paths 27 | * @param {function} callback 28 | */ 29 | function addSchemaListener(paths, callback) { 30 | if (watcher) { 31 | return 32 | } 33 | 34 | const watchPaths = paths.reduce((memo, p) => { 35 | memo.push(p.schemaPath) 36 | memo.push(p.schemaMarkdownPath) 37 | return memo 38 | }, []) 39 | 40 | watcher = watch(watchPaths, { 41 | ignoreInitial: true, 42 | }) 43 | 44 | const handleSchemaChange = schemaPath => { 45 | let target 46 | if (schemaPath.endsWith('.json')) { 47 | target = paths.find(p => p.schemaPath === schemaPath) 48 | } else { 49 | target = paths.find(p => p.schemaMarkdownPath === schemaPath) 50 | } 51 | 52 | const { sitePath } = target 53 | const targetPage = ctx.pages.find(page => page.path === sitePath) 54 | if (targetPage) { 55 | const { _filePath } = targetPage 56 | return { 57 | sitePath, 58 | filePath: _filePath, 59 | schemaPath, 60 | } 61 | } 62 | } 63 | 64 | watcher.on('change', schemaPath => { 65 | logger.tip(`[schema2md] ${cyan(schemaPath)} changed`) 66 | const ret = handleSchemaChange(schemaPath) 67 | callback(ret) 68 | }) 69 | 70 | watcher.on('unlink', schemaPath => { 71 | logger.tip(`[schema2md] ${cyan(schemaPath)} removed`) 72 | const ret = handleSchemaChange(schemaPath) 73 | fs.removeSync(ret.filePath) 74 | }) 75 | } 76 | 77 | return { 78 | async additionalPages() { 79 | const { cwd = process.cwd(), locale, write = false, pages } = options 80 | const pagePaths = Object.keys(pages) 81 | const configs = pagePaths.map(p => pages[p]) 82 | 83 | const schemaPaths = pagePaths.map(p => { 84 | const abSchemaPath = normalizePath(cwd, pages[p].schemaPath) 85 | return { 86 | sitePath: p, 87 | schemaMarkdownPath: resolveSchemaMarkdownPath( 88 | pages[p].schemaMarkdown, 89 | abSchemaPath, 90 | ), 91 | schemaPath: abSchemaPath, 92 | } 93 | }) 94 | 95 | addSchemaListener(schemaPaths, async ret => { 96 | const targetConfog = pages[ret.sitePath] 97 | if (targetConfog) { 98 | const content = await transform({ 99 | cwd, 100 | locale, 101 | write, 102 | ...targetConfog, 103 | }) 104 | await fs.writeFile(ret.filePath, content, 'utf-8') 105 | } 106 | }) 107 | 108 | const ret = await batchTransform({ 109 | cwd, 110 | locale, 111 | write, 112 | configs, 113 | }) 114 | 115 | return pagePaths.map((path, index) => ({ 116 | path, 117 | content: ret[index], 118 | })) 119 | }, 120 | 121 | generated() { 122 | if (watcher) { 123 | watcher.close && watcher.close() 124 | } 125 | }, 126 | } 127 | } 128 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vuepress-plugin-schema2md", 3 | "version": "0.2.2", 4 | "description": "A VuePress plugin to help you generate pages via JSON Schema (HMR Support).", 5 | "main": "lib/index.js", 6 | "files": [ 7 | "lib" 8 | ], 9 | "scripts": { 10 | "test": "jest", 11 | "cov": "jest --coverage", 12 | "lint": "eslint --fix lib", 13 | "prepublishOnly": "conventional-changelog -p angular -r 2 -i CHANGELOG.md -s", 14 | "docs:dev": "vuepress dev docs --temp docs/.temp", 15 | "docs:build": "npm run docs:prepare && vuepress build docs --temp docs/.temp", 16 | "depcost": "depcost --record --npm-client=npm", 17 | "postpublish": "npm run depcost" 18 | }, 19 | "repository": { 20 | "url": "https://github.com/rich-lab/json-schema-2-markdown", 21 | "type": "git" 22 | }, 23 | "author": "ulivz ", 24 | "license": "MIT", 25 | "dependencies": { 26 | "chokidar": "^3.3.1", 27 | "schema2md": "^0.1.5" 28 | }, 29 | "devDependencies": { 30 | "vuepress": "^1.3.1", 31 | "@vuepress/shared-utils": "^1.3.1", 32 | "jest-cli": "^25.1.0", 33 | "eslint": "^6.8.0", 34 | "eslint-config-lab": "^0.1.4", 35 | "depcost": "^0.2.1" 36 | }, 37 | "publishConfig": { 38 | "registry": "https://registry.npmjs.org/" 39 | } 40 | } 41 | --------------------------------------------------------------------------------