aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ext/bg/js/ankiweb.js26
-rw-r--r--ext/manifest.json2
2 files changed, 20 insertions, 8 deletions
diff --git a/ext/bg/js/ankiweb.js b/ext/bg/js/ankiweb.js
index 6a45b9c5..69a1b44d 100644
--- a/ext/bg/js/ankiweb.js
+++ b/ext/bg/js/ankiweb.js
@@ -47,7 +47,8 @@ class AnkiWeb {
const data = {
data: JSON.stringify([fields, note.tags.join(' ')]),
mid: model.id,
- deck: note.deckName
+ deck: note.deckName,
+ csrf_token: info.token
};
return AnkiWeb.loadAccountPage('https://ankiweb.net/edit/save', data, this.username, this.password);
@@ -78,8 +79,8 @@ class AnkiWeb {
return Promise.resolve(this.noteInfo);
}
- return AnkiWeb.scrape(this.username, this.password).then(({deckNames, models}) => {
- this.noteInfo = {deckNames, models};
+ return AnkiWeb.scrape(this.username, this.password).then(({deckNames, models, token}) => {
+ this.noteInfo = {deckNames, models, token};
return this.noteInfo;
});
}
@@ -100,8 +101,14 @@ class AnkiWeb {
return Promise.reject('failed to scrape deck data');
}
+ const tokenMatch = /editor\.csrf_token = \'(.*)\';/.exec(response);
+ if (tokenMatch === null) {
+ return Promise.reject('failed to acquire csrf_token');
+ }
+
const modelsJson = JSON.parse(modelsMatch[1]);
const decksJson = JSON.parse(decksMatch[1]);
+ const token = tokenMatch[1];
const deckNames = Object.keys(decksJson).map(d => decksJson[d].name);
const models = [];
@@ -113,16 +120,16 @@ class AnkiWeb {
});
}
- return {deckNames, models};
+ return {deckNames, models, token};
});
}
- static login(username, password) {
+ static login(username, password, token) {
if (username.length === 0 || password.length === 0) {
return Promise.reject('login credentials not specified');
}
- const data = {username, password, submitted: 1};
+ const data = {username, password, csrf_token: token, submitted: 1};
return AnkiWeb.loadPage('https://ankiweb.net/account/login', data).then(response => {
if (!response.includes('class="mitem"')) {
return Promise.reject('failed to authenticate');
@@ -133,7 +140,12 @@ class AnkiWeb {
static loadAccountPage(url, data, username, password) {
return AnkiWeb.loadPage(url, data).then(response => {
if (response.includes('name="password"')) {
- return AnkiWeb.login(username, password).then(() => AnkiWeb.loadPage(url, data));
+ const tokenMatch = /name="csrf_token" value="(.*)"/.exec(response);
+ if (tokenMatch === null) {
+ return Promise.reject('failed to acquire csrf_token');
+ }
+
+ return AnkiWeb.login(username, password, tokenMatch[1]).then(() => AnkiWeb.loadPage(url, data));
} else {
return response;
}
diff --git a/ext/manifest.json b/ext/manifest.json
index c7c1ffa9..e1c1b7a9 100644
--- a/ext/manifest.json
+++ b/ext/manifest.json
@@ -1,7 +1,7 @@
{
"manifest_version": 2,
"name": "Yomichan",
- "version": "1.0.1",
+ "version": "1.0.2",
"description": "Japanese dictionary with Anki integration",
"icons": {"16": "img/icon16.png", "48": "img/icon48.png", "128": "img/icon128.png"},