import { parseXml, XmlDocument, XmlElement, XmlText } from "@rgrove/parse-xml"; export type versionNotes = { title: string; date: Date | string; link: string; html: string; } export default class Updater { public archiveURL: string; public feedType: string; constructor(archiveURL: string = "/", feedType: string = "atom") { this.archiveURL = archiveURL; this.feedType = feedType; } private async getRawArchive(): Promise { const res = await fetch(`http://cors.emaker.limited/?url=${this.archiveURL}.${this.feedType}`, { // "mode": "cors" }); const text = await res.text(); return text; } // atom feeds private atomGetVersionDetails(entry: XmlElement): versionNotes { let outEntry: versionNotes = {title: "", date: new Date, link: "", html: ""}; entry.children.forEach((elm) => { let element = elm as XmlElement; if (element.name == "title") { outEntry.title = (element.children[0] as XmlText).text; } else if (element.name == "date") { outEntry.date = new Date((element.children[0] as XmlText).text); } else if (element.name == "link") { outEntry.link = element.attributes["href"]; } else if (element.name == "content") { outEntry.html = (element.children[0] as XmlText).text; } }) return outEntry; } private async atomGetArchive(): Promise { const rawArchive: string = await this.getRawArchive(); const releaseNotes: XmlDocument = parseXml(rawArchive); const output: versionNotes[] = []; // console.dir(releaseNotes) (releaseNotes.children[0] as XmlElement).children.forEach((elm) => { if (elm.type == "element") { const element = elm as XmlElement; if (element.name == "entry") { output.push(this.atomGetVersionDetails(element)) } } }); return output; } // rss feeds private rssGetVersionDetails(entry: XmlElement): versionNotes { let outEntry: versionNotes = {title: "", date: new Date, link: "", html: ""}; entry.children.forEach((elm) => { let element = elm as XmlElement; if (element.name == "title") { outEntry.title = (element.children[0] as XmlText).text; } else if (element.name == "pubDate") { outEntry.date = (element.children[0] as XmlText).text; } else if (element.name == "link") { outEntry.link = (element.children[0] as XmlText).text; } else if (element.name == "content") { outEntry.html = (element.children[0] as XmlText).text; } }) return outEntry; } private async rssGetArchive(): Promise { const rawArchive: string = await this.getRawArchive(); const releaseNotes: XmlDocument = parseXml(rawArchive); const output: versionNotes[] = []; ((releaseNotes.children[0] as XmlElement).children[1] as XmlElement).children.forEach((elm) => { if (elm.type == "element") { const element = elm as XmlElement; if (element.name == "item") { output.push(this.atomGetVersionDetails(element)) } } }) return output; } public async getArchive(): Promise { if (this.feedType == "atom") { return this.atomGetArchive() } else if (this.feedType == "rss"){ return this.rssGetArchive() } } }