forked from github/docs
-
Notifications
You must be signed in to change notification settings - Fork 0
/
msft-tokens.js
90 lines (75 loc) · 2.43 KB
/
msft-tokens.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
import walk from 'walk-sync'
import { Tokenizer } from 'liquidjs'
import { readFileSync } from 'fs'
import gitDiff from 'git-diff'
import _ from 'lodash'
function getGitDiff(a, b) {
return gitDiff(a, b, { flags: '--text --ignore-all-space' })
}
function getMissingLines(diff) {
return diff
.split('\n')
.filter((line) => line.startsWith('-'))
.map((line) => line.replace('-', ''))
}
function getExceedingLines(diff) {
return diff
.split('\n')
.filter((line) => line.startsWith('+'))
.map((line) => line.replace('+', ''))
}
export function languageFiles(language, folder = 'content') {
const englishFiles = walk(folder, { directories: false })
const languageFiles = walk(`${language.dir}/${folder}`, { directories: false })
return [
_.intersection(englishFiles, languageFiles).map((file) => `${folder}/${file}`),
_.difference(languageFiles, englishFiles).map((file) => `${language.dir}/${folder}/${file}`), // returns languageFiles not included in englishFiles
]
}
export function compareLiquidTags(file, language) {
const translation = `${language.dir}/${file}`
const sourceTokens = getTokensFromFile(file).rejectType('html')
const otherFileTokens = getTokensFromFile(translation).rejectType('html')
const diff = sourceTokens.diff(otherFileTokens)
return {
file,
translation,
diff,
}
}
function getTokens(contents) {
const tokenizer = new Tokenizer(contents)
return new Tokens(...tokenizer.readTopLevelTokens())
}
export function getTokensFromFile(filePath) {
const contents = readFileSync(filePath, 'utf8')
try {
return new Tokens(...getTokens(contents))
} catch (e) {
const error = new Error(`Error parsing ${filePath}: ${e.message}`)
error.filePath = filePath
throw error
}
}
export class Tokens extends Array {
rejectType(tagType) {
return this.filter(
(token) => token.constructor.name.toUpperCase() !== `${tagType}Token`.toUpperCase()
)
}
onlyText() {
return this.map((token) => token.getText())
}
diff(otherTokens) {
const a = this.onlyText().sort()
const b = otherTokens.onlyText().sort()
const diff = getGitDiff(a.join('\n'), b.join('\n'))
if (!diff) {
return { count: 0, missing: [], exceeding: [], output: '' }
}
const missing = getMissingLines(diff)
const exceeding = getExceedingLines(diff)
const count = exceeding.length + missing.length
return { count, missing, exceeding, output: diff }
}
}