storyblok 3.13.1 → 3.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +12 -0
- package/package.json +2 -1
- package/src/cli.js +25 -0
- package/src/tasks/index.js +1 -0
- package/src/tasks/pull-languages.js +39 -0
- package/src/tasks/sync-commands/datasources.js +145 -13
- package/src/tasks/sync.js +8 -8
- package/src/utils/api.js +9 -0
- package/tests/constants.js +21 -1
- package/tests/units/pull-languages.spec.js +62 -0
package/README.md
CHANGED
|
@@ -28,6 +28,18 @@ Usage to kickstart a boilerplate, fieldtype or theme
|
|
|
28
28
|
$ storyblok select
|
|
29
29
|
```
|
|
30
30
|
|
|
31
|
+
### pull-languages
|
|
32
|
+
|
|
33
|
+
Download your space's languages schema as json. This command will download 1 file.
|
|
34
|
+
|
|
35
|
+
```sh
|
|
36
|
+
$ storyblok pull-languages --space <SPACE_ID>
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
#### Options
|
|
40
|
+
|
|
41
|
+
* `space`: your space id
|
|
42
|
+
|
|
31
43
|
### pull-components
|
|
32
44
|
|
|
33
45
|
Download your space's components schema as json. This command will download 2 files: 1 for the components and 1 for the presets.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "storyblok",
|
|
3
|
-
"version": "3.
|
|
3
|
+
"version": "3.15.0",
|
|
4
4
|
"description": "A simple CLI to start Storyblok from your command line.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"storyblok",
|
|
@@ -37,6 +37,7 @@
|
|
|
37
37
|
"open": "^6.0.0",
|
|
38
38
|
"p-series": "^2.1.0",
|
|
39
39
|
"path": "^0.12.7",
|
|
40
|
+
"simple-uuid": "^0.0.1",
|
|
40
41
|
"storyblok-js-client": "^4.5.6",
|
|
41
42
|
"update-notifier": "^5.1.0",
|
|
42
43
|
"xml-js": "^1.6.11"
|
package/src/cli.js
CHANGED
|
@@ -69,6 +69,31 @@ program
|
|
|
69
69
|
}
|
|
70
70
|
})
|
|
71
71
|
|
|
72
|
+
// pull-languages
|
|
73
|
+
program
|
|
74
|
+
.command('pull-languages')
|
|
75
|
+
.description("Download your space's languages schema as json")
|
|
76
|
+
.action(async () => {
|
|
77
|
+
console.log(`${chalk.blue('-')} Executing pull-languages task`)
|
|
78
|
+
const space = program.space
|
|
79
|
+
if (!space) {
|
|
80
|
+
console.log(chalk.red('X') + ' Please provide the space as argument --space YOUR_SPACE_ID.')
|
|
81
|
+
process.exit(0)
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
try {
|
|
85
|
+
if (!api.isAuthorized()) {
|
|
86
|
+
await api.processLogin()
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
api.setSpaceId(space)
|
|
90
|
+
await tasks.pullLanguages(api, { space })
|
|
91
|
+
} catch (e) {
|
|
92
|
+
console.log(chalk.red('X') + ' An error occurred when executing the pull-languages task: ' + e.message)
|
|
93
|
+
process.exit(1)
|
|
94
|
+
}
|
|
95
|
+
})
|
|
96
|
+
|
|
72
97
|
// pull-components
|
|
73
98
|
program
|
|
74
99
|
.command(COMMANDS.PULL_COMPONENTS)
|
package/src/tasks/index.js
CHANGED
|
@@ -3,6 +3,7 @@ module.exports = {
|
|
|
3
3
|
scaffold: require('./scaffold'),
|
|
4
4
|
quickstart: require('./quickstart'),
|
|
5
5
|
pullComponents: require('./pull-components'),
|
|
6
|
+
pullLanguages: require('./pull-languages'),
|
|
6
7
|
pushComponents: require('./push-components'),
|
|
7
8
|
generateMigration: require('./migrations/generate'),
|
|
8
9
|
runMigration: require('./migrations/run'),
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
const fs = require('fs')
|
|
2
|
+
const chalk = require('chalk')
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* @method pullLanguages
|
|
6
|
+
* @param {Object} api
|
|
7
|
+
* @param {Object} options { space: Number }
|
|
8
|
+
* @return {Promise<Object>}
|
|
9
|
+
*/
|
|
10
|
+
const pullLanguages = async (api, options) => {
|
|
11
|
+
const { space } = options
|
|
12
|
+
|
|
13
|
+
try {
|
|
14
|
+
const options = await api.getSpaceOptions()
|
|
15
|
+
const languages = {
|
|
16
|
+
default_lang_name: options.default_lang_name,
|
|
17
|
+
languages: options.languages
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
const file = `languages.${space}.json`
|
|
21
|
+
const data = JSON.stringify(languages, null, 2)
|
|
22
|
+
|
|
23
|
+
console.log(`${chalk.green('✓')} We've saved your languages in the file: ${file}`)
|
|
24
|
+
|
|
25
|
+
fs.writeFile(`./${file}`, data, (err) => {
|
|
26
|
+
if (err) {
|
|
27
|
+
Promise.reject(err)
|
|
28
|
+
return
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
Promise.resolve(file)
|
|
32
|
+
})
|
|
33
|
+
} catch (e) {
|
|
34
|
+
console.error(`${chalk.red('X')} An error ocurred in pull-languages task when load components data`)
|
|
35
|
+
return Promise.reject(new Error(e))
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
module.exports = pullLanguages
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const chalk = require('chalk')
|
|
2
|
-
const
|
|
2
|
+
const UUID = require('simple-uuid')
|
|
3
|
+
const api = require('../../utils/api')
|
|
3
4
|
|
|
4
5
|
class SyncDatasources {
|
|
5
6
|
/**
|
|
@@ -11,9 +12,7 @@ class SyncDatasources {
|
|
|
11
12
|
this.sourceSpaceId = options.sourceSpaceId
|
|
12
13
|
this.targetSpaceId = options.targetSpaceId
|
|
13
14
|
this.oauthToken = options.oauthToken
|
|
14
|
-
this.client =
|
|
15
|
-
oauthToken: options.oauthToken
|
|
16
|
-
})
|
|
15
|
+
this.client = api.getClient()
|
|
17
16
|
}
|
|
18
17
|
|
|
19
18
|
async sync () {
|
|
@@ -41,9 +40,10 @@ class SyncDatasources {
|
|
|
41
40
|
await this.updateDatasources()
|
|
42
41
|
}
|
|
43
42
|
|
|
44
|
-
async getDatasourceEntries (spaceId, datasourceId) {
|
|
43
|
+
async getDatasourceEntries (spaceId, datasourceId, dimensionId = null) {
|
|
44
|
+
const dimensionQuery = dimensionId ? `&dimension=${dimensionId}` : ''
|
|
45
45
|
try {
|
|
46
|
-
const entriesFirstPage = await this.client.get(`spaces/${spaceId}/datasource_entries/?datasource_id=${datasourceId}`)
|
|
46
|
+
const entriesFirstPage = await this.client.get(`spaces/${spaceId}/datasource_entries/?datasource_id=${datasourceId}${dimensionQuery}`)
|
|
47
47
|
const entriesRequets = []
|
|
48
48
|
for (let i = 2; i <= Math.ceil(entriesFirstPage.total / 25); i++) {
|
|
49
49
|
entriesRequets.push(this.client.get(`spaces/${spaceId}/datasource_entries/?datasource_id=${datasourceId}`, { page: i }))
|
|
@@ -88,9 +88,9 @@ class SyncDatasources {
|
|
|
88
88
|
}
|
|
89
89
|
}
|
|
90
90
|
|
|
91
|
-
async syncDatasourceEntries (
|
|
91
|
+
async syncDatasourceEntries (datasourceId, targetId) {
|
|
92
92
|
try {
|
|
93
|
-
const sourceEntries = await this.getDatasourceEntries(this.sourceSpaceId,
|
|
93
|
+
const sourceEntries = await this.getDatasourceEntries(this.sourceSpaceId, datasourceId)
|
|
94
94
|
const targetEntries = await this.getDatasourceEntries(this.targetSpaceId, targetId)
|
|
95
95
|
const updateEntries = targetEntries.filter(e => sourceEntries.map(se => se.name).includes(e.name))
|
|
96
96
|
const addEntries = sourceEntries.filter(e => !targetEntries.map(te => te.name).includes(e.name))
|
|
@@ -126,17 +126,31 @@ class SyncDatasources {
|
|
|
126
126
|
|
|
127
127
|
for (let i = 0; i < datasourcesToAdd.length; i++) {
|
|
128
128
|
try {
|
|
129
|
+
console.log(` ${chalk.green('-')} Creating datasource ${datasourcesToAdd[i].name} (${datasourcesToAdd[i].slug})`)
|
|
129
130
|
/* Create the datasource */
|
|
130
131
|
const newDatasource = await this.client.post(`spaces/${this.targetSpaceId}/datasources`, {
|
|
131
132
|
name: datasourcesToAdd[i].name,
|
|
132
133
|
slug: datasourcesToAdd[i].slug
|
|
133
134
|
})
|
|
134
135
|
|
|
135
|
-
|
|
136
|
-
|
|
136
|
+
if (datasourcesToAdd[i].dimensions.length) {
|
|
137
|
+
console.log(
|
|
138
|
+
` ${chalk.blue('-')} Creating dimensions...`
|
|
139
|
+
)
|
|
140
|
+
const { data } = await this.createDatasourcesDimensions(datasourcesToAdd[i].dimensions, newDatasource.data.datasource)
|
|
141
|
+
await this.syncDatasourceEntries(datasourcesToAdd[i].id, newDatasource.data.datasource.id)
|
|
142
|
+
console.log(
|
|
143
|
+
` ${chalk.blue('-')} Sync dimensions values...`
|
|
144
|
+
)
|
|
145
|
+
await this.syncDatasourceDimensionsValues(datasourcesToAdd[i], data.datasource)
|
|
146
|
+
console.log(` ${chalk.green('✓')} Created datasource ${datasourcesToAdd[i].name}`)
|
|
147
|
+
} else {
|
|
148
|
+
await this.syncDatasourceEntries(datasourcesToAdd[i].id, newDatasource.data.datasource.id)
|
|
149
|
+
console.log(` ${chalk.green('✓')} Created datasource ${datasourcesToAdd[i].name}`)
|
|
150
|
+
}
|
|
137
151
|
} catch (err) {
|
|
138
152
|
console.error(
|
|
139
|
-
`${chalk.red('X')} Datasource ${datasourcesToAdd[i].name} creation failed: ${err.message}`
|
|
153
|
+
`${chalk.red('X')} Datasource ${datasourcesToAdd[i].name} creation failed: ${err.response.data.error || err.message}`
|
|
140
154
|
)
|
|
141
155
|
}
|
|
142
156
|
}
|
|
@@ -154,13 +168,35 @@ class SyncDatasources {
|
|
|
154
168
|
try {
|
|
155
169
|
/* Update the datasource */
|
|
156
170
|
const sourceDatasource = this.sourceDatasources.find(d => d.slug === datasourcesToUpdate[i].slug)
|
|
171
|
+
|
|
157
172
|
await this.client.put(`spaces/${this.targetSpaceId}/datasources/${datasourcesToUpdate[i].id}`, {
|
|
158
173
|
name: sourceDatasource.name,
|
|
159
174
|
slug: sourceDatasource.slug
|
|
160
175
|
})
|
|
161
176
|
|
|
162
|
-
|
|
163
|
-
|
|
177
|
+
if (datasourcesToUpdate[i].dimensions.length) {
|
|
178
|
+
console.log(` ${chalk.blue('-')} Updating datasources dimensions ${datasourcesToUpdate[i].name}...`)
|
|
179
|
+
const sourceDimensionsNames = sourceDatasource.dimensions.map((dimension) => dimension.name)
|
|
180
|
+
const targetDimensionsNames = datasourcesToUpdate[i].dimensions.map((dimension) => dimension.name)
|
|
181
|
+
const intersection = sourceDimensionsNames.filter(item => !targetDimensionsNames.includes(item))
|
|
182
|
+
let datasourceToSyncDimensionsValues = datasourcesToUpdate[i]
|
|
183
|
+
|
|
184
|
+
if (intersection) {
|
|
185
|
+
const dimensionsToCreate = sourceDatasource.dimensions.filter((dimension) => {
|
|
186
|
+
if (intersection.includes(dimension.name)) return dimension
|
|
187
|
+
})
|
|
188
|
+
const { data } = await this.createDatasourcesDimensions(dimensionsToCreate, datasourcesToUpdate[i], true)
|
|
189
|
+
datasourceToSyncDimensionsValues = data.datasource
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
await this.syncDatasourceEntries(sourceDatasource.id, datasourcesToUpdate[i].id)
|
|
193
|
+
|
|
194
|
+
await this.syncDatasourceDimensionsValues(sourceDatasource, datasourceToSyncDimensionsValues)
|
|
195
|
+
console.log(`${chalk.green('✓')} Updated datasource ${datasourcesToUpdate[i].name}`)
|
|
196
|
+
} else {
|
|
197
|
+
await this.syncDatasourceEntries(sourceDatasource.id, datasourcesToUpdate[i].id)
|
|
198
|
+
console.log(`${chalk.green('✓')} Updated datasource ${datasourcesToUpdate[i].name}`)
|
|
199
|
+
}
|
|
164
200
|
} catch (err) {
|
|
165
201
|
console.error(
|
|
166
202
|
`${chalk.red('X')} Datasource ${datasourcesToUpdate[i].name} update failed: ${err.message}`
|
|
@@ -168,6 +204,102 @@ class SyncDatasources {
|
|
|
168
204
|
}
|
|
169
205
|
}
|
|
170
206
|
}
|
|
207
|
+
|
|
208
|
+
async createDatasourcesDimensions (dimensions, datasource, isToUpdate = false) {
|
|
209
|
+
const newDimensions = dimensions.map((dimension) => {
|
|
210
|
+
return {
|
|
211
|
+
name: dimension.name,
|
|
212
|
+
entry_value: dimension.entry_value,
|
|
213
|
+
datasource_id: datasource.id,
|
|
214
|
+
_uid: UUID()
|
|
215
|
+
}
|
|
216
|
+
})
|
|
217
|
+
|
|
218
|
+
let payload = null
|
|
219
|
+
|
|
220
|
+
if (isToUpdate) {
|
|
221
|
+
payload = {
|
|
222
|
+
dimensions: [...datasource.dimensions, ...newDimensions],
|
|
223
|
+
dimensions_attributes: [...datasource.dimensions, ...newDimensions]
|
|
224
|
+
}
|
|
225
|
+
} else {
|
|
226
|
+
payload = {
|
|
227
|
+
dimensions: newDimensions,
|
|
228
|
+
dimensions_attributes: newDimensions
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
try {
|
|
233
|
+
return await this.client.put(`spaces/${this.targetSpaceId}/datasources/${datasource.id}`, {
|
|
234
|
+
...datasource,
|
|
235
|
+
...payload
|
|
236
|
+
})
|
|
237
|
+
} catch (error) {
|
|
238
|
+
console.error(error)
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
|
|
242
|
+
async syncDatasourceDimensionsValues (sourceDatasource, targetDatasource) {
|
|
243
|
+
const sourceEntriesPromisses = []
|
|
244
|
+
const targetEmptyEntriesPromisses = []
|
|
245
|
+
try {
|
|
246
|
+
for (let index = 0; index < sourceDatasource.dimensions.length; index++) {
|
|
247
|
+
const targetDimensionId = targetDatasource.dimensions[index].id
|
|
248
|
+
sourceEntriesPromisses.push(...await this.getDatasourceEntries(this.sourceSpaceId, sourceDatasource.id, sourceDatasource.dimensions[index].id))
|
|
249
|
+
targetEmptyEntriesPromisses.push(
|
|
250
|
+
...await this.getDatasourceEntries(this.targetSpaceId, targetDatasource.id, targetDimensionId).then((res) => {
|
|
251
|
+
return res.map((entry) => {
|
|
252
|
+
return {
|
|
253
|
+
...entry,
|
|
254
|
+
target_dimension_id: targetDimensionId
|
|
255
|
+
}
|
|
256
|
+
})
|
|
257
|
+
})
|
|
258
|
+
)
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
await Promise.all(sourceEntriesPromisses)
|
|
262
|
+
await Promise.all(targetEmptyEntriesPromisses)
|
|
263
|
+
|
|
264
|
+
const targetEntriesPromisses = []
|
|
265
|
+
|
|
266
|
+
while (sourceEntriesPromisses.length !== 0) {
|
|
267
|
+
const currentSourceEntry = sourceEntriesPromisses[0]
|
|
268
|
+
const targetEntryIndex = targetEmptyEntriesPromisses.findIndex((tEntry) => tEntry.name === currentSourceEntry.name)
|
|
269
|
+
const currentTargetEntry = targetEmptyEntriesPromisses[targetEntryIndex]
|
|
270
|
+
const valuesAreEqual = currentTargetEntry.dimension_value === currentSourceEntry.dimension_value
|
|
271
|
+
|
|
272
|
+
if (valuesAreEqual) {
|
|
273
|
+
sourceEntriesPromisses.shift()
|
|
274
|
+
targetEmptyEntriesPromisses.splice(targetEntryIndex, 1)
|
|
275
|
+
} else {
|
|
276
|
+
const payload = {
|
|
277
|
+
...currentTargetEntry,
|
|
278
|
+
dimension_value: currentSourceEntry.dimension_value
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
targetEntriesPromisses.push(await this.syncDimensionEntryValues(currentTargetEntry.target_dimension_id, currentTargetEntry.id, payload))
|
|
282
|
+
sourceEntriesPromisses.shift()
|
|
283
|
+
targetEmptyEntriesPromisses.splice(targetEntryIndex, 1)
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
await Promise.all(targetEntriesPromisses)
|
|
288
|
+
} catch (error) {
|
|
289
|
+
console.error(` ${chalk.red('X')} Sync dimensions values failed: ${error.response.data.error || error.message || error}`)
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
async syncDimensionEntryValues (dimensionId = null, datasourceEntryId = null, payload = null) {
|
|
294
|
+
try {
|
|
295
|
+
await this.client.put(`spaces/${this.targetSpaceId}/datasource_entries/${datasourceEntryId}`, {
|
|
296
|
+
datasource_entry: payload,
|
|
297
|
+
dimension_id: dimensionId
|
|
298
|
+
})
|
|
299
|
+
} catch (error) {
|
|
300
|
+
console.error(` ${chalk.red('X')} Sync entry error ${payload.name} sync failed: ${error.response.data.error || error.message}`)
|
|
301
|
+
}
|
|
302
|
+
}
|
|
171
303
|
}
|
|
172
304
|
|
|
173
305
|
module.exports = SyncDatasources
|
package/src/tasks/sync.js
CHANGED
|
@@ -43,29 +43,29 @@ const SyncSpaces = {
|
|
|
43
43
|
|
|
44
44
|
async syncStories () {
|
|
45
45
|
console.log(chalk.green('✓') + ' Syncing stories...')
|
|
46
|
-
|
|
46
|
+
const targetFolders = await this.client.getAll(`spaces/${this.targetSpaceId}/stories`, {
|
|
47
47
|
folder_only: 1,
|
|
48
48
|
sort_by: 'slug:asc'
|
|
49
49
|
})
|
|
50
50
|
|
|
51
|
-
|
|
51
|
+
const folderMapping = {}
|
|
52
52
|
|
|
53
53
|
for (let i = 0; i < targetFolders.length; i++) {
|
|
54
54
|
var folder = targetFolders[i]
|
|
55
55
|
folderMapping[folder.full_slug] = folder.id
|
|
56
56
|
}
|
|
57
57
|
|
|
58
|
-
|
|
58
|
+
const all = await this.client.getAll(`spaces/${this.sourceSpaceId}/stories`, {
|
|
59
59
|
story_only: 1
|
|
60
60
|
})
|
|
61
61
|
|
|
62
62
|
for (let i = 0; i < all.length; i++) {
|
|
63
63
|
console.log(chalk.green('✓') + ' Starting update ' + all[i].full_slug)
|
|
64
64
|
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
65
|
+
const { data } = await this.client.get('spaces/' + this.sourceSpaceId + '/stories/' + all[i].id)
|
|
66
|
+
const sourceStory = data.story
|
|
67
|
+
const slugs = sourceStory.full_slug.split('/')
|
|
68
|
+
let folderId = 0
|
|
69
69
|
|
|
70
70
|
if (slugs.length > 1) {
|
|
71
71
|
slugs.pop()
|
|
@@ -87,7 +87,7 @@ const SyncSpaces = {
|
|
|
87
87
|
const payload = {
|
|
88
88
|
story: storyData,
|
|
89
89
|
force_update: '1',
|
|
90
|
-
...(sourceStory.published ? {
|
|
90
|
+
...(sourceStory.published ? { publish: 1 } : {})
|
|
91
91
|
}
|
|
92
92
|
|
|
93
93
|
let createdStory = null
|
package/src/utils/api.js
CHANGED
|
@@ -156,6 +156,15 @@ module.exports = {
|
|
|
156
156
|
.catch(err => Promise.reject(err))
|
|
157
157
|
},
|
|
158
158
|
|
|
159
|
+
getSpaceOptions () {
|
|
160
|
+
const client = this.getClient()
|
|
161
|
+
|
|
162
|
+
return client
|
|
163
|
+
.get(this.getPath(''))
|
|
164
|
+
.then((data) => data.data.space.options || {})
|
|
165
|
+
.catch((err) => Promise.reject(err))
|
|
166
|
+
},
|
|
167
|
+
|
|
159
168
|
getComponents () {
|
|
160
169
|
const client = this.getClient()
|
|
161
170
|
|
package/tests/constants.js
CHANGED
|
@@ -229,11 +229,31 @@ const FAKE_SPACES = () => [
|
|
|
229
229
|
}
|
|
230
230
|
]
|
|
231
231
|
|
|
232
|
+
const FAKE_SPACE_OPTIONS = () => ({
|
|
233
|
+
languages: [
|
|
234
|
+
{
|
|
235
|
+
code: 'pt',
|
|
236
|
+
name: 'Português'
|
|
237
|
+
},
|
|
238
|
+
{
|
|
239
|
+
code: 'nl-be',
|
|
240
|
+
name: 'Dutch (Belgian)'
|
|
241
|
+
}
|
|
242
|
+
],
|
|
243
|
+
hosted_backup: false,
|
|
244
|
+
onboarding_step: '3',
|
|
245
|
+
default_lang_name: 'English',
|
|
246
|
+
rev_share_enabled: true,
|
|
247
|
+
required_assest_fields: [],
|
|
248
|
+
use_translated_stories: false
|
|
249
|
+
})
|
|
250
|
+
|
|
232
251
|
module.exports = {
|
|
233
252
|
EMAIL_TEST,
|
|
234
253
|
TOKEN_TEST,
|
|
235
254
|
FAKE_STORIES,
|
|
236
255
|
PASSWORD_TEST,
|
|
237
256
|
FAKE_COMPONENTS,
|
|
238
|
-
FAKE_SPACES
|
|
257
|
+
FAKE_SPACES,
|
|
258
|
+
FAKE_SPACE_OPTIONS
|
|
239
259
|
}
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
const fs = require('fs')
|
|
2
|
+
const pullLanguages = require('../../src/tasks/pull-languages')
|
|
3
|
+
const { FAKE_SPACE_OPTIONS } = require('../constants')
|
|
4
|
+
|
|
5
|
+
jest.mock('fs')
|
|
6
|
+
|
|
7
|
+
describe('testing pullLanguages', () => {
|
|
8
|
+
afterEach(() => {
|
|
9
|
+
jest.clearAllMocks()
|
|
10
|
+
})
|
|
11
|
+
|
|
12
|
+
it('api.getSpaceOptions() should be called once time', () => {
|
|
13
|
+
const api = {
|
|
14
|
+
getSpaceOptions: jest.fn(() => Promise.resolve(FAKE_SPACE_OPTIONS()))
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
return pullLanguages(api, {})
|
|
18
|
+
.then(() => {
|
|
19
|
+
expect(api.getSpaceOptions.mock.calls.length).toBe(1)
|
|
20
|
+
})
|
|
21
|
+
})
|
|
22
|
+
|
|
23
|
+
it('api.getSpaceOptions() should be call fs.writeFile correctly', async () => {
|
|
24
|
+
const SPACE = 12345
|
|
25
|
+
const BODY = FAKE_SPACE_OPTIONS()
|
|
26
|
+
|
|
27
|
+
const api = {
|
|
28
|
+
getSpaceOptions () {
|
|
29
|
+
return Promise.resolve(BODY)
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
const options = {
|
|
34
|
+
space: SPACE
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const expectFileName = `languages.${SPACE}.json`
|
|
38
|
+
const expectData = {
|
|
39
|
+
default_lang_name: BODY.default_lang_name,
|
|
40
|
+
languages: BODY.languages
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
return pullLanguages(api, options)
|
|
44
|
+
.then(_ => {
|
|
45
|
+
const [path, data] = fs.writeFile.mock.calls[0]
|
|
46
|
+
|
|
47
|
+
expect(fs.writeFile.mock.calls.length).toBe(1)
|
|
48
|
+
expect(path).toBe(`./${expectFileName}`)
|
|
49
|
+
expect(JSON.parse(data)).toEqual(expectData)
|
|
50
|
+
})
|
|
51
|
+
})
|
|
52
|
+
|
|
53
|
+
it('api.getSpaceOptions() when a error ocurred, catch the body response', async () => {
|
|
54
|
+
const _api = {
|
|
55
|
+
getSpaceOptions (_, fn) {
|
|
56
|
+
return Promise.reject(new Error('Failed'))
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
await expect(pullLanguages(_api, {})).rejects.toThrow('Error: Failed')
|
|
61
|
+
})
|
|
62
|
+
})
|