Skip to content

Instantly share code, notes, and snippets.

@jinjor
Last active November 14, 2018 20:09
Show Gist options
  • Save jinjor/fb9eefa2c0beb62da6839f1da3d0d6a0 to your computer and use it in GitHub Desktop.
Save jinjor/fb9eefa2c0beb62da6839f1da3d0d6a0 to your computer and use it in GitHub Desktop.
const fs = require("fs");
const fetch = require("node-fetch");
const readline = require("readline");
run().catch(err => {
console.error(err.message);
process.exit(1);
});
async function run() {
let targetPackage = process.argv[2];
let targetVersion = process.argv[3];
if (targetPackage) {
await apply(targetPackage, targetVersion);
} else {
await show();
}
}
async function show() {
let elmJson = getElmJson();
const directDeps = elmJson.dependencies.direct;
for (let packageName in directDeps) {
directDeps[packageName] = parseVersion(directDeps[packageName]);
}
const indirectDeps = elmJson.dependencies.indirect;
for (let packageName in indirectDeps) {
indirectDeps[packageName] = parseVersion(indirectDeps[packageName]);
}
const allPackages = await getAllPackages();
const outdated = getOutDated(allPackages, directDeps);
for (let packageName in outdated) {
const info = outdated[packageName];
console.log(
packageName,
info.current.raw,
info.compatibleLatest.raw,
info.latest.raw
);
}
}
async function apply(targetPackage, targetVersion) {
targetVersion = parseVersion(targetVersion);
throw new Error("not implemented");
}
function getOutDated(allPackages, directDeps) {
const outdated = {};
for (let packageName in directDeps) {
const currentVersion = directDeps[packageName];
const availableVersions = allPackages[packageName].map(parseVersion);
let latest = null;
let compatibleLatest = null;
for (let availableVer of availableVersions) {
const d = diff(currentVersion, availableVer);
latest = availableVer;
if (!d.major) {
compatibleLatest = availableVer;
}
}
if (latest.raw !== currentVersion.raw) {
outdated[packageName] = {
current: currentVersion,
compatibleLatest,
latest
};
}
}
return outdated;
}
// version
function parseVersionRange(raw) {
const left = parseVersion(raw.split(" <= v")[0]);
const right = parseVersion(raw.split("v < ")[1]);
return { left, right, raw };
}
function parseVersion(raw) {
const [major, minor, patch] = raw.split(".").map(s => parseInt(s));
return { major, minor, patch, raw };
}
function diff(oldVer, newVer) {
return {
major: newVer.major - oldVer.major,
minor: newVer.minor - oldVer.minor,
patch: newVer.patch - oldVer.patch
};
}
// get info
function getElmJson() {
let elmJson = fs.readFileSync("elm.json", { encoding: "utf-8" });
if (!elmJson) {
throw new Error("elm.json not found");
}
try {
elmJson = JSON.parse(elmJson);
} catch (e) {
throw new Error("Cannot parse elm.json");
}
return elmJson;
}
async function getElmJsonOfPackage(package, version) {
return fetchJson(
`https://raw.githubusercontent.com/${package}/${version}/elm.json`
);
}
async function getAllPackages() {
return fetchJson(
"https://package.elm-lang.org/all-packages?elm-package-version=0.19"
);
}
async function fetchJson(url) {
const res = await fetch(url);
return res.json();
}
// cli util
function ask(question) {
return new Promise((resolve, reject) => {
console.log(question);
const rl = readline.createInterface({
input: process.stdin,
output: process.stdout
});
rl.on("line", line => {
rl.close();
resolve(line);
});
});
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment