Skip to content

fix(fence_enhance): cursor style of CodeMirror-scroll should not be… #100

fix(fence_enhance): cursor style of CodeMirror-scroll should not be…

fix(fence_enhance): cursor style of CodeMirror-scroll should not be… #100

name: Check Setting Schemas On Commit
on:
push:
paths:
- 'plugin/global/settings/**'
- 'plugin/preferences/**'
jobs:
check_schemas:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Setup Node.js
uses: actions/setup-node@v2
- name: Check Schemas
uses: actions/github-script@v6
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
script: |
const hasNestedProperty = (obj, key) => {
if (key == null) {
return false
}
if (obj.hasOwnProperty(key)) {
return true
}
return key.split(".").every(k => {
if (obj && typeof obj === "object" && obj.hasOwnProperty(k)) {
obj = obj[k]
return true
}
return false
})
}
const loadSettings = async () => {
const fs = require("fs").promises
const toml = require("./plugin/global/core/lib/smol-toml.js")
const base = await fs.readFile("./plugin/global/settings/settings.default.toml", "utf-8")
const custom = await fs.readFile("./plugin/global/settings/custom_plugin.default.toml", "utf-8")
return { ...toml.parse(base), ...toml.parse(custom) }
}
const loadSchemas = () => {
const schemas = require("./plugin/preferences/schemas.js")
Object.values(schemas).forEach(boxes => {
boxes.forEach(box => box.fields = box.fields.filter(ctl => ctl.key && ctl.type !== "static" && ctl.type !== "action"))
})
return schemas
}
const checkExtraKeys = (schemas, settings) => {
Object.entries(schemas).forEach(([fixedName, boxes]) => {
const setting = settings[fixedName]
boxes.forEach(box => {
box.fields.forEach(ctl => {
if (!hasNestedProperty(setting, ctl.key)) {
throw new TypeError(`settings ${fixedName} has no such Key: ${ctl.key}`)
}
})
})
})
}
const checkMessingKeys = (schemas, settings) => {
const isIgnored = (fixedName, key) => (
fixedName === "abc" && key.startsWith("VISUAL_OPTIONS")
|| (fixedName === "markdownLint") && key.startsWith("rule_config")
)
const flattenKeys = (obj, prefix = [], result = new Set()) => {
for (const [key, val] of Object.entries(obj)) {
if (Array.isArray(val)) {
val.forEach(k => flattenKeys(val, [...prefix, key], result))
} else if (typeof val === "object") {
flattenKeys(val, [...prefix, key], result)
} else {
const pre = prefix.length === 0 ? "" : prefix.join(".") + "."
const r = (pre + key).replace(/\.\d+/g, "")
result.add(r)
}
}
return result
}
Object.entries(settings).forEach(([fixedName, setting]) => {
const boxes = schemas[fixedName]
if (!boxes) {
throw new TypeError(`schemas has no such schema: ${fixedName}`)
}
const keysInBoxes = boxes.flatMap(box => {
return box.fields.flatMap(field => {
return field.type !== "table"
? field.key
: field.nestedBoxes.flatMap(b => b.fields.flatMap(f => `${field.key}.${f.key}`))
})
})
const keysObject = Object.fromEntries(keysInBoxes.map(e => [e.replace(/\.\d+/g, ""), undefined]))
const newKeys = flattenKeys(setting)
newKeys.forEach(key => {
const exist = hasNestedProperty(keysObject, key)
if (exist || isIgnored(fixedName, key)) return
throw new TypeError(`schemas ${fixedName} has no such Key: ${key}`)
})
})
}
(async () => {
const schemas = loadSchemas()
const settings = await loadSettings()
checkExtraKeys(schemas, settings)
checkMessingKeys(schemas, settings)
console.log("schemas test passed")
})()
- run: |
echo "./plugin/preferences/schemas.js has checked"