1 | import { getIfUpdate, UpdatedObject } from "@xmcl/net";
|
2 | import * as parser from "fast-html-parser";
|
3 | import { ForgeInstaller } from "./index";
|
4 |
|
5 | export namespace ForgeWebPage {
|
6 |
|
7 | export interface Download {
|
8 | md5: string;
|
9 | sha1: string;
|
10 | path: string;
|
11 | }
|
12 |
|
13 | |
14 |
|
15 |
|
16 | export function parse(content: string): ForgeWebPage {
|
17 | const dom = parser.parse(content);
|
18 | const selected = dom.querySelector(".elem-active");
|
19 | const mcversion = selected.text;
|
20 | return {
|
21 | timestamp: "",
|
22 | mcversion,
|
23 | versions: dom.querySelector(".download-list").querySelector("tbody").querySelectorAll("tr")
|
24 | .map((e) => {
|
25 | const links = e.querySelector(".download-links").childNodes
|
26 | .filter((elem) => elem.tagName === "li")
|
27 | .map((elem) => {
|
28 | elem = elem.removeWhitespace();
|
29 | const tt = elem.querySelector(".info-tooltip");
|
30 | const url = tt.querySelector("a") || elem.querySelector("a");
|
31 | return {
|
32 | name: url.childNodes[1].rawText.trim(),
|
33 | md5: tt.childNodes[1].text.trim(),
|
34 | sha1: tt.lastChild.text.trim(),
|
35 | path: url.attributes.href,
|
36 | };
|
37 | });
|
38 | const downloadVersionElem = e.querySelector(".download-version");
|
39 | let version;
|
40 | let type: ForgeWebPage.Version["type"] = "common";
|
41 | const icon = downloadVersionElem.querySelector("i");
|
42 | if (icon) {
|
43 | if (icon.classNames.indexOf("promo-recommended") !== -1) {
|
44 | type = "recommended";
|
45 | } else if (icon.classNames.indexOf("promo-latest") !== -1) {
|
46 | type = "latest";
|
47 | } else if (icon.classNames.indexOf("fa-bug") !== -1) {
|
48 | type = "buggy";
|
49 | }
|
50 | version = downloadVersionElem.firstChild.text.trim();
|
51 | } else {
|
52 | version = downloadVersionElem.text.trim();
|
53 | }
|
54 | const installer = links.find((l) => l.name === "Installer");
|
55 | const universal = links.find((l) => l.name === "Universal");
|
56 |
|
57 | if (installer === undefined || universal === undefined) {
|
58 | throw new Error(`Cannot parse forge web since it missing installer and universal jar info.`);
|
59 | }
|
60 | const result = {
|
61 | version,
|
62 | "date": e.querySelector(".download-time").text.trim(),
|
63 | "changelog": links[0],
|
64 | installer,
|
65 | "installer-win": links.find((l) => l.name === "Installer-win"),
|
66 | "mdk": links.find((l) => l.name === "Mdk"),
|
67 | universal,
|
68 | "mcversion": mcversion,
|
69 | type,
|
70 | };
|
71 |
|
72 | return result;
|
73 | }),
|
74 | };
|
75 | }
|
76 |
|
77 | |
78 |
|
79 |
|
80 |
|
81 |
|
82 |
|
83 |
|
84 |
|
85 | export function getWebPage(): Promise<ForgeWebPage | undefined>;
|
86 | |
87 |
|
88 |
|
89 |
|
90 |
|
91 |
|
92 |
|
93 |
|
94 | export function getWebPage(option?: {
|
95 | mcversion?: string;
|
96 | }): Promise<ForgeWebPage | undefined>;
|
97 | |
98 |
|
99 |
|
100 |
|
101 |
|
102 |
|
103 |
|
104 |
|
105 | export function getWebPage(option?: {
|
106 | mcversion?: string;
|
107 | fallback?: ForgeWebPage;
|
108 | }): Promise<ForgeWebPage | undefined>;
|
109 | |
110 |
|
111 |
|
112 |
|
113 |
|
114 |
|
115 |
|
116 |
|
117 | export function getWebPage(option?: {
|
118 | mcversion?: string;
|
119 | fallback: ForgeWebPage;
|
120 | }): Promise<ForgeWebPage>;
|
121 |
|
122 | |
123 |
|
124 |
|
125 |
|
126 |
|
127 |
|
128 |
|
129 |
|
130 | export async function getWebPage(option: {
|
131 | mcversion?: string,
|
132 | fallback?: ForgeWebPage,
|
133 | } = {}): Promise<ForgeWebPage | undefined> {
|
134 | const mcversion = option.mcversion || "";
|
135 | const url = mcversion === "" ? `http://files.minecraftforge.net/maven/net/minecraftforge/forge/index.html` : `http://files.minecraftforge.net/maven/net/minecraftforge/forge/index_${mcversion}.html`;
|
136 | const page = await getIfUpdate(url, parse, option.fallback);
|
137 | return page;
|
138 | }
|
139 |
|
140 | |
141 |
|
142 |
|
143 | export interface Version extends ForgeInstaller.VersionMeta {
|
144 | |
145 |
|
146 |
|
147 | mcversion: string;
|
148 | |
149 |
|
150 |
|
151 | version: string;
|
152 | date: string;
|
153 | |
154 |
|
155 |
|
156 | changelog: ForgeWebPage.Download;
|
157 | installer: ForgeWebPage.Download;
|
158 | mdk?: ForgeWebPage.Download;
|
159 | universal: ForgeWebPage.Download;
|
160 | |
161 |
|
162 |
|
163 | type: "buggy" | "recommended" | "common" | "latest";
|
164 | }
|
165 |
|
166 | export namespace Version {
|
167 | export function to(webPageVersion: ForgeWebPage.Version): ForgeInstaller.VersionMeta {
|
168 | return {
|
169 | universal: webPageVersion.universal,
|
170 | installer: webPageVersion.installer,
|
171 | mcversion: webPageVersion.mcversion,
|
172 | version: webPageVersion.version,
|
173 | };
|
174 | }
|
175 | }
|
176 | }
|
177 |
|
178 | declare module "./index" {
|
179 | export namespace VersionMeta {
|
180 | export function from(webPageVersion: ForgeWebPage.Version): ForgeInstaller.VersionMeta;
|
181 | }
|
182 | }
|
183 |
|
184 | (ForgeInstaller as any).VersionMeta = (ForgeInstaller as any).VersionMeta || {};
|
185 | (ForgeInstaller as any).VersionMeta.from = ForgeWebPage.Version.to;
|
186 |
|
187 | export interface ForgeWebPage extends UpdatedObject {
|
188 | versions: ForgeWebPage.Version[];
|
189 | mcversion: string;
|
190 | }
|
191 |
|
192 |
|
193 |
|