Skip to content

Commit

Permalink
⭐ new(cli): squeeze and infuse commands
Browse files Browse the repository at this point in the history
  • Loading branch information
kazupon committed Aug 26, 2019
1 parent 26f0505 commit 60d1136
Show file tree
Hide file tree
Showing 14 changed files with 951 additions and 23 deletions.
7 changes: 6 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,24 +6,29 @@
"name": "kazuya kawaguchi",
"email": "kawakazu80@gmail.com"
},
"bin": "lib/cli.js",
"bugs": {
"url": "https://github.com/kazupon/vue-i18n-locale-message/issues"
},
"dependencies": {
"@vue/component-compiler-utils": "^3.0.0",
"debug": "^4.1.1",
"glob": "^7.1.4",
"js-yaml": "^3.13.1",
"json5": "^2.1.0",
"prettier": "^1.18.2",
"vue-template-compiler": "^2.6.10"
"vue-template-compiler": "^2.6.10",
"yargs": "^13.3.0"
},
"devDependencies": {
"@types/debug": "^4.1.4",
"@types/glob": "^7.1.1",
"@types/jest": "^24.0.15",
"@types/js-yaml": "^3.12.1",
"@types/json5": "^0.0.30",
"@types/node": "^12.6.8",
"@types/prettier": "^1.18.1",
"@types/yargs": "^13.0.2",
"@typescript-eslint/eslint-plugin": "^1.13.0",
"@typescript-eslint/parser": "^1.13.0",
"@typescript-eslint/typescript-estree": "^1.13.0",
Expand Down
23 changes: 23 additions & 0 deletions src/cli.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
#!/usr/bin/env node

import * as yargs from 'yargs'

yargs
.usage('Usage: $0 <command> [options]')
.commandDir('./commands', {
extensions: process.env.NODE_ENV === 'development' ? ['js', 'ts'] : ['js']
})
.demandCommand()
.help()
.version()
.argv

process.on('uncaughtException', err => {
console.error(`uncaught exception: ${err}\n`)
process.exit(1)
})

process.on('unhandledRejection', (reason, p) => {
console.error('unhandled rejection at:', p, 'reason:', reason)
process.exit(1)
})
59 changes: 59 additions & 0 deletions src/commands/infuse.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
import { Arguments, Argv } from 'yargs'

import { resolve, readSFC } from '../utils'
import infuse from '../infuser'
import fs from 'fs'
import { LocaleMessages, SFCFileInfo } from '../../types'

type InfuseOptions = {
target: string
messages: string
}

export const command = 'infuse'
export const aliases = 'inf'
export const describe = 'infuse locale messages to single-file components'

export const builder = (args: Argv): Argv<InfuseOptions> => {
return args
.option('target', {
type: 'string',
alias: 't',
describe: 'target path that single-file components is stored',
demandOption: true
})
.option('messages', {
type: 'string',
alias: 'o',
describe: 'locale messages path to be infused',
demandOption: true
})
}

export const handler = (args: Arguments<InfuseOptions>): void => {
const targetPath = resolve(args.target)
const messagesPath = resolve(args.messages)
const newSources = infuse(targetPath, readSFC(targetPath), readLocaleMessages(messagesPath))
writeSFC(newSources)
}

function readLocaleMessages (path: string): LocaleMessages {
// TODO: async implementation
const data = fs.readFileSync(path, { encoding: 'utf8' })
return JSON.parse(data) as LocaleMessages
}

function writeSFC (sources: SFCFileInfo[]) {
// TODO: async implementation
sources.forEach(({ path, content }) => {
fs.writeFileSync(path, content)
})
}

export default {
command,
aliases,
describe,
builder,
handler
}
51 changes: 51 additions & 0 deletions src/commands/squeeze.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
import { Arguments, Argv } from 'yargs'
import { LocaleMessages } from '../../types'

import { resolve, readSFC } from '../utils'
import squeeze from '../squeezer'
import fs from 'fs'

type SqueezeOptions = {
target: string
output: string
}

export const command = 'squeeze'
export const aliases = 'sqz'
export const describe = 'squeeze locale messages from single-file components'

export const builder = (args: Argv): Argv<SqueezeOptions> => {
const outputDefault = `${process.cwd()}/messages.json`
return args
.option('target', {
type: 'string',
alias: 't',
describe: 'target path that single-file components is stored',
demandOption: true
})
.option('output', {
type: 'string',
alias: 'o',
default: outputDefault,
describe: 'path to output squeezed locale messages'
})
}

export const handler = (args: Arguments<SqueezeOptions>): void => {
const targetPath = resolve(args.target)
const messages = squeeze(targetPath, readSFC(targetPath))
writeLocaleMessages(resolve(args.output), messages)
}

function writeLocaleMessages (output: string, messages: LocaleMessages) {
// TODO: async implementation
fs.writeFileSync(output, JSON.stringify(messages, null, 2))
}

export default {
command,
aliases,
describe,
builder,
handler
}
25 changes: 25 additions & 0 deletions src/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,19 @@ import { VueTemplateCompiler } from '@vue/component-compiler-utils/dist/types'

import { parse } from '@vue/component-compiler-utils'
import * as compiler from 'vue-template-compiler'
import fs from 'fs'
import glob from 'glob'
import path from 'path'
import JSON5 from 'json5'
import yaml from 'js-yaml'

import { debug as Debug } from 'debug'
const debug = Debug('vue-i18n-locale-message:utils')

export function resolve (...paths: string[]): string {
return path.resolve(...paths)
}

export function reflectSFCDescriptor (basePath: string, components: SFCFileInfo[]): SFCDescriptor[] {
return components.map(target => {
const { template, script, styles, customBlocks } = parse({
Expand Down Expand Up @@ -68,3 +74,22 @@ export function stringfyContent (content: any, lang: string): string {
return JSON.stringify(content, null, 2)
}
}

export function readSFC (target: string): SFCFileInfo[] {
const targets = resolveGlob(target)
debug('readSFC: targets = ', targets)

// TODO: async implementation
return targets.map(target => {
const data = fs.readFileSync(target)
return {
path: target,
content: data.toString()
}
})
}

function resolveGlob (target: string) {
// TODO: async implementation
return glob.sync(`${target}/**/*.vue`)
}
42 changes: 42 additions & 0 deletions test/__snapshots__/cli.test.ts.snap
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`infuse command output help 1`] = `
"processChild.js infuse
infuse locale messages to single-file components
Options:
--version Show version number [boolean]
--help Show help [boolean]
--target, -t target path that single-file components is stored
[string] [required]
--messages, -o locale messages path to be infused [string] [required]"
`;

exports[`squeeze command output help 1`] = `
"processChild.js squeeze
squeeze locale messages from single-file components
Options:
--version Show version number [boolean]
--help Show help [boolean]
--target, -t target path that single-file components is stored
[string] [required]
--output, -o path to output squeezed locale messages
[string] [default: \\"/path/to/project1/messages.json\\"]"
`;

exports[`top output help 1`] = `
"Usage: processChild.js <command> [options]
Commands:
processChild.js squeeze squeeze locale messages from single-file components
[aliases: sqz]
processChild.js infuse infuse locale messages to single-file components
[aliases: inf]
Options:
--version Show version number [boolean]
--help Show help [boolean]"
`;
62 changes: 62 additions & 0 deletions test/cli.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
import * as yargs from 'yargs'
import squeeze from '../src/commands/squeeze'
import infuse from '../src/commands/infuse'

let orgCwd
beforeEach(async () => {
orgCwd = process.cwd
process.cwd = jest.fn(() => '/path/to/project1')
})

afterEach(() => {
jest.clearAllMocks()
process.cwd = orgCwd
})

test('top output help', async () => {
const cmd = yargs
.usage('Usage: $0 <command> [options]')
.command(squeeze)
.command(infuse)
.demandCommand()
.locale('en')
.help()
const output = await new Promise(resolve => {
// eslint-disable-next-line handle-callback-err
cmd.parse('--help', (err, argv, output) => {
resolve(output)
})
})

expect(output).toMatchSnapshot()
})

test('squeeze command output help', async () => {
const cmd = yargs
.command(squeeze)
.locale('en')
.help()
const output = await new Promise(resolve => {
// eslint-disable-next-line handle-callback-err
cmd.parse('squeeze --help', (err, argv, output) => {
resolve(output)
})
})

expect(output).toMatchSnapshot()
})

test('infuse command output help', async () => {
const cmd = yargs
.command(infuse)
.locale('en')
.help()
const output = await new Promise(resolve => {
// eslint-disable-next-line handle-callback-err
cmd.parse('infuse --help', (err, argv, output) => {
resolve(output)
})
})

expect(output).toMatchSnapshot()
})

0 comments on commit 60d1136

Please sign in to comment.