我正在尝试API:Login文档中描述的Wikipedia客户端登录流程,但发生了一些错误:1)我正确地得到了一个用 HTTP GET 引发的令牌https://en.wikipedia.org/w/api.php?action=query&meta=tokens&type=login&format=json我得到一个有效的logintoken字符串。2.1)然后我尝试clientlogin类似:HTTP POST /w/api.php?action=clientlogin&format=json&lgname=xxxx&lgtoken=xxxx%2B%5CPOST BODY 是
{ "lgpassword" : "xxxxx", "lgtoken" : "xxxxx" }
但我收到一个错误:
{ "error": { "code": "notoken", "info": "The \"token\" parameter must be set." }, "servedby": "mw1228" }
如果我尝试更改lgtoken为token我得到相同的结果。
2.2) 然后我尝试了旧方法 ieaction=login并传递正文,但它不起作用,因为它给了我另一个登录令牌:HTTP POSThttps://en.wikipedia.org/w/api.php?action=login&format=json&lgname=xxxx和相同的POST BODY然后我得到
{ "warnings": {} }, "login": { "result": "NeedToken", "token": "xxxxx+\\" }
当文档在这里指出,NeedToken if the lgtoken parameter was not provided or no session was active (e.g. your cookie handling is broken).但我已经通过了lgtokenjson 正文中的 。我正在使用Node.js和内置http模块,它应该以Cookies正确的方式传递和保持会话(使用其他 api 可以正常工作)。我在这里的 LrMediaWiki 客户端上发现了类似的问题。[更新] 这是我目前的实现:
Wikipedia.prototype.loginUser = function (username, password) { var self = this; return new Promise((resolve, reject) => { var cookies = self.cookies({}); var headers = { 'Cookie': cookies.join(';'), 'Accept': '*/*', 'User-Agent': self.browser.userAgent() }; // fetch login token self.api.RequestGetP('/w/api.php', headers, { action: 'query', meta: 'tokens', type: 'login', format: 'json' }) .then(response => { // success if (response.query && response.query.tokens && response.query.tokens['logintoken']) { self.login.logintoken = response.query.tokens['logintoken']; self.logger.info("Wikipedia.login token:%s", self.login); return self.api.RequestPostP('/w/api.php', headers, { action: 'login', format: 'json', lgname: username }, { lgpassword: password, lgtoken: self.login.logintoken }); } else { var error = new Error('no logintoken'); return reject(error); } }) .then(response => { // success return resolve(response); }) .catch(error => { // error self.logger.error("Wikipedia.login error%s\n%@", error.message, error.stack); return reject(error); }); }); }//loginUser
哪里this.api是 Node.js http 的简单包装器,源代码可在此处获得,API 签名如下:
Promise:API.RequestGetP(url,headers,querystring) Promise:API.RequestPostP(url,headers,querystring,body)