本人是一個魔獸世界老玩家,因爲今年twitch的curse客戶端已國內不發正常使用了,致使如今更新插件每次要去網站上下載,而後在手動拖到魔獸插件的根目錄替換,很是麻煩並且容易搞錯。因此就萌生了本身實現一個簡版的twitch功能,curse在國內能夠訪問因此打算就用electron來作,內置nodejs環境這樣我能夠用爬蟲爬取curse網站的插件數據,獲取插件列表,插件下載地址,而後下載zip包解壓安裝到wow插件目錄,徹底自動化。html
getAddonsList = (path:string, page?:number) : Promise<any> => {
return new Promise((resolve) => {
let timer = setTimeout(():void => {
electron.ipcRenderer.removeListener('getBaseAddons', () => {});
resolve(TIME_OUT_KEY)
}, AJAX_TIME_OUT);
electron.ipcRenderer.send('baseAddons', path, page);
electron.ipcRenderer.on('getBaseAddons', (e:any, data:any) => {
clearTimeout(timer);
electron.ipcRenderer.removeListener('getBaseAddons', () => {});
resolve(data)
})
})
};
複製代碼
getAddonDownUrl = (rowData: any = {}): Promise<any> => {
const installFilePath = localStorage.getItem(WOW_ADDONS_FILE_PATH_KEY);
return new Promise((resolve) => {
let timer = setTimeout((): void => {
electron.ipcRenderer.removeListener(`${rowData.path}-getDownAddonUrl`, () => {});
resolve(TIME_OUT_KEY);
}, AJAX_TIME_OUT);
electron.ipcRenderer.send('downAddon', rowData, installFilePath);
electron.ipcRenderer.on(`${rowData.path}-getDownAddonUrl`, (e:any, data:any) => {
if (data) {
resolve(data);
}
electron.ipcRenderer.removeListener(`${rowData.path}-getDownAddonUrl`, () => {});
clearTimeout(timer);
});
})
};
複製代碼
handleDownloading = (downloadUrl: string, rowData: any): void => { // 下載插件
let file = `${this.state.installFilePath}/${rowData.label}_${Date.now()}.zip`;
let writeStream = fs.createWriteStream(file);
this.setState({ loading: true, btnTxt: LOAD_BTN_TXT, zipFile: file });
request.get(downloadUrl).pipe(writeStream);
// 開始下載
writeStream.on('drain', () : void => {});
// 下載成功
writeStream.on('finish', (): void => {
this.setState({ btnTxt: INSTALL_BTN_TXT });
this.unzipAddon().then((folderList: Array<any>): void => {
this.handleInstallDown(folderList, rowData);
})
});
// 下載失敗
writeStream.on('error', ():void => {
rimraf(file, () => {});
this.setState({ loading: false, btnTxt: `下載插件失敗重試` });
})
};
複製代碼
unzipAddon = (): Promise<any> => { // 解壓插件zip包
return new Promise((resolve) => {
const zip = new AdmZip(this.state.zipFile);
const folderList: Array<any> = [];
zip.getEntries().forEach((entry:any) => {
const entryName = entry.entryName;
const folderName = entryName.split('/')[0];
if (folderList.indexOf(folderName) === -1) {
folderList.push(folderName);
}
});
// 執行解壓
zip.extractAllTo(this.state.installFilePath, true);
resolve(folderList)
})
};
複製代碼
handleInstallDown = (folderList:Array<any>, rowData:any): void => {
const fileJson = `${this.state.installFilePath}/${INSTALL_ADDONS}`;
const { setMyAddonList, updateAddonList, setUpdateAddonList } = this.props.store!;
if (!fs.existsSync(fileJson)) {
fs.writeFileSync(fileJson, '[]')
}
const item = JSON.parse(JSON.stringify(rowData));
item.folderList = folderList;
// 同步本地插件列表
myAddon.setAddon(item);
// 從新獲取一次安裝插件列表
setMyAddonList(myAddon.getAddonList());
// 刪除zip包
rimraf(this.state.zipFile, () => {});
// 若安裝的插件在須要更新的列表裏存在則刪除掉
let cacheUpdateAddonList = JSON.parse(JSON.stringify(updateAddonList));
if (cacheUpdateAddonList.filter((v:any) => v.path === rowData.path).length !== 0) {
setUpdateAddonList(cacheUpdateAddonList.filter((v:any) => v.path !== rowData.path))
}
this.setState({ btnTxt: SUCCESS_BTN_TXT, loading: false });
};
複製代碼