sysinfo/scripts/lib.js

112 řádky
3.0 KiB
JavaScript
Executable File

import yaml from 'js-yaml'
import fs from 'fs'
import jsonata from 'jsonata'
import fetch from 'node-fetch'
import * as dotenv from 'dotenv'
dotenv.config()
const SOURCE_FILE = process.env.GWEICZ_SYSINFO_SPEC || './spec/services.yaml'
const outputFn = 'build/spec.json'
function defaultOptions(conf) {
const opts = {}
if (conf.auth && conf.auth.type === 'basic') {
opts.headers = {
Authorization: `Basic ${Buffer.from(process.env[conf.auth.env]).toString('base64')}`
}
}
if (conf.auth && conf.auth.type === 'token') {
opts.headers = {
Authorization: `Token ${process.env[conf.auth.env]}`
}
}
return opts
}
async function ghRequest (url, conf, all) {
const req = await fetch('https://api.github.com/'+url, {
headers: {
Authorization: `Token ${process.env.GWEICZ_GH_TOKEN}`
}
})
const resp = await req.json()
return resp
}
const strategies = {
async default (conf, all) {
const options = conf.options || {}
const req = await fetch(conf.url, { ...options, ...defaultOptions(conf) })
let resp;
try {
resp = await req.json()
} catch (e) {
console.error(`Error: Failed!!!: ` + conf.url)
resp = {}
}
return jsonata(conf.query).evaluate(resp)
},
async github (conf, all) {
const resp = await ghRequest('repos/@@/releases/latest'.replace(/@@/, all.repo), conf, all)
const prefix = typeof(conf.prefix) === 'string' ? conf.prefix : 'v'
const prop = conf.prop || 'tag_name'
return jsonata(`$match(${prop},/^${prefix}(.+)/)[0].groups[0]`).evaluate(resp)
},
async github_tags (conf, all) {
const resp = await ghRequest('repos/@@/tags'.replace(/@@/, all.repo), conf, all)
for (const t of resp) {
let match = t.name.match(/^v(.+)/)
if (match) {
return match[1]
}
}
},
async html (conf, all) {
const req = await fetch(conf.url)
const resp = await req.text()
return resp.match(conf.query)[1]
},
async none () {}
}
async function getVersions (config, all) {
const local = await strategies[config.from.strategy ? config.from.strategy : 'default'](config.from, all)
const latest = await strategies[config.to.strategy ? config.to.strategy : 'default'](config.to, all)
return { local, latest }
}
export default async function build (src = SOURCE_FILE) {
console.log(`Source: ${src}`)
const spec = yaml.load(fs.readFileSync(src))
for (const item of spec.servers) {
console.error(`Fetching info for host: ${item.host}`)
const resp = await fetch(`https://${item.host}/sysinfo`)
const json = await resp.json()
item.uptime = json.uptime
item.system = json.system
}
for (const item of spec.services) {
item.url = item.host ? `https://${item.host}` : item.url
if (item.version_conf) {
item.versions = await getVersions(item.version_conf, item)
}
//delete item.version_conf
}
spec.time = new Date
fs.writeFileSync(outputFn, JSON.stringify(spec, null, 2))
console.log(`saved: ${outputFn}`)
console.log('build done')
return spec
}