@@ -5,7 +5,13 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
5
5
Object . defineProperty ( exports , "__esModule" , { value : true } ) ;
6
6
const utils_1 = require ( "../utils" ) ;
7
7
const infuser_1 = __importDefault ( require ( "../infuser" ) ) ;
8
+ const squeezer_1 = __importDefault ( require ( "../squeezer" ) ) ;
8
9
const fs_1 = __importDefault ( require ( "fs" ) ) ;
10
+ const path_1 = __importDefault ( require ( "path" ) ) ;
11
+ const deep_diff_1 = require ( "deep-diff" ) ;
12
+ const glob_1 = __importDefault ( require ( "glob" ) ) ;
13
+ const debug_1 = require ( "debug" ) ;
14
+ const debug = debug_1 . debug ( 'vue-i18n-locale-message:commands:infuse' ) ;
9
15
exports . command = 'infuse' ;
10
16
exports . aliases = 'inf' ;
11
17
exports . describe = 'infuse locale messages to single-file components' ;
@@ -17,23 +23,140 @@ exports.builder = (args) => {
17
23
describe : 'target path that single-file components is stored' ,
18
24
demandOption : true
19
25
} )
20
- . option ( 'messages ' , {
26
+ . option ( 'locales ' , {
21
27
type : 'string' ,
22
- alias : 'm ' ,
28
+ alias : 'l ' ,
23
29
describe : 'locale messages path to be infused' ,
24
30
demandOption : true
31
+ } )
32
+ . option ( 'match' , {
33
+ type : 'string' ,
34
+ alias : 'm' ,
35
+ describe : 'option should be accepted a regex filenames, must be specified together --messages'
25
36
} ) ;
26
37
} ;
27
38
exports . handler = ( args ) => {
28
39
const targetPath = utils_1 . resolve ( args . target ) ;
29
- const messagesPath = utils_1 . resolve ( args . messages ) ;
30
- const newSources = infuser_1 . default ( targetPath , utils_1 . readSFC ( targetPath ) , readLocaleMessages ( messagesPath ) ) ;
40
+ const messagesPath = utils_1 . resolve ( args . locales ) ;
41
+ const sources = utils_1 . readSFC ( targetPath ) ;
42
+ const messages = readLocaleMessages ( messagesPath , args . match ) ;
43
+ const meta = squeezer_1 . default ( targetPath , sources ) ;
44
+ apply ( messages , meta ) ;
45
+ const newSources = infuser_1 . default ( targetPath , sources , meta ) ;
31
46
writeSFC ( newSources ) ;
32
47
} ;
33
- function readLocaleMessages ( path ) {
34
- // TODO: async implementation
35
- const data = fs_1 . default . readFileSync ( path , { encoding : 'utf8' } ) ;
36
- return JSON . parse ( data ) ;
48
+ function readLocaleMessages ( targetPath , matchRegex ) {
49
+ debug ( 'readLocaleMessages' , targetPath , matchRegex ) ;
50
+ if ( ! matchRegex ) {
51
+ const data = fs_1 . default . readFileSync ( targetPath , { encoding : 'utf8' } ) ;
52
+ return JSON . parse ( data ) ;
53
+ }
54
+ else {
55
+ const globPath = path_1 . default . normalize ( `${ targetPath } /*.json` ) ;
56
+ const paths = glob_1 . default . sync ( globPath ) ;
57
+ return paths . reduce ( ( messages , p ) => {
58
+ const re = new RegExp ( matchRegex , 'ig' ) ;
59
+ const filename = path_1 . default . basename ( p ) ;
60
+ const match = re . exec ( filename ) ;
61
+ debug ( 'regex match' , match ) ;
62
+ if ( match ) {
63
+ const data = fs_1 . default . readFileSync ( p , { encoding : 'utf8' } ) ;
64
+ Object . assign ( messages , { [ match [ 1 ] ] : JSON . parse ( data ) } ) ;
65
+ }
66
+ return messages ;
67
+ } , { } ) ;
68
+ }
69
+ }
70
+ function removeItem ( item , items ) {
71
+ const index = items . indexOf ( item ) ;
72
+ if ( index === - 1 ) {
73
+ return false ;
74
+ }
75
+ items . splice ( index , 1 ) ;
76
+ return true ;
77
+ }
78
+ function apply ( messages , meta ) {
79
+ const { target, components } = meta ;
80
+ for ( const [ component , blocks ] of Object . entries ( components ) ) {
81
+ debug ( `apply component = ${ component } , blocks = ${ JSON . stringify ( blocks ) } ` ) ;
82
+ const { hierarchy } = utils_1 . parsePath ( target , component ) ;
83
+ const collectMessages = getTargetLocaleMessages ( messages , hierarchy ) ;
84
+ debug ( 'collect messages' , JSON . stringify ( collectMessages , null , 2 ) ) ;
85
+ const sourceLocales = Object . keys ( collectMessages ) ;
86
+ const targetLocales = blocks . reduce ( ( locales , block ) => {
87
+ if ( block . locale ) {
88
+ locales . push ( block . locale ) ;
89
+ }
90
+ else {
91
+ locales = Object . keys ( block . messages ) . reduce ( ( locales , locale ) => {
92
+ locales . push ( locale ) ;
93
+ return locales ;
94
+ } , locales ) ;
95
+ }
96
+ return locales ;
97
+ } , [ ] ) ;
98
+ debug ( `locales: source = ${ sourceLocales } , target = ${ targetLocales } ` ) ;
99
+ blocks . forEach ( block => {
100
+ const { locale } = block ;
101
+ if ( locale ) {
102
+ deep_diff_1 . applyDiff ( block . messages [ locale ] , collectMessages [ locale ] ) ;
103
+ removeItem ( locale , sourceLocales ) ;
104
+ removeItem ( locale , targetLocales ) ;
105
+ }
106
+ else {
107
+ const locales = Object . keys ( block . messages ) ;
108
+ locales . forEach ( locale => {
109
+ deep_diff_1 . applyDiff ( block . messages [ locale ] , collectMessages [ locale ] ) ;
110
+ removeItem ( locale , sourceLocales ) ;
111
+ removeItem ( locale , targetLocales ) ;
112
+ } ) ;
113
+ }
114
+ } ) ;
115
+ debug ( `locales remain: source = ${ sourceLocales } , target = ${ targetLocales } ` ) ;
116
+ if ( sourceLocales . length ) {
117
+ sourceLocales . forEach ( locale => {
118
+ blocks . push ( {
119
+ lang : 'json' ,
120
+ locale,
121
+ messages : Object . assign ( { } , { [ locale ] : collectMessages [ locale ] } )
122
+ } ) ;
123
+ } ) ;
124
+ }
125
+ if ( targetLocales . length ) {
126
+ debug ( 'invalid target remain locales ...' , targetLocales . length ) ;
127
+ }
128
+ }
129
+ return meta ;
130
+ }
131
+ function getTargetLocaleMessages ( messages , hierarchy ) {
132
+ return Object . keys ( messages ) . reduce ( ( target , locale ) => {
133
+ debug ( `processing curernt: locale=${ locale } , target=${ JSON . stringify ( target ) } ` ) ;
134
+ const obj = messages [ locale ] ;
135
+ if ( obj ) {
136
+ let o = obj ;
137
+ let prev = null ;
138
+ const h = hierarchy . concat ( ) ;
139
+ while ( h . length > 0 ) {
140
+ const key = h . shift ( ) ;
141
+ debug ( 'processing hierarchy key: ' , key ) ;
142
+ if ( ! key || ! o ) {
143
+ break ;
144
+ }
145
+ o = o [ key ] ;
146
+ prev = o ;
147
+ debug ( `processing o = ${ JSON . stringify ( o ) } , prev = ${ JSON . stringify ( prev ) } ` ) ;
148
+ }
149
+ if ( ! o && ! prev ) {
150
+ return target ;
151
+ }
152
+ else {
153
+ return Object . assign ( target , { [ locale ] : ( ( ! o && prev ) ? prev : o ) } ) ;
154
+ }
155
+ }
156
+ else {
157
+ return target ;
158
+ }
159
+ } , { } ) ;
37
160
}
38
161
function writeSFC ( sources ) {
39
162
// TODO: async implementation
0 commit comments