mirror of
https://github.com/Wanxp/obsidian-douban.git
synced 2026-04-04 00:28:43 +08:00
移除旧结构
This commit is contained in:
parent
0fb3be63f4
commit
781b2aa1ca
124
douban/Douban.ts
124
douban/Douban.ts
@ -1,124 +0,0 @@
|
||||
import { i18nHelper } from "lang/helper";
|
||||
import { type } from "os";
|
||||
|
||||
export interface DoubanPluginSettings {
|
||||
movieTemplate:string,
|
||||
bookTemplate:string,
|
||||
musicTemplate:string,
|
||||
noteTemplate:string
|
||||
dateFormat:string,
|
||||
dateTimeFormat:string,
|
||||
searchUrl:string,
|
||||
arraySpilt:string,
|
||||
searchHeaders?:string,
|
||||
personNameMode:PersonNameMode,
|
||||
}
|
||||
|
||||
export enum PersonNameMode {
|
||||
CH_NAME = "CH",
|
||||
EN_NAME = "EN",
|
||||
CH_EN_NAME = "CH_EN",
|
||||
}
|
||||
|
||||
|
||||
export const doubanHeadrs = {
|
||||
"Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
|
||||
"Accept-Language": "en-US,en;q=0.9,zh-CN;q=0.8,zh;q=0.7",
|
||||
"User-Agent": "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/102.0.5005.61 Safari/537.36",
|
||||
};
|
||||
|
||||
export const DEFAULT_SETTINGS:DoubanPluginSettings = {
|
||||
movieTemplate:
|
||||
`---
|
||||
doubanId: {{id}}
|
||||
title: {{title}}
|
||||
originalTitle: {{originalTitle}}
|
||||
type: {{type}}
|
||||
score: {{score}}
|
||||
genre: {{genre}}
|
||||
datePublished: {{datePublished}}
|
||||
director: {{director}}
|
||||
actor: {{actor}}
|
||||
author: {{author}}
|
||||
url: {{url}}
|
||||
desc: {{desc}}
|
||||
---
|
||||
|
||||

|
||||
`,
|
||||
bookTemplate:
|
||||
`---
|
||||
doubanId: {{id}}
|
||||
title: {{title}}
|
||||
subTitle: {{subTitle}}
|
||||
originalTitle: {{originalTitle}}
|
||||
type: {{type}}
|
||||
author: {{author}}
|
||||
score: {{score}}
|
||||
datePublished: {{datePublished}}
|
||||
translator: {{translator}}
|
||||
publish: {{publish}}
|
||||
isbn: {{isbn}}
|
||||
url: {{url}}
|
||||
totalPage: {{totalPage}}
|
||||
price: {{price}}
|
||||
tags: Book
|
||||
desc: {{desc}}
|
||||
---
|
||||
|
||||

|
||||
`,
|
||||
musicTemplate:
|
||||
`---
|
||||
doubanId: {{id}}
|
||||
title: {{title}}
|
||||
type: {{type}}
|
||||
actor: {{actor}}
|
||||
score: {{score}}
|
||||
genre: {{genre}}
|
||||
medium: {{medium}}
|
||||
albumType: {{albumType}}
|
||||
datePublished: {{datePublished}}
|
||||
publish: {{publish}}
|
||||
barcode: {{barcode}}
|
||||
url: {{url}}
|
||||
numberOfRecords: {{numberOfRecords}}
|
||||
tags: Music
|
||||
desc: {{desc}}
|
||||
---
|
||||
|
||||

|
||||
`,
|
||||
noteTemplate:
|
||||
`---
|
||||
doubanId: {{id}}
|
||||
title: {{title}}
|
||||
type: {{type}}
|
||||
author: [{{author}}]({{authorUrl}})
|
||||
timePublished: {{timePublished}}
|
||||
url: {{url}}
|
||||
tags: Article
|
||||
desc: {{desc}}
|
||||
---
|
||||
|
||||
- content
|
||||
{{content}}
|
||||
`,
|
||||
// totalWord: {{totalWord}}
|
||||
|
||||
searchUrl: 'https://www.douban.com/search?q=',
|
||||
searchHeaders: JSON.stringify(doubanHeadrs),
|
||||
dateFormat: "yyyy-MM-DD",
|
||||
dateTimeFormat: "yyyy-MM-DD HH:mm:ss",
|
||||
arraySpilt: ", ",
|
||||
personNameMode: PersonNameMode.CH_NAME
|
||||
|
||||
}
|
||||
|
||||
export const personNameModeRecords: {[key in PersonNameMode]: string} = {
|
||||
[PersonNameMode.CH_NAME]: i18nHelper.getMessage("Chinese Name"),
|
||||
[PersonNameMode.EN_NAME]: i18nHelper.getMessage("English Name"),
|
||||
[PersonNameMode.CH_EN_NAME]: i18nHelper.getMessage("Chinese And English Name"),
|
||||
}
|
||||
|
||||
|
||||
@ -1,291 +0,0 @@
|
||||
import { App, PluginSettingTab, Setting } from "obsidian";
|
||||
import { DEFAULT_SETTINGS, PersonNameMode, personNameModeRecords } from "./Douban";
|
||||
|
||||
import DoubanPlugin from "main";
|
||||
import { i18nHelper } from "lang/helper";
|
||||
import { log } from "utils/Logutil";
|
||||
|
||||
export class DoubanSettingTab extends PluginSettingTab {
|
||||
plugin: DoubanPlugin;
|
||||
|
||||
constructor(app: App, plugin: DoubanPlugin) {
|
||||
super(app, plugin);
|
||||
this.plugin = plugin;
|
||||
}
|
||||
|
||||
display(): void {
|
||||
let { containerEl } = this;
|
||||
|
||||
containerEl.empty();
|
||||
|
||||
containerEl.createEl("h2", { text: "Obsidian Douban" });
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage('douban search url'))
|
||||
.then((setting) => {
|
||||
setting.addText((textField) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('douban search url desc 1'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('douban search url desc 2'));
|
||||
frag.createEl(
|
||||
'a',
|
||||
{
|
||||
text: i18nHelper.getMessage('Douban'),
|
||||
href: 'https://www.douban.com',
|
||||
},
|
||||
(a) => {
|
||||
a.setAttr('target', '_blank');
|
||||
}
|
||||
);
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('douban search url desc 3'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('douban search url desc 4'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('douban search url desc 5'));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
textField.inputEl.addClass("settings_textField");
|
||||
textField
|
||||
.setPlaceholder(DEFAULT_SETTINGS.searchUrl)
|
||||
.setValue(this.plugin.settings.searchUrl)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.searchUrl = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage("movie content template")).then((setting) => {
|
||||
setting.addTextArea((textarea) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 1'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 2'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 3'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 4'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 5'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('movie content template desc 6'));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
textarea.inputEl.addClass("settings_area");
|
||||
textarea.inputEl.setAttr("rows", 10);
|
||||
textarea.setPlaceholder(DEFAULT_SETTINGS.movieTemplate)
|
||||
.setValue(this.plugin.settings.movieTemplate)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.movieTemplate = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage("book content template")).then((setting) => {
|
||||
setting.addTextArea((textarea) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 1'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 2'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 3'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 4'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 5'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('book content template desc 6'));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
textarea.inputEl.addClass("settings_area");
|
||||
textarea.inputEl.setAttr("rows", 10);
|
||||
textarea.setPlaceholder(DEFAULT_SETTINGS.bookTemplate)
|
||||
.setValue(this.plugin.settings.bookTemplate)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.bookTemplate = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage("music content template")).then((setting) => {
|
||||
setting.addTextArea((textarea) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 1'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 2'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 3'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 4'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 5'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('music content template desc 6'));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
textarea.inputEl.addClass("settings_area");
|
||||
textarea.inputEl.setAttr("rows", 10);
|
||||
textarea.setPlaceholder(DEFAULT_SETTINGS.musicTemplate)
|
||||
.setValue(this.plugin.settings.musicTemplate)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.musicTemplate = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage("note content template")).then((setting) => {
|
||||
setting.addTextArea((textarea) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('note content template desc 1'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('note content template desc 2'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('note content template desc 3'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('note content template desc 4'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('note content template desc 5'));
|
||||
frag.createEl('br');
|
||||
|
||||
})
|
||||
);
|
||||
textarea.inputEl.addClass("settings_area");
|
||||
textarea.inputEl.setAttr("rows", 10);
|
||||
textarea.setPlaceholder(DEFAULT_SETTINGS.noteTemplate)
|
||||
.setValue(this.plugin.settings.noteTemplate)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.noteTemplate = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage("Person Name Language Mode")).then((setting) => {
|
||||
setting.addDropdown((dropdwon) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(i18nHelper.getMessage('options:'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('Chinese Name mode, only show Chinese name'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('English Name mode, only show English name'));
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('Chinese English Name mode, show Chinese English name both'));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
// dropdwon.inputEl.addClass("settings_area");
|
||||
// dropdwon.inputEl.setAttr("rows", 10);
|
||||
dropdwon.addOption(PersonNameMode.CH_NAME, personNameModeRecords.CH)
|
||||
dropdwon.addOption(PersonNameMode.EN_NAME, personNameModeRecords.EN)
|
||||
dropdwon.addOption(PersonNameMode.CH_EN_NAME, personNameModeRecords.CH_EN)
|
||||
dropdwon.setValue(this.plugin.settings.personNameMode)
|
||||
.onChange(async (value:string) => {
|
||||
this.plugin.settings.personNameMode = value as PersonNameMode;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage('Date format')).then((setting) => {
|
||||
setting.addMomentFormat((mf) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(
|
||||
i18nHelper.getMessage('This format will be used when available template variables contain date.')
|
||||
);
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('For more syntax, refer to') + ' ');
|
||||
frag.createEl(
|
||||
'a',
|
||||
{
|
||||
text: i18nHelper.getMessage('format reference'),
|
||||
href: 'https://momentjs.com/docs/#/displaying/format/',
|
||||
},
|
||||
(a) => {
|
||||
a.setAttr('target', '_blank');
|
||||
}
|
||||
);
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('Your current syntax looks like this') + ': ');
|
||||
mf.setSampleEl(frag.createEl('b', { cls: 'u-pop' }));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
mf.setPlaceholder(DEFAULT_SETTINGS.dateFormat);
|
||||
mf.setValue(this.plugin.settings.dateFormat)
|
||||
mf.onChange(async (value) => {
|
||||
this.plugin.settings.dateFormat = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
|
||||
new Setting(containerEl).setName(i18nHelper.getMessage('DateTime format')).then((setting) => {
|
||||
setting.addMomentFormat((mf) => {
|
||||
setting.descEl.appendChild(
|
||||
createFragment((frag) => {
|
||||
frag.appendText(
|
||||
i18nHelper.getMessage('This format will be used when available template variables contain dateTime.')
|
||||
);
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('For more syntax, refer to') + ' ');
|
||||
frag.createEl(
|
||||
'a',
|
||||
{
|
||||
text: i18nHelper.getMessage('format reference'),
|
||||
href: 'https://momentjs.com/docs/#/displaying/format/',
|
||||
},
|
||||
(a) => {
|
||||
a.setAttr('target', '_blank');
|
||||
}
|
||||
);
|
||||
frag.createEl('br');
|
||||
frag.appendText(i18nHelper.getMessage('Your current syntax looks like this') + ': ');
|
||||
mf.setSampleEl(frag.createEl('b', { cls: 'u-pop' }));
|
||||
frag.createEl('br');
|
||||
})
|
||||
);
|
||||
mf.setPlaceholder(DEFAULT_SETTINGS.dateTimeFormat);
|
||||
mf.setValue(this.plugin.settings.dateTimeFormat)
|
||||
mf.onChange(async (value) => {
|
||||
this.plugin.settings.dateTimeFormat = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
new Setting(containerEl)
|
||||
.setName(i18nHelper.getMessage("Array Spilt String"))
|
||||
.setDesc(i18nHelper.getMessage(`string to join between array type, such as author, actor`))
|
||||
.addText((textField) => {
|
||||
textField.setPlaceholder(DEFAULT_SETTINGS.arraySpilt)
|
||||
.setValue(this.plugin.settings.arraySpilt)
|
||||
.onChange(async (value) => {
|
||||
this.plugin.settings.arraySpilt = value;
|
||||
await this.plugin.saveSettings();
|
||||
});
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
@ -1,13 +0,0 @@
|
||||
import { Notice } from "obsidian";
|
||||
|
||||
export const ensureStatusCode = (expected:any) => {
|
||||
if (!Array.isArray(expected))
|
||||
expected = [expected];
|
||||
return (res:any) => {
|
||||
const { statusCode } = res;
|
||||
if(!expected.includes(statusCode)) {
|
||||
new Notice(`Request Douban failed, Status code must be "${expected}" but actually "${statusCode}"`)
|
||||
}
|
||||
return res;
|
||||
};
|
||||
};
|
||||
@ -1,93 +0,0 @@
|
||||
import { CheerioAPI, load } from 'cheerio';
|
||||
import { DoubanPluginSettings, PersonNameMode } from "douban/Douban";
|
||||
import { get, readStream } from "tiny-network";
|
||||
|
||||
import DoubanPlugin from "main";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import DoubanSubjectLoadHandler from "./DoubanSubjectLoadHandler";
|
||||
import { Editor } from "obsidian";
|
||||
import { i18nHelper } from 'lang/helper';
|
||||
import { log } from "utils/Logutil";
|
||||
|
||||
export default abstract class DoubanAbstractLoadHandler<T extends DoubanSubject> implements DoubanSubjectLoadHandler<T> {
|
||||
|
||||
|
||||
public doubanPlugin:DoubanPlugin;
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
this.doubanPlugin = doubanPlugin;
|
||||
}
|
||||
|
||||
abstract parseText(extract: T, settings:DoubanPluginSettings): string;
|
||||
|
||||
abstract support(extract: DoubanSubject): boolean;
|
||||
|
||||
handle(url:string, editor:Editor):void {
|
||||
Promise.resolve().then(() => get(log.traceN("GET URL", url + "/"), log.traceN("GET HEAD", JSON.parse(this.doubanPlugin.settings.searchHeaders))))
|
||||
.then(readStream)
|
||||
.then(a => {log.trace(a.toString()); return a;})
|
||||
.then(load)
|
||||
.then(this.parseSubjectFromHtml)
|
||||
.then(content => this.toEditor(editor, content))
|
||||
// .then(content => content ? editor.replaceSelection(content) : content)
|
||||
.catch(e => log.error(i18nHelper.getMessage("Fetch Data Error")))
|
||||
;
|
||||
|
||||
}
|
||||
|
||||
abstract parseSubjectFromHtml(data:CheerioAPI):T | undefined;
|
||||
|
||||
toEditor(editor:Editor, extract: T):T {
|
||||
this.doubanPlugin.putToEditor(editor, extract);
|
||||
return extract;
|
||||
}
|
||||
|
||||
getPersonName(name:string, settings:DoubanPluginSettings):string {
|
||||
if(!name || !settings || !settings.personNameMode) {
|
||||
return "";
|
||||
}
|
||||
var resultName = "";
|
||||
switch(settings.personNameMode) {
|
||||
case PersonNameMode.CH_NAME:
|
||||
var regValue = /[\u4e00-\u9fa5]{2,20}/g.exec(name);
|
||||
resultName = regValue?regValue[0]:name;
|
||||
break;
|
||||
case PersonNameMode.EN_NAME:
|
||||
var regValue = /[a-zA-Z.\s\-]{2,50}/g.exec(name);
|
||||
resultName = regValue?regValue[0]:name;
|
||||
break;
|
||||
default:
|
||||
resultName = name;
|
||||
}
|
||||
return resultName;
|
||||
}
|
||||
|
||||
html_encode(str:string):string
|
||||
{
|
||||
var s = "";
|
||||
if (str.length == 0) return "";
|
||||
s = str.replace(/&/g, "&");
|
||||
s = s.replace(/</g, "<");
|
||||
s = s.replace(/>/g, ">");
|
||||
s = s.replace(/ /g, " ");
|
||||
s = s.replace(/\'/g, "'");
|
||||
s = s.replace(/\"/g, """);
|
||||
s = s.replace(/\n/g, "<br/>");
|
||||
return s;
|
||||
}
|
||||
|
||||
html_decode(str:string):string
|
||||
{
|
||||
var s = "";
|
||||
if (str.length == 0) return "";
|
||||
s = str.replace(/&/g, "&");
|
||||
s = s.replace(/</g, "<");
|
||||
s = s.replace(/>/g, ">");
|
||||
s = s.replace(/ /g, " ");
|
||||
s = s.replace(/'/g, "\'");
|
||||
s = s.replace(/"/g, "\"");
|
||||
s = s.replace(/<br\/>/g, "\n");
|
||||
return s;
|
||||
}
|
||||
|
||||
}
|
||||
@ -1,117 +0,0 @@
|
||||
import { Editor, moment, renderResults } from "obsidian";
|
||||
|
||||
import { CheerioAPI } from 'cheerio';
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import DoubanBookSubject from "douban/model/DoubanBookSubject";
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
|
||||
export default class DoubanBookLoadHandler extends DoubanAbstractLoadHandler<DoubanBookSubject> {
|
||||
|
||||
parseText(extract: DoubanBookSubject, settings:DoubanPluginSettings): string {
|
||||
return settings.bookTemplate ? settings.bookTemplate.replaceAll("{{id}}", extract.id)
|
||||
.replaceAll("{{type}}", extract.type ? extract.type : "")
|
||||
.replaceAll("{{title}}", extract.title ? extract.title : "")
|
||||
.replaceAll("{{desc}}", extract.desc ? extract.desc : "")
|
||||
.replaceAll("{{image}}", extract.image ? extract.image : "")
|
||||
.replaceAll("{{author}}", extract.author ? extract.author.join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{datePublished}}", extract.datePublished ? moment(extract.datePublished).format(settings.dateFormat) : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{score}}", extract.score && extract.score ? extract.score + "" : "")
|
||||
.replaceAll("{{translator}}", extract.translator ? extract.translator.join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{totalWord}}", extract.totalWord ? extract.totalWord+"" : "")
|
||||
.replaceAll("{{isbn}}", extract.isbn ? extract.isbn : "")
|
||||
.replaceAll("{{publish}}", extract.publish ? extract.publish : "")
|
||||
.replaceAll("{{originalTitle}}", extract.originalTitle ? extract.originalTitle : "")
|
||||
.replaceAll("{{subTitle}}", extract.subTitle ? extract.subTitle : "")
|
||||
.replaceAll("{{totalPage}}", extract.totalPage ? extract.totalPage + "" : "")
|
||||
.replaceAll("{{menu}}", extract.menu ? extract.menu.join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{price}}", extract.price ? extract.price + "" : "")
|
||||
.replaceAll("{{labels}}", extract.labels ? extract.labels.join(settings.arraySpilt) : "")
|
||||
|
||||
: undefined;
|
||||
}
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return extract && extract.type && (extract.type.contains("书籍") || extract.type.contains("Book") || extract.type.contains("book"));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
super(doubanPlugin);
|
||||
}
|
||||
|
||||
parseSubjectFromHtml(html: CheerioAPI): DoubanBookSubject {
|
||||
var title = html(html("head > meta[property= 'og:title']").get(0)).attr("content");
|
||||
var desc = html(html("head > meta[property= 'og:description']").get(0)).attr("content");
|
||||
var url = html(html("head > meta[property= 'og:url']").get(0)).attr("content");
|
||||
var image = html(html("head > meta[property= 'og:image']").get(0)).attr("content");
|
||||
var type = html(html("head > meta[property= 'og:type']").get(0)).attr("content");
|
||||
var author = html(html("head > meta[property= 'book:author']").get(0)).attr("content");
|
||||
var isbn = html(html("head > meta[property= 'book:isbn']").get(0)).attr("content");
|
||||
var score = html(html("#interest_sectl > div > div.rating_self.clearfix > strong[property= 'v:average']").get(0)).text();
|
||||
var detailDom = html(html("#info").get(0));
|
||||
var publish = detailDom.find("span.pl");
|
||||
|
||||
var valueMap = new Map<string, string>();
|
||||
|
||||
publish.map((index, info) => {
|
||||
let key = html(info).text().trim();
|
||||
let value = ''
|
||||
if(key.indexOf('作者') >= 0 || key.indexOf('丛书') >= 0 || key.indexOf('译者') >= 0 || key.indexOf('出版社') >= 0){
|
||||
value = html(info.next.next).text().trim();
|
||||
}else{
|
||||
value = html(info.next).text().trim();
|
||||
}
|
||||
valueMap.set(BookKeyValueMap.get(key), value);
|
||||
})
|
||||
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var id = idPattern.exec(url);
|
||||
|
||||
const result:DoubanBookSubject = {
|
||||
author: [author],
|
||||
translator: [valueMap.get('translator')],
|
||||
bookType: "",
|
||||
image: image,
|
||||
datePublished: valueMap.has('datePublished')?new Date(valueMap.get('datePublished')) : null,
|
||||
totalWord: valueMap.has('totalWord') ? Number(valueMap.get('totalWord')) : null,
|
||||
isbn: isbn,
|
||||
publish: valueMap.has('publish') ? valueMap.get('publish') : "",
|
||||
score: Number(score),
|
||||
originalTitle: valueMap.has('originalTitle') ? valueMap.get('originalTitle') : "",
|
||||
subTitle: "",
|
||||
totalPage: valueMap.has('originalTitle') ? Number(valueMap.get('totalPage')) : null,
|
||||
belong: "",
|
||||
menu: [],
|
||||
price: valueMap.has('price') ? Number(valueMap.get('price').replace('元', '')) : null,
|
||||
labels: [],
|
||||
id: id ? id[0]:"",
|
||||
type: "Book",
|
||||
title: title,
|
||||
desc: desc,
|
||||
url: url
|
||||
};
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
const BookKeyValueMap:Map<string, string> = new Map(
|
||||
[['作者', 'author'],
|
||||
['出版社:', 'publish'],
|
||||
['原作名:', 'originalTitle'],
|
||||
['出版年:', 'datePublished'],
|
||||
['页数:', 'totalPage'],
|
||||
['定价:', 'price'],
|
||||
['装帧:', 'binding'],
|
||||
['丛书:', 'bush'],
|
||||
['ISBN:', 'isbn'],
|
||||
['译者', 'translator'],
|
||||
]
|
||||
);
|
||||
@ -1,78 +0,0 @@
|
||||
import { CheerioAPI } from 'cheerio';
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import DoubanMovieSubject from "douban/model/DoubanMovieSubject";
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import SchemaOrg from "utils/SchemaOrg";
|
||||
import { moment } from "obsidian";
|
||||
|
||||
export default class DoubanMovieLoadHandler extends DoubanAbstractLoadHandler<DoubanMovieSubject> {
|
||||
|
||||
parseText(extract: DoubanMovieSubject, settings:DoubanPluginSettings): string {
|
||||
return settings.movieTemplate ? settings.movieTemplate.replaceAll("{{id}}", extract.id)
|
||||
.replaceAll("{{type}}", extract.type ? extract.type : "")
|
||||
.replaceAll("{{title}}", extract.title ? extract.title : "")
|
||||
.replaceAll("{{originalTitle}}", extract.originalTitle ? extract.originalTitle : "")
|
||||
.replaceAll("{{desc}}", extract.desc ? extract.desc : "")
|
||||
.replaceAll("{{image}}", extract.image ? extract.image : "")
|
||||
.replaceAll("{{director}}", extract.director ? extract.director.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{actor}}", extract.actor ? extract.actor.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{author}}", extract.author ? extract.author.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{datePublished}}", extract.datePublished ? moment(extract.datePublished).format(settings.dateFormat) : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{score}}", extract.aggregateRating && extract.aggregateRating.ratingValue ? extract.aggregateRating.ratingValue + "" : "")
|
||||
.replaceAll("{{genre}}", extract.genre ? extract.genre.join(settings.arraySpilt) : "")
|
||||
|
||||
: undefined; }
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return extract && extract.type && (extract.type.contains("电影") || extract.type.contains("Movie") || extract.type.contains("movie"));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
super(doubanPlugin);
|
||||
}
|
||||
|
||||
parseSubjectFromHtml(data: CheerioAPI): DoubanMovieSubject {
|
||||
return data('script')
|
||||
.get()
|
||||
.filter(scd => "application/ld+json" == data(scd).attr("type"))
|
||||
.map(i => {
|
||||
var item = data(i).text();
|
||||
item = super.html_decode(item);
|
||||
var obj = JSON.parse(item.replace(/[\r\n\s+]/g, ''));
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var id = idPattern.exec(obj.url);
|
||||
var name = obj.name;
|
||||
var titleExec = /[\u4e00-\u9fa5]{2,20}/g.exec(name);
|
||||
var title = titleExec?titleExec[0]:name;
|
||||
|
||||
var originalTitleExec = /[a-zA-Z.\s\-]{2,50}/g.exec(name);
|
||||
var originalTitle = originalTitleExec?originalTitleExec[0]:name;
|
||||
|
||||
const result:DoubanMovieSubject = {
|
||||
id: id?id[0]:'',
|
||||
type: 'Movie',
|
||||
title: title,
|
||||
originalTitle: originalTitle,
|
||||
desc: obj.description,
|
||||
url: "https://movie.douban.com" + obj.url,
|
||||
director: obj.director,
|
||||
author: obj.author,
|
||||
actor: obj.actor,
|
||||
aggregateRating: obj.aggregateRating,
|
||||
datePublished: obj.datePublished ? new Date(obj.datePublished) : undefined,
|
||||
image:obj.image,
|
||||
genre:obj.genre
|
||||
}
|
||||
return result;
|
||||
})[0];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -1,103 +0,0 @@
|
||||
import { CheerioAPI } from 'cheerio';
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import DoubanMusicSubject from 'douban/model/DoubanMusicSubject';
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import { moment } from "obsidian";
|
||||
|
||||
export default class DoubanMusicLoadHandler extends DoubanAbstractLoadHandler<DoubanMusicSubject> {
|
||||
|
||||
parseText(extract: DoubanMusicSubject, settings:DoubanPluginSettings): string {
|
||||
return settings.bookTemplate ? settings.musicTemplate
|
||||
.replaceAll("{{id}}", extract.id)
|
||||
.replaceAll("{{type}}", extract.type ? extract.type : "")
|
||||
.replaceAll("{{title}}", extract.title ? extract.title : "")
|
||||
.replaceAll("{{desc}}", extract.desc ? extract.desc : "")
|
||||
.replaceAll("{{image}}", extract.image ? extract.image : "")
|
||||
.replaceAll("{{actor}}", extract.actor ? extract.actor.join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{datePublished}}", extract.datePublished ? moment(extract.datePublished).format(settings.dateFormat) : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{score}}", extract.score && extract.score ? extract.score + "" : "")
|
||||
.replaceAll("{{barcode}}", extract.barcode ? extract.barcode : "")
|
||||
.replaceAll("{{publish}}", extract.publish ? extract.publish : "")
|
||||
.replaceAll("{{genre}}", extract.genre ? extract.genre : "")
|
||||
.replaceAll("{{medium}}", extract.medium ? extract.medium : "")
|
||||
.replaceAll("{{albumType}}", extract.albumType ? extract.albumType : "")
|
||||
.replaceAll("{{numberOfRecords}}", extract.numberOfRecords ? extract.numberOfRecords + "" : "")
|
||||
: undefined;
|
||||
}
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return extract && extract.type && (extract.type.contains("音乐") || extract.type.contains("Music") || extract.type.contains("music"));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
super(doubanPlugin);
|
||||
}
|
||||
|
||||
parseSubjectFromHtml(html: CheerioAPI): DoubanMusicSubject {
|
||||
var title = html(html("head > meta[property= 'og:title']").get(0)).attr("content");
|
||||
var desc = html(html("head > meta[property= 'og:description']").get(0)).attr("content");
|
||||
var url = html(html("head > meta[property= 'og:url']").get(0)).attr("content");
|
||||
var image = html(html("head > meta[property= 'og:image']").get(0)).attr("content");
|
||||
var score = html(html("#interest_sectl > div > div.rating_self.clearfix > strong[property= 'v:average']").get(0)).text();
|
||||
var detailDom = html(html("#info").get(0));
|
||||
var publish = detailDom.find("span.pl");
|
||||
|
||||
var valueMap = new Map<string, string>();
|
||||
|
||||
publish.map((index, info) => {
|
||||
let key = html(info).text().trim();
|
||||
let value = ''
|
||||
if(key.indexOf('表演者') >= 0){
|
||||
// value = html(info.next.next).text().trim();
|
||||
var vas:string[] = key.split("\n \n ");
|
||||
value = vas && vas.length > 1? vas[1]:"";
|
||||
key = vas && vas.length > 0? vas[0]:"";
|
||||
}else{
|
||||
value = html(info.next).text().trim();
|
||||
}
|
||||
valueMap.set(BookKeyValueMap.get(key), value);
|
||||
})
|
||||
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var id = idPattern.exec(url);
|
||||
|
||||
const result:DoubanMusicSubject = {
|
||||
image: image,
|
||||
datePublished: valueMap.has('datePublished') ? new Date(valueMap.get('datePublished')) : null,
|
||||
publish: valueMap.has('publish') ? valueMap.get('publish') : "",
|
||||
score: Number(score),
|
||||
numberOfRecords: valueMap.has('numberOfRecords') ? Number(valueMap.get('numberOfRecords')) : null,
|
||||
id: id ? id[0] : "",
|
||||
type: "Music",
|
||||
title: title,
|
||||
desc: desc,
|
||||
url: url,
|
||||
actor: [valueMap.has('actor') ? valueMap.get('actor') : null],
|
||||
genre: valueMap.has('genre') ? valueMap.get('genre') : "",
|
||||
albumType: valueMap.has('albumType') ? valueMap.get('albumType') : "",
|
||||
medium: valueMap.has('medium') ? valueMap.get('medium') : "",
|
||||
barcode: valueMap.has('barcode') ? valueMap.get('barcode') : ""
|
||||
};
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
const BookKeyValueMap:Map<string, string> = new Map(
|
||||
[['表演者:', 'actor'],
|
||||
['流派:', 'genre'],
|
||||
['发行时间:', 'datePublished'],
|
||||
['专辑类型:', 'albumType'],
|
||||
['介质:', 'medium'],
|
||||
['出版者:', 'publish'],
|
||||
['唱片数:', 'numberOfRecords'],
|
||||
['条形码:', 'barcode']]
|
||||
);
|
||||
@ -1,69 +0,0 @@
|
||||
import { CheerioAPI } from 'cheerio';
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import DoubanNoteSubject from 'douban/model/DoubanNoteSubject';
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import html2markdown from '@notable/html2markdown';
|
||||
import { moment } from "obsidian";
|
||||
|
||||
export default class DoubanNoteLoadHandler extends DoubanAbstractLoadHandler<DoubanNoteSubject> {
|
||||
|
||||
parseText(extract: DoubanNoteSubject, settings:DoubanPluginSettings): string {
|
||||
return settings.bookTemplate ? settings.noteTemplate
|
||||
.replaceAll("{{id}}", extract.id)
|
||||
.replaceAll("{{type}}", extract.type ? extract.type : "")
|
||||
.replaceAll("{{title}}", extract.title ? extract.title : "")
|
||||
.replaceAll("{{desc}}", extract.desc ? extract.desc : "")
|
||||
.replaceAll("{{image}}", extract.image ? extract.image : "")
|
||||
.replaceAll("{{timePublished}}", extract.timePublished ? moment(extract.timePublished).format(settings.dateTimeFormat) : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{content}}", extract.content ? extract.content : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{authorUrl}}", extract.authorUrl ? extract.authorUrl : "")
|
||||
.replaceAll("{{author}}", extract.author ? extract.author : "")
|
||||
|
||||
|
||||
: undefined;
|
||||
}
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return extract && extract.type && (extract.type.contains("日记") || extract.type.contains("Note") || extract.type.contains("Article"));
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
super(doubanPlugin);
|
||||
}
|
||||
|
||||
parseSubjectFromHtml(html: CheerioAPI): DoubanNoteSubject {
|
||||
var title = html(html("head > meta[property= 'og:title']").get(0)).attr("content");
|
||||
var desc = html(html("head > meta[property= 'og:description']").get(0)).attr("content");
|
||||
var url = html(html("head > meta[property= 'og:url']").get(0)).attr("content");
|
||||
var image = html(html("head > meta[property= 'og:image']").get(0)).attr("content");
|
||||
var type = html(html("head > meta[property= 'og:type']").get(0)).attr("content");
|
||||
var authorA = html(html("a.note-author").get(0));
|
||||
var timePublished = html(html(".pub-date").get(0)).text();
|
||||
var content = html(html(".note").get(1));
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var id = idPattern.exec(url);
|
||||
|
||||
const result:DoubanNoteSubject = {
|
||||
image: image,
|
||||
timePublished: timePublished ? new Date(timePublished) : null,
|
||||
content: content ? html2markdown(content.toString()): "",
|
||||
id: id ? id[0] : "",
|
||||
type: "Article",
|
||||
title: title,
|
||||
desc: desc,
|
||||
url: url,
|
||||
author: authorA ? authorA.text() : null,
|
||||
authorUrl: authorA ? authorA.attr("href") : null,
|
||||
};
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -1,29 +0,0 @@
|
||||
import { Editor, Notice } from "obsidian";
|
||||
|
||||
import { CheerioAPI } from "cheerio";
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import { i18nHelper } from "lang/helper";
|
||||
import { log } from "utils/Logutil";
|
||||
|
||||
/**
|
||||
* 默认的处理器
|
||||
*/
|
||||
export default class DoubanOtherLoadHandler extends DoubanAbstractLoadHandler<DoubanSubject> {
|
||||
parseText(extract: DoubanSubject, settings:DoubanPluginSettings): string {
|
||||
log.warn(i18nHelper.getMessage('current version not support type'));
|
||||
return "";
|
||||
}
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return false;
|
||||
}
|
||||
parseSubjectFromHtml(data: CheerioAPI): DoubanSubject {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
@ -1,69 +0,0 @@
|
||||
import { App, Editor } from "obsidian";
|
||||
|
||||
import DoubanBookLoadHandler from "./DoubanBookLoadHandler";
|
||||
import DoubanMovieLoadHandler from "./DoubanMovieLoadHandler";
|
||||
import DoubanMusicLoadHandler from "./DoubanMusicLoadHandler";
|
||||
import DoubanNoteLoadHandler from "./DoubanNoteLoadHandler";
|
||||
import DoubanOtherLoadHandler from "./DoubanOtherLoadHandler";
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "../model/DoubanSubject";
|
||||
import DoubanSubjectLoadHandler from "./DoubanSubjectLoadHandler";
|
||||
import { DoubanTeleplayLoadHandler } from "./DoubanTeleplayLoadHandler";
|
||||
|
||||
export class DoubanSearchChooseItemHandler {
|
||||
|
||||
private _app:App;
|
||||
private _doubanPlugin:DoubanPlugin;
|
||||
private _doubanSubjectHandlers:DoubanSubjectLoadHandler<DoubanSubject>[];
|
||||
private _doubanSubjectHandlerDefault:DoubanSubjectLoadHandler<DoubanSubject>;
|
||||
|
||||
|
||||
|
||||
constructor(app:App, doubanPlugin:DoubanPlugin) {
|
||||
this._app = app;
|
||||
this._doubanPlugin = doubanPlugin;
|
||||
this._doubanSubjectHandlerDefault = new DoubanOtherLoadHandler(doubanPlugin);
|
||||
this._doubanSubjectHandlers = [new DoubanMovieLoadHandler(doubanPlugin), new DoubanBookLoadHandler(doubanPlugin),
|
||||
new DoubanTeleplayLoadHandler(doubanPlugin),
|
||||
new DoubanMusicLoadHandler(doubanPlugin),
|
||||
new DoubanNoteLoadHandler(doubanPlugin),
|
||||
|
||||
this._doubanSubjectHandlerDefault];
|
||||
|
||||
}
|
||||
|
||||
public handle(searchExtract:DoubanSubject, editor: Editor):void{
|
||||
if(!searchExtract) {
|
||||
return;
|
||||
}
|
||||
var doubanSubjectHandlers:DoubanSubjectLoadHandler<DoubanSubject>[] = this._doubanSubjectHandlers
|
||||
.filter(h => h.support(searchExtract));
|
||||
if(doubanSubjectHandlers && doubanSubjectHandlers.length > 0) {
|
||||
doubanSubjectHandlers[0].handle(searchExtract.url, editor);
|
||||
}else {
|
||||
this._doubanSubjectHandlerDefault.handle(searchExtract.url, editor);
|
||||
}
|
||||
}
|
||||
|
||||
public parseText(extract:DoubanSubject, settings:DoubanPluginSettings):string {
|
||||
if(!settings) {
|
||||
return "";
|
||||
}
|
||||
var doubanSubjectHandlers:DoubanSubjectLoadHandler<DoubanSubject>[] = this._doubanSubjectHandlers
|
||||
.filter(h => h.support(extract));
|
||||
if(doubanSubjectHandlers && doubanSubjectHandlers.length > 0) {
|
||||
var result = doubanSubjectHandlers.map(h => h.parseText(extract, settings));
|
||||
if(result && result.length > 0) {
|
||||
return result[0];
|
||||
}else {
|
||||
return "";
|
||||
}
|
||||
}else {
|
||||
return this._doubanSubjectHandlerDefault.parseText(extract, settings);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -1,14 +0,0 @@
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import { Editor } from "obsidian";
|
||||
|
||||
export default interface DoubanSubjectLoadHandler<T extends DoubanSubject> {
|
||||
|
||||
parseText(extract: T, settings:DoubanPluginSettings): string;
|
||||
|
||||
support(extract:DoubanSubject):boolean;
|
||||
|
||||
handle(url:string, editor: Editor):void;
|
||||
|
||||
|
||||
}
|
||||
@ -1,80 +0,0 @@
|
||||
import { CheerioAPI } from "cheerio";
|
||||
import DoubanAbstractLoadHandler from "./DoubanAbstractLoadHandler";
|
||||
import DoubanPlugin from "main";
|
||||
import { DoubanPluginSettings } from "douban/Douban";
|
||||
import DoubanSubject from "douban/model/DoubanSubject";
|
||||
import DoubanTeleplaySubject from "douban/model/DoubanTeleplaySubject";
|
||||
import SchemaOrg from "utils/SchemaOrg";
|
||||
import { moment } from "obsidian";
|
||||
|
||||
/**
|
||||
* teleplay
|
||||
*/
|
||||
export class DoubanTeleplayLoadHandler extends DoubanAbstractLoadHandler<DoubanTeleplaySubject>{
|
||||
|
||||
|
||||
|
||||
constructor(doubanPlugin:DoubanPlugin) {
|
||||
super(doubanPlugin);
|
||||
}
|
||||
|
||||
|
||||
parseText(extract: DoubanTeleplaySubject, settings:DoubanPluginSettings): string {
|
||||
return settings.movieTemplate ? settings.movieTemplate.replaceAll("{{id}}", extract.id)
|
||||
.replaceAll("{{type}}", extract.type ? extract.type : "")
|
||||
.replaceAll("{{title}}", extract.title ? extract.title : "")
|
||||
.replaceAll("{{originalTitle}}", extract.originalTitle ? extract.originalTitle : "")
|
||||
.replaceAll("{{desc}}", extract.desc ? extract.desc : "")
|
||||
.replaceAll("{{image}}", extract.image ? extract.image : "")
|
||||
.replaceAll("{{director}}", extract.director ? extract.director.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{actor}}", extract.actor ? extract.actor.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{author}}", extract.author ? extract.author.map(SchemaOrg.getPersonName).map(name => super.getPersonName(name, settings)).filter(c => c).join(settings.arraySpilt) : "")
|
||||
.replaceAll("{{datePublished}}", extract.datePublished ? moment(extract.datePublished).format(settings.dateFormat) : "")
|
||||
.replaceAll("{{url}}", extract.url ? extract.url : "")
|
||||
.replaceAll("{{score}}", extract.aggregateRating && extract.aggregateRating.ratingValue ? extract.aggregateRating.ratingValue + "" : "")
|
||||
.replaceAll("{{genre}}", extract.genre ? extract.genre.join(settings.arraySpilt) : "")
|
||||
|
||||
: undefined; }
|
||||
|
||||
support(extract: DoubanSubject): boolean {
|
||||
return extract && extract.type && (extract.type.contains("电视剧") || extract.type.contains("Teleplay") || extract.type.contains("teleplay"));
|
||||
}
|
||||
|
||||
|
||||
parseSubjectFromHtml(data: CheerioAPI): DoubanTeleplaySubject {
|
||||
return data('script')
|
||||
.get()
|
||||
.filter(scd => "application/ld+json" == data(scd).attr("type"))
|
||||
.map(i => {
|
||||
var item = data(i).text();
|
||||
item = super.html_decode(item);
|
||||
var obj = JSON.parse(item.replace(/[\r\n\s+]/g, ''));
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var id = idPattern.exec(obj.url);
|
||||
var name = obj.name;
|
||||
var titleExec = /[\u4e00-\u9fa5]{2,20}/g.exec(name);
|
||||
var title = titleExec?titleExec[0]:name;
|
||||
|
||||
var originalTitleExec = /[a-zA-Z.\s\-]{2,50}/g.exec(name);
|
||||
var originalTitle = originalTitleExec?originalTitleExec[0]:name;
|
||||
|
||||
const result:DoubanTeleplaySubject = {
|
||||
id: id?id[0]:'',
|
||||
type: 'Movie',
|
||||
title: title,
|
||||
originalTitle: originalTitle,
|
||||
desc: obj.description,
|
||||
url: "https://movie.douban.com" + obj.url,
|
||||
director: obj.director,
|
||||
author: obj.author,
|
||||
actor: obj.actor,
|
||||
aggregateRating: obj.aggregateRating,
|
||||
datePublished: obj.datePublished ? new Date(obj.datePublished) : undefined,
|
||||
image:obj.image,
|
||||
genre:obj.genre
|
||||
}
|
||||
return result;
|
||||
})[0];
|
||||
}
|
||||
|
||||
}
|
||||
@ -1,22 +0,0 @@
|
||||
import {AggregateRating, Person, WithContext} from 'schema-dts';
|
||||
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanMovieSubject extends DoubanSubject {
|
||||
author:string[];
|
||||
translator:string[];
|
||||
bookType:string;
|
||||
image:string;
|
||||
datePublished:Date;
|
||||
totalWord:number;
|
||||
isbn:string;
|
||||
publish:string;
|
||||
score:number;
|
||||
originalTitle:string;
|
||||
subTitle:string;
|
||||
totalPage:number
|
||||
belong:string;
|
||||
menu:string[];
|
||||
price:number;
|
||||
labels:string[];
|
||||
}
|
||||
@ -1,15 +0,0 @@
|
||||
import {AggregateRating, Person, WithContext} from 'schema-dts';
|
||||
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanMovieSubject extends DoubanSubject {
|
||||
director:Person[];
|
||||
author:Person[];
|
||||
actor:Person[];
|
||||
aggregateRating:AggregateRating;
|
||||
datePublished:Date;
|
||||
image:string;
|
||||
genre:string[];
|
||||
originalTitle:string;
|
||||
|
||||
}
|
||||
@ -1,16 +0,0 @@
|
||||
import {AggregateRating, Person, WithContext} from 'schema-dts';
|
||||
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanMusicSubject extends DoubanSubject {
|
||||
actor:string[];
|
||||
datePublished:Date;
|
||||
image:string;
|
||||
genre:string;
|
||||
albumType:string;
|
||||
medium:string;
|
||||
publish:string;
|
||||
numberOfRecords:number;
|
||||
barcode:string;
|
||||
score:number;
|
||||
}
|
||||
@ -1,11 +0,0 @@
|
||||
import {AggregateRating, Person, WithContext} from 'schema-dts';
|
||||
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanNoteSubject extends DoubanSubject {
|
||||
author:string;
|
||||
authorUrl:string;
|
||||
timePublished:Date;
|
||||
image:string;
|
||||
content:string;
|
||||
}
|
||||
@ -1,6 +0,0 @@
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanSearchResultSubject extends DoubanSubject {
|
||||
score:string;
|
||||
cast:string;
|
||||
}
|
||||
@ -1,7 +0,0 @@
|
||||
export default class DoubanExtract {
|
||||
id: string;
|
||||
type: string;
|
||||
title: string;
|
||||
desc: string;
|
||||
url: string;
|
||||
}
|
||||
@ -1,14 +0,0 @@
|
||||
import {AggregateRating, Person, WithContext} from 'schema-dts';
|
||||
|
||||
import DoubanSubject from "./DoubanSubject";
|
||||
|
||||
export default class DoubanTeleplaySubject extends DoubanSubject {
|
||||
director:Person[];
|
||||
author:Person[];
|
||||
actor:Person[];
|
||||
aggregateRating:AggregateRating;
|
||||
datePublished:Date;
|
||||
image:string;
|
||||
genre:string[];
|
||||
originalTitle:string;
|
||||
}
|
||||
@ -1,53 +0,0 @@
|
||||
import { App, Editor, FuzzySuggestModal } from "obsidian";
|
||||
|
||||
import DoubanPlugin from "main";
|
||||
import DoubanSearchResultSubject from "douban/model/DoubanSearchResultSubject";
|
||||
import { log } from "utils/Logutil";
|
||||
|
||||
export {DoubanFuzzySuggester}
|
||||
|
||||
|
||||
class DoubanFuzzySuggester extends FuzzySuggestModal<DoubanSearchResultSubject> {
|
||||
|
||||
public editor: Editor;
|
||||
private plugin: DoubanPlugin;
|
||||
private doubanSearchResultExtract:DoubanSearchResultSubject[]
|
||||
|
||||
constructor(plugin: DoubanPlugin, editor: Editor) {
|
||||
super(app);
|
||||
this.editor = editor;
|
||||
this.plugin = plugin;
|
||||
this.setPlaceholder("Choose an item...");
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
getItems(): DoubanSearchResultSubject[] {
|
||||
return this.doubanSearchResultExtract;
|
||||
}
|
||||
|
||||
getItemText(item: DoubanSearchResultSubject): string {
|
||||
let text:string = item.type + "/" + item.score + "/" + item.title + "/" + item.cast;
|
||||
return text;
|
||||
}
|
||||
|
||||
onChooseItem(item: DoubanSearchResultSubject, evt: MouseEvent | KeyboardEvent): void {
|
||||
log.trace(`you chosen : ${JSON.stringify(item)}`)
|
||||
this.plugin.doubanEtractHandler.handle(item, this.editor);
|
||||
}
|
||||
|
||||
public showSearchList(doubanSearchResultExtractList:DoubanSearchResultSubject[]) {
|
||||
this.doubanSearchResultExtract = doubanSearchResultExtractList;
|
||||
this.start();
|
||||
}
|
||||
|
||||
public start(): void {
|
||||
try {
|
||||
this.open();
|
||||
} catch (e) {
|
||||
log.error(e);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@ -1,65 +0,0 @@
|
||||
import { App, Editor, Modal, TextComponent } from "obsidian";
|
||||
|
||||
import DoubanPlugin from "../../main";
|
||||
import { i18nHelper } from "lang/helper";
|
||||
import { log } from "utils/Logutil";
|
||||
|
||||
export class DoubanSearchModal extends Modal {
|
||||
searchTerm: string;
|
||||
plugin: DoubanPlugin;
|
||||
editor: Editor;
|
||||
|
||||
constructor(app: App, plugin: DoubanPlugin, editor: Editor) {
|
||||
super(app);
|
||||
this.plugin = plugin;
|
||||
this.editor = editor;
|
||||
}
|
||||
|
||||
onOpen() {
|
||||
let { contentEl } = this;
|
||||
|
||||
contentEl.createEl("h2", { text: i18nHelper.getMessage('Enter Search Term:') });
|
||||
|
||||
const inputs = contentEl.createDiv("inputs");
|
||||
const searchInput = new TextComponent(inputs).onChange((searchTerm) => {
|
||||
this.searchTerm = searchTerm;
|
||||
});
|
||||
searchInput.inputEl.addClass("search_input");
|
||||
|
||||
searchInput.inputEl.focus();
|
||||
searchInput.inputEl.addEventListener("keydown", (event) => {
|
||||
if (event.key === "Enter") {
|
||||
this.close();
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
|
||||
const controls = contentEl.createDiv("controls");
|
||||
const searchButton = controls.createEl("button", {
|
||||
text: i18nHelper.getMessage('Search'),
|
||||
cls: "mod-cta",
|
||||
attr: {
|
||||
autofocus: true,
|
||||
},
|
||||
});
|
||||
searchButton.addClass("search_button");
|
||||
|
||||
searchButton.addEventListener("click", this.close.bind(this));
|
||||
const cancelButton = controls.createEl("button", { text: i18nHelper.getMessage('Cancel') });
|
||||
cancelButton.addEventListener("click", this.close.bind(this));
|
||||
cancelButton.addClass("search_button");
|
||||
|
||||
}
|
||||
|
||||
|
||||
async onClose() {
|
||||
let { contentEl } = this;
|
||||
|
||||
contentEl.empty();
|
||||
if (this.searchTerm) {
|
||||
await this.plugin.search(this.searchTerm, this.editor);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@ -1,24 +0,0 @@
|
||||
import { DoubanPluginSettings, doubanHeadrs } from 'douban/Douban';
|
||||
import cheerio, { load } from 'cheerio';
|
||||
import { get, readStream } from 'tiny-network';
|
||||
|
||||
import DoubanSearchResultSubject from 'douban/model/DoubanSearchResultSubject';
|
||||
import SearchParserHandler from './SearchParser';
|
||||
import { ensureStatusCode } from 'douban/ResponseHandle';
|
||||
import { log } from 'utils/Logutil';
|
||||
|
||||
export default class Searcher {
|
||||
static search(searchItem:string, doubanSettings:DoubanPluginSettings):Promise<DoubanSearchResultSubject[]> {
|
||||
// getData();
|
||||
// getData2();
|
||||
// return Promise.resolve();
|
||||
return Promise
|
||||
.resolve()
|
||||
.then(() => get(log.traceN("GET", doubanSettings.searchUrl + searchItem), JSON.parse(doubanSettings.searchHeaders)))
|
||||
.then(ensureStatusCode(200))
|
||||
.then(readStream)
|
||||
.then(load)
|
||||
.then(SearchParserHandler.parseSearch)
|
||||
.then(log.trace);
|
||||
};
|
||||
}
|
||||
@ -1,28 +0,0 @@
|
||||
import { CheerioAPI } from "cheerio";
|
||||
import DoubanSearchResultSubject from "douban/model/DoubanSearchResultSubject";
|
||||
|
||||
export default class SearchParserHandler {
|
||||
static parseSearch(dataHtml:CheerioAPI):DoubanSearchResultSubject[] {
|
||||
return dataHtml('.result')
|
||||
.get()
|
||||
.map((i:any) => {
|
||||
const item = dataHtml(i);
|
||||
var idPattern = /(\d){5,10}/g;
|
||||
var urlPattern = /(https%3A%2F%2F)\S+(\d){5,10}/g;
|
||||
var linkValue = item.find("div.content > div > h3 > a").attr("href");
|
||||
var ececResult = idPattern.exec(linkValue);
|
||||
var urlResult = urlPattern.exec(linkValue);
|
||||
var cast = item.find(".subject-cast").text();
|
||||
const result:DoubanSearchResultSubject = {
|
||||
id: ececResult?ececResult[0]:'',
|
||||
title: item.find("div.content > div > h3 > a").text(),
|
||||
score: item.find(".rating_nums").text(),
|
||||
cast: cast,
|
||||
type: item.find("div.content > div > h3 > span").text(),
|
||||
desc: item.find("div.content > p").text(),
|
||||
url: urlResult?decodeURIComponent(urlResult[0]):'https://www.douban.com',
|
||||
};
|
||||
return result;
|
||||
})
|
||||
};
|
||||
}
|
||||
24
jest.config.js
Normal file
24
jest.config.js
Normal file
@ -0,0 +1,24 @@
|
||||
const { default: tsjPreset } = require('ts-jest/presets');
|
||||
module.exports = {
|
||||
preset: 'ts-jest',
|
||||
rootDir: './',
|
||||
transform: {
|
||||
...tsjPreset.transform
|
||||
},
|
||||
testRegex: '(/test/.*\\.(test|spec))\\.[tj]sx?$',
|
||||
moduleFileExtensions: [
|
||||
"ts",
|
||||
"tsx",
|
||||
"js",
|
||||
"jsx"
|
||||
],
|
||||
moduleNameWrapper: {
|
||||
'^@APP/(.*)$': '<rootDir>/src/douban/$1'
|
||||
},
|
||||
collectCoverageFrom: {
|
||||
"**/baseTs/upperFirst.ts",
|
||||
"**/baseTs/camelCase.ts",
|
||||
"!**/node_modules/**",
|
||||
"!**/vendor/**"
|
||||
}
|
||||
}
|
||||
@ -1,23 +0,0 @@
|
||||
import en from './locale/en';
|
||||
import zhCN from './locale/zh-cn';
|
||||
|
||||
const localeMap: { [k: string]: Partial<typeof en> } = {
|
||||
en,
|
||||
zh: zhCN,
|
||||
};
|
||||
|
||||
const lang = window.localStorage.getItem('language');
|
||||
const locale = localeMap[lang || 'en'];
|
||||
|
||||
|
||||
export default class I18nHelper {
|
||||
public getMessage(str: keyof typeof en): string {
|
||||
if (!locale) {
|
||||
console.error('Error: obsidian douban locale not found', lang);
|
||||
}
|
||||
|
||||
return (locale && locale[str]) || en[str];
|
||||
}
|
||||
}
|
||||
|
||||
export const i18nHelper:I18nHelper = new I18nHelper();
|
||||
@ -1,77 +0,0 @@
|
||||
//简体中文
|
||||
export default {
|
||||
//main.ts
|
||||
'search douban by current file name':'search douban by current file name',
|
||||
'search douban and import to current file':'search douban and import to current file',
|
||||
'Enter Search Term:':`Enter Search Term:`,
|
||||
'Search':`Search`,
|
||||
'Cancel':`Cancel`,
|
||||
//DoubanSettingTab
|
||||
'douban search url': `Douban Search Url`,
|
||||
'douban search url desc 1': `Douban search page request address. `,
|
||||
'douban search url desc 2': `First go to:`,
|
||||
'douban search url desc 3': `Don't enter anything in the search input box, just click Search,`,
|
||||
'douban search url desc 4': `The redirected web page address is the search address,`,
|
||||
'douban search url desc 5': `Just copy the web address to the current input box.`,
|
||||
|
||||
'movie content template': `Movie Content Template`,
|
||||
'movie content template desc 1': `Set markdown Movie template for extract to be inserted.`,
|
||||
'movie content template desc 2': `Available template variables are :`,
|
||||
'movie content template desc 3': `{{id}}, {{type}}, {{title}}, {{originalTitle}},`,
|
||||
'movie content template desc 4': `{{score}}, {{datePublished}}, {{director}},`,
|
||||
'movie content template desc 5': `{{author}}, {{actor}}, {{desc}}, {{genre}},`,
|
||||
'movie content template desc 6': `{{image}}, {{url}}`,
|
||||
|
||||
'book content template': `Book Content Template`,
|
||||
'book content template desc 1': `Set markdown Book template for extract to be inserted.`,
|
||||
'book content template desc 2': `Available Book template variables are :`,
|
||||
'book content template desc 3': `{{id}}, {{title}}, {{originalTitle}}, {{subTitle}},`,
|
||||
'book content template desc 4': `{{score}}, {{author}}, {{datePublished}}, {{type}},`,
|
||||
'book content template desc 5': `{{publish}}, {{desc}}, {{translator}}, {{isbn}},`,
|
||||
'book content template desc 6': `{{image}}, {{url}}, {{price}}, {{desc}}, {{totalPage}}`,
|
||||
|
||||
'music content template': `Music Content Template`,
|
||||
'music content template desc 1': `Set markdown Music template for extract to be inserted.`,
|
||||
'music content template desc 2': `Available Music template variables are :`,
|
||||
'music content template desc 3': `{{id}}, {{title}}, {{actor}}, {{genre}},`,
|
||||
'music content template desc 4': `{{score}}, {{medium}}, {{datePublished}}, {{type}},`,
|
||||
'music content template desc 5': `{{publish}}, {{desc}}, {{albumType}}, {{barcode}},`,
|
||||
'music content template desc 6': `{{image}}, {{url}}, {{numberOfRecords}}, {{desc}}`,
|
||||
|
||||
'note content template': `Article Content Template`,
|
||||
'note content template desc 1': `Set markdown Article template for extract to be inserted.`,
|
||||
'note content template desc 2': `Available Article template variables are :`,
|
||||
'note content template desc 3': `{{id}}, {{title}}, {{author}}, {{authorUrl}},`,
|
||||
'note content template desc 4': `{{timePublished}}, {{url}}, {{desc}}, {{type}},`,
|
||||
'note content template desc 5': `{{content}}`,
|
||||
|
||||
'Date format': `Date Format`,
|
||||
'DateTime format': `DateTime Format`,
|
||||
|
||||
'This format will be used when available template variables contain date.':
|
||||
`This format will be used when available template variables contain date.`,
|
||||
'This format will be used when available template variables contain dateTime.':
|
||||
`This format will be used when available template variables contain dateTime.`,
|
||||
'For more syntax, refer to': `For more syntax, refer to`,
|
||||
'Your current syntax looks like this':`Your current syntax looks like this`,
|
||||
'format reference': `format reference`,
|
||||
'Array Spilt String':`Array Spilt String`,
|
||||
'string to join between array type, such as author, actor':`string to join between array type, such as author, actor`,
|
||||
'Douban Request Headers':`Douban Request Headers`,
|
||||
'current version not support type': `This type of import is not supported temporarily, please go to github to submit issues for help`,
|
||||
'Douban': `Douban`,
|
||||
'Person Name Language Mode':'Person Name Language Mode',
|
||||
'options:':"options:",
|
||||
'Chinese Name mode, only show Chinese name':'Chinese Name mode, person name only show Chinese name',
|
||||
'English Name mode, only show English name':'English Name mode, person name only show English name',
|
||||
'Chinese English Name mode, show Chinese English name both':'Chinese English Name mode, show Chinese and English name both',
|
||||
'Chinese Name': 'Chinese Name',
|
||||
'English Name': 'English Name',
|
||||
'Chinese And English Name': 'Chinese And English Name',
|
||||
|
||||
|
||||
//error
|
||||
"Fetch Data Error": "Fetch Data Error, You can go to Github add Issues",
|
||||
"Obsidian Douban Plugin Error:": "Obsidian Douban Plugin Error: ",
|
||||
"Obsidian Douban Plugin Warn:": "Obsidian Douban Plugin Warn: ",
|
||||
}
|
||||
@ -1,83 +0,0 @@
|
||||
//简体中文
|
||||
export default {
|
||||
//main.ts
|
||||
'search douban by current file name':'用当前文档名搜索豆瓣并写入当前文档',
|
||||
'search douban and import to current file':'在豆瓣搜索并写入到当前文档',
|
||||
'Enter Search Term:':`输入搜索内容:`,
|
||||
'Search':`搜索`,
|
||||
'Cancel':`取消`,
|
||||
|
||||
//DoubanSettingTab
|
||||
'douban search url': `豆瓣搜索地址`,
|
||||
'douban search url desc 1': `豆瓣搜索页面请求地址, 通常是网页搜索的地址. `,
|
||||
'douban search url desc 2': `先访问:`,
|
||||
'douban search url desc 3': `然后在搜索输入框不输入任何内容,直接点击搜索,`,
|
||||
'douban search url desc 4': `所跳转的网页地址即是搜索地址,`,
|
||||
'douban search url desc 5': `将网页地址复制到当前输入框即可,`,
|
||||
|
||||
'movie content template': `电影文本模板`,
|
||||
'movie content template desc 1': `设置选择电影后导入的文本内容模板,`,
|
||||
'movie content template desc 2': `支持以下参数名称 :`,
|
||||
'movie content template desc 3': `{{id}}, {{type}}, {{title}}, {{originalTitle}},`,
|
||||
'movie content template desc 4': `{{score}}, {{datePublished}}, {{director}},`,
|
||||
'movie content template desc 5': `{{author}}, {{actor}}, {{desc}}, {{genre}},`,
|
||||
'movie content template desc 6': `{{image}}, {{url}}`,
|
||||
|
||||
'book content template': `书籍文本模板`,
|
||||
'book content template desc 1': `设置选择书籍后导入的文本内容模板,`,
|
||||
'book content template desc 2': `支持以下参数名称 :`,
|
||||
'book content template desc 3': `{{id}}, {{title}}, {{originalTitle}}, {{subTitle}},`,
|
||||
'book content template desc 4': `{{score}}, {{author}}, {{datePublished}}, {{type}},`,
|
||||
'book content template desc 5': `{{publish}}, {{desc}}, {{translator}}, {{isbn}},`,
|
||||
'book content template desc 6': `{{image}}, {{url}}, {{price}}, {{desc}}, {{totalPage}}`,
|
||||
|
||||
'music content template': `音乐文本模板`,
|
||||
'music content template desc 1': `设置选择音乐后导入的文本内容模板,`,
|
||||
'music content template desc 2': `支持以下参数名称 :`,
|
||||
'music content template desc 3': `{{id}}, {{title}}, {{actor}}, {{genre}},`,
|
||||
'music content template desc 4': `{{score}}, {{medium}}, {{datePublished}}, {{type}},`,
|
||||
'music content template desc 5': `{{publish}}, {{desc}}, {{albumType}}, {{barcode}},`,
|
||||
'music content template desc 6': `{{image}}, {{url}}, {{numberOfRecords}}, {{desc}}`,
|
||||
|
||||
'note content template': `日记文本模板`,
|
||||
'note content template desc 1': `设置选择日记后导入的文本内容模板,`,
|
||||
'note content template desc 2': `支持以下参数名称 :`,
|
||||
'note content template desc 3': `{{id}}, {{title}}, {{author}}, {{authorUrl}},`,
|
||||
'note content template desc 4': `{{timePublished}}, {{url}}, {{desc}}, {{type}},`,
|
||||
'note content template desc 5': `{{content}}`,
|
||||
|
||||
|
||||
'Date format': `参数日期格式`,
|
||||
'This format will be used when available template variables contain date.':
|
||||
`这个格式是给上面获取到的参数进行格式化日期时显示的内容 .`,
|
||||
|
||||
'DateTime format': `参数时间格式`,
|
||||
'This format will be used when available template variables contain dateTime.':
|
||||
`这个格式是给上面获取到的参数进行格式化时间时显示的内容 .`,
|
||||
'For more syntax, refer to': `详细介绍请参考`,
|
||||
'Your current syntax looks like this':`时间参数时间格式预览`,
|
||||
'format reference': `格式参考`,
|
||||
'Array Spilt String':`数组分割字符串`,
|
||||
'string to join between array type, such as author, actor':`当模板中的变量存在数组, 则需要设定数组元素中的分割符号,比如 演员列表等`,
|
||||
'Douban Request Headers':`豆瓣HTTP请求头`,
|
||||
'Douban Request Headers Desc': `如果豆瓣搜索或者获取数据失败,请尝试修改这个参数,\n
|
||||
参数获取方式为:\n
|
||||
1. 访问http://www.douban.com
|
||||
2. 复制请求头,仅复制以下请求头 `,
|
||||
'current version not support type': `暂时不支持该类型导入,请至github提交issuess获取帮助`,
|
||||
'Douban': `豆瓣网`,
|
||||
|
||||
'Person Name Language Mode':'人名显示模式',
|
||||
'options:':"可选项:",
|
||||
'Chinese Name mode, only show Chinese name':'中文名称模式, 人名只显示中文名',
|
||||
'English Name mode, only show English name':'英文名称模式, 人名只显示英文名',
|
||||
'Chinese English Name mode, show Chinese English name both':'中文和英文名称模式, 人名同时显示中文和英文名',
|
||||
'Chinese Name': '中文名',
|
||||
'English Name': '英文名',
|
||||
'Chinese And English Name': '中文名和英文名',
|
||||
|
||||
"Fetch Data Error": "获取数据失败,您如有需要请至Github提交Issues",
|
||||
"Obsidian Douban Plugin Error: ": "Obsidian Douban插件错误提示:",
|
||||
"Obsidian Douban Plugin Warn: ": "Obsidian Douban插件异常提示:",
|
||||
|
||||
}
|
||||
2539
package-lock.json
generated
2539
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -6,20 +6,24 @@
|
||||
"scripts": {
|
||||
"dev": "node esbuild.config.mjs",
|
||||
"build": "tsc -noEmit -skipLibCheck && node esbuild.config.mjs production",
|
||||
"version": "node version-bump.mjs && git add manifest.json versions.json"
|
||||
"version": "node version-bump.mjs && git add manifest.json versions.json",
|
||||
"test": "jest"
|
||||
},
|
||||
"keywords": [],
|
||||
"author": "",
|
||||
"license": "MIT",
|
||||
"devDependencies": {
|
||||
"@types/jest": "^28.1.4",
|
||||
"@types/node": "^16.11.6",
|
||||
"@typescript-eslint/eslint-plugin": "^5.2.0",
|
||||
"@typescript-eslint/parser": "^5.2.0",
|
||||
"builtin-modules": "^3.2.0",
|
||||
"esbuild": "0.13.12",
|
||||
"jest": "^28.1.2",
|
||||
"obsidian": "latest",
|
||||
"ts-jest": "^28.0.5",
|
||||
"tslib": "2.3.1",
|
||||
"typescript": "4.7.2"
|
||||
"typescript": "^4.7.2"
|
||||
},
|
||||
"dependencies": {
|
||||
"@notable/html2markdown": "^1.1.3",
|
||||
|
||||
@ -18,7 +18,9 @@
|
||||
"ES2021.String"
|
||||
],
|
||||
"outDir": "dist",
|
||||
|
||||
"paths": {
|
||||
"@App/*": ["src/douban/*"]
|
||||
}
|
||||
},
|
||||
"include": [
|
||||
"**/*.ts"
|
||||
|
||||
6
typings/tiny-network.d.ts
vendored
6
typings/tiny-network.d.ts
vendored
@ -1,6 +0,0 @@
|
||||
declare module 'tiny-network' {
|
||||
export function get(url:string, headers:any): any;
|
||||
export function get(url:string): any;
|
||||
export function readStream(param:any): any;
|
||||
export function ensureStatusCode(code:number): any;
|
||||
}
|
||||
@ -1,34 +0,0 @@
|
||||
import * as https from 'https';
|
||||
|
||||
import { get } from 'tiny-network';
|
||||
import { log } from './Logutil';
|
||||
|
||||
export default class HttpUtil {
|
||||
|
||||
static getHttps(url:string, options:any):Promise<any> {
|
||||
return new Promise<any>(
|
||||
function (resolve, reject) {
|
||||
https.get(url + '/', options, (response) => {
|
||||
console.log('url:', url + '/');
|
||||
console.log('statusCode:', response.statusCode);
|
||||
console.log('headers:', response.headers);
|
||||
if (response.statusCode === 200) {
|
||||
response.on('data', (d) => {
|
||||
resolve(d);
|
||||
});
|
||||
} if (response.statusCode === 301 || response.statusCode === 302 || response.statusCode == 303) {
|
||||
resolve(response.headers.location);
|
||||
} else {
|
||||
reject(new Error(response.statusMessage));
|
||||
}
|
||||
response.on('data', (d) => {
|
||||
process.stdout.write(d);
|
||||
});
|
||||
|
||||
}).on('error', (e) => {
|
||||
reject(new Error('XMLHttpRequest Error: ' + e.message));
|
||||
});
|
||||
|
||||
});
|
||||
}
|
||||
}
|
||||
@ -1,35 +0,0 @@
|
||||
import { Notice } from "obsidian";
|
||||
import SchemaOrg from "./SchemaOrg";
|
||||
import { i18nHelper } from "lang/helper";
|
||||
|
||||
class Logger {
|
||||
|
||||
public error(e:any):any {
|
||||
new Notice(i18nHelper.getMessage("Obsidian Douban Plugin Error:") + e);
|
||||
return e;
|
||||
}
|
||||
|
||||
public warn(e:any):any {
|
||||
new Notice(i18nHelper.getMessage("Obsidian Douban Plugin Warn:") + e);
|
||||
return e;
|
||||
}
|
||||
|
||||
public info(e:any):any {
|
||||
// console.log(`Douban Plugin info:` + `${typeof e == 'string' ? e : JSON.stringify(e)}`);
|
||||
return e;
|
||||
}
|
||||
|
||||
public trace(e:any):any {
|
||||
// return e;
|
||||
// console.log(`Douban Plugin trace:` + `${typeof e == 'string' ? e : JSON.stringify(e)}`);
|
||||
return e;
|
||||
}
|
||||
|
||||
public traceN(notion:string, e:any):any {
|
||||
// return e;
|
||||
// console.log(`${notion} ${typeof e == 'string' ? e : JSON.stringify(e)}`);
|
||||
return e;
|
||||
}
|
||||
}
|
||||
|
||||
export const log:Logger = new Logger();
|
||||
@ -1,25 +0,0 @@
|
||||
import { Person } from "schema-dts";
|
||||
|
||||
export default class SchemaOrg {
|
||||
public static getPersonName(p:Person):string {
|
||||
if(isString(p)) {
|
||||
return p;
|
||||
}else {
|
||||
let name: any = getProperty(p, 'name');
|
||||
return name + "";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
function isString(s:any): s is string {
|
||||
return typeof s === 'string';
|
||||
}
|
||||
|
||||
|
||||
function getProperty<T, K extends keyof T>(o: T, name: K): T[K] {
|
||||
return o[name];
|
||||
}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user