API:Вхід
Ця сторінка є частиною документації по MediaWiki Action API. |
API MediaWiki може вимагати від вашої програми або клієнта надання автентифікованих облікових даних користувача та входу для (a) запиту інформації або дій, що модифікують дані (b) для створення великих запитів із вищим обмеженням кількості запитів.
Два методи автентифікації
Є два способи автентифікації за допомогою MediaWiki Action API:
Метод 1. login
Боти та інші неінтерактивні програми повинні використовувати метод тільки для власників споживачів OAuth, якщо вони доступні, оскільки це безпечніше.
Якщо метод недоступний або незастосовний до клієнта, то можна використати дію login
з паролем бота.
Документація API
Приклад
Запит POST
Відповідь
{
"login": {
"lguserid": 21,
"result": "Success",
"lgusername": "William"
}
}
Приклад коду
MediaWiki JS
/*
login.js
MediaWiki API Demos
Demo of `Login` module: Sending request to login
MIT License
*/
var api = new mw.Api();
api.login( 'your_bot_username', 'your_bot_password' ).done( function ( data ) {
console.log( 'You are logged in as ' + data.login.lgusername );
} );
JavaScript
/*
edit.js
MediaWiki API Demos
Demo of `Login` module: Sending post request to login
MIT license
*/
var request = require( 'request' ).defaults( { jar: true } ),
url = 'https://test.wikipedia.org/w/api.php';
// Step 1: GET request to fetch login token
function getLoginToken() {
var params = {
action: 'query',
meta: 'tokens',
type: 'login',
format: 'json'
};
request.get( { url: url, qs: params }, function ( error, res, body ) {
var data;
if ( error ) {
return;
}
data = JSON.parse( body );
loginRequest( data.query.tokens.logintoken );
} );
}
// Step 2: POST request to log in.
// Use of main account for login is not
// supported. Obtain credentials via Special:BotPasswords
// (https://www.mediawiki.org/wiki/Special:BotPasswords) for lgname & lgpassword
function loginRequest( loginToken ) {
var params = {
action: 'login',
lgname: 'bot_username',
lgpassword: 'bot_password',
lgtoken: loginToken,
format: 'json'
};
request.post( { url: url, form: params }, function ( error, res, body ) {
if ( error ) {
return;
}
console.log( body );
} );
}
// Start From Step 1
getLoginToken();
PHP
<?php
/*
login.php
MediaWiki API Demos
Demo of `Login` module: Sending post request to login
MIT license
*/
$endPoint = "https://test.wikipedia.org/w/api.php";
$login_Token = getLoginToken(); // Step 1
loginRequest( $login_Token ); // Step 2
// Step 1: GET request to fetch login token
function getLoginToken() {
global $endPoint;
$params1 = [
"action" => "query",
"meta" => "tokens",
"type" => "login",
"format" => "json"
];
$url = $endPoint . "?" . http_build_query( $params1 );
$ch = curl_init( $url );
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
curl_setopt( $ch, CURLOPT_COOKIEJAR, "/tmp/cookie.txt" );
curl_setopt( $ch, CURLOPT_COOKIEFILE, "/tmp/cookie.txt" );
$output = curl_exec( $ch );
curl_close( $ch );
$result = json_decode( $output, true );
return $result["query"]["tokens"]["logintoken"];
}
// Step 2: POST request to log in. Use of main account for login is not
// supported. Obtain credentials via Special:BotPasswords
// (https://www.mediawiki.org/wiki/Special:BotPasswords) for lgname & lgpassword
function loginRequest( $logintoken ) {
global $endPoint;
$params2 = [
"action" => "login",
"lgname" => "your_bot_username",
"lgpassword" => "your_bot_password",
"lgtoken" => $logintoken,
"format" => "json"
];
$ch = curl_init();
curl_setopt( $ch, CURLOPT_URL, $endPoint );
curl_setopt( $ch, CURLOPT_POST, true );
curl_setopt( $ch, CURLOPT_POSTFIELDS, http_build_query( $params2 ) );
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
curl_setopt( $ch, CURLOPT_COOKIEJAR, "/tmp/cookie.txt" );
curl_setopt( $ch, CURLOPT_COOKIEFILE, "/tmp/cookie.txt" );
$output = curl_exec( $ch );
curl_close( $ch );
echo( $output );
}
Python
#!/usr/bin/python3
"""
login.py
MediaWiki API Demos
Demo of `Login` module: Sending post request to login
MIT license
"""
import requests
USERNAME = "your_bot_username"
PASSWORD = "your_bot_password"
S = requests.Session()
URL = "https://www.mediawiki.org/w/api.php"
# Retrieve login token first
PARAMS_0 = {
'action':"query",
'meta':"tokens",
'type':"login",
'format':"json"
}
R = S.get(url=URL, params=PARAMS_0)
DATA = R.json()
LOGIN_TOKEN = DATA['query']['tokens']['logintoken']
print(LOGIN_TOKEN)
# Send a post request to login. Using the main account for login is not
# supported. Obtain credentials via Special:BotPasswords
# (https://www.mediawiki.org/wiki/Special:BotPasswords) for lgname & lgpassword
PARAMS_1 = {
'action': "login",
'lgname': USERNAME,
'lgpassword': PASSWORD,
'lgtoken': LOGIN_TOKEN,
'format': "json"
}
R = S.post(URL, data=PARAMS_1)
DATA = R.json()
print(DATA)
assert DATA['login']['result'] == 'Success'
clientlogin
. Вхід у систему та збереження входу в систему вимагає, щоб ваш клієнт правильно обробляв файли cookie HTTP для всіх запитів. У наведеному вище прикладі Python ми показуємо, як об’єкт сеансу requests.Session()
допомагає зберігати файли cookie.
Можливі помилки
Код | Інформація |
---|---|
Failed | Введено неправильне ім’я користувача чи пароль. Будь ласка спробуйте ще раз. |
Failed | Unable to continue login. Your session most likely timed out. (or you are not correctly handling cookies). |
WrongToken | Надано недійсний токен |
NeedToken | `lgtoken` не наданий |
Aborted | Увійдіть, використовуючи пароль основного облікового запису, а не паролі бота. |
mustpostparams | Вказані параметри було знайдено в рядку запиту, але мають бути у тілі POST: $1. |
Метод 2. clientlogin
Інтерактивні програми, такі як користувацькі редактори або додатки для патрулювання, які надають послугу, не маючи наміру повністю замінити веб-сайт або мобільні програми, які мають на меті повністю замінити доступ до веб-інтерфейсу користувача, повинні використовувати дію clientlogin
.
Однак треба надавати перевагу використанню OAuth , якщо він доступний для автентифікації інструменту, оскільки він простіший і безпечніший.
Цей модуль доступний починаючи з MediaWiki 1.27.
Документація API
Приклад 1: Обробка вікі без спеціальних розширень автентифікації
Запит POST
Отримайте токен логіна у наведеному вище запиті через API:Токени .
Відповідь
{
"clientlogin":{
"status":"PASS",
"username":"William"
}
}
Приклад коду
clientlogin.py |
---|
#!/usr/bin/python3
"""
clientlogin.py
MediaWiki Action API Code Samples
Demo of `clientlogin` module: Sending post request to login
This demo app uses Flask (a Python web development framework).
MIT license
"""
import requests
from flask import Flask, render_template, flash, request
S = requests.Session()
URL = "https://en.wikipedia.org/w/api.php"
# App config.
DEBUG = True
APP = Flask(__name__)
APP.config.from_object(__name__)
APP.config['SECRET_KEY'] = 'enter_your_secret_key'
@APP.route("/", methods=['GET', 'POST'])
def show_form():
""" Render form template and handle form submission request """
if request.method == 'POST':
username = request.form['username']
password = request.form['password']
start_client_login(username, password)
return render_template('clientlogin_form.html')
def start_client_login(username, password):
""" Send a post request along with login token, user information
and return URL to the API to log in on a wiki """
login_token = fetch_login_token()
response = S.post(url=URL, data={
'action': "clientlogin",
'username': username,
'password': password,
'loginreturnurl': 'http://127.0.0.1:5000/',
'logintoken': login_token,
'format': "json"
})
data = response.json()
if data['clientlogin']['status'] == 'PASS':
flash('Login success! Welcome, ' + data['clientlogin']['username'] + '!')
else:
flash('Oops! Something went wrong -- ' + data['clientlogin']['messagecode'])
def fetch_login_token():
""" Fetch login token via `tokens` module """
response = S.get(
url=URL,
params={
'action': "query",
'meta': "tokens",
'type': "login",
'format': "json"})
data = response.json()
return data['query']['tokens']['logintoken']
if __name__ == "__main__":
APP.run()
|
form.html |
---|
<!DOCTYPE html>
<title>MediaWiki Log in</title>
<link rel="stylesheet" href="static/bootstrap/css/bootstrap.min.css">
<div class="container">
<h2>MediaWiki Log in</h2>
<form action="" method="post" role="form">
<div class="form-group">
<div class="form-field">
<div class="label-field">Username</div>
<input name="username">
</div>
<div class="form-field">
<div class="label-field">Password</div>
<input type="password" name="password">
</div>
</div>
<button type="submit" class="btn btn-success">Log in</button>
</form>
<br>
{% with messages = get_flashed_messages(with_categories=true) %}
{% if messages %}
{% for message in messages %}
<div class="alert alert-info">
{{ message[1] }}
</div>
{% endfor %}
{% endif %}
{% endwith %}
</div>
<br>
</div>
</div>
|
Приклад 2: Обробка вікі з спеціальними розширеннями автентифікації
Вікі зі спеціальними розширеннями автентифікації, такими як ConfirmEdit (капчі), OpenID Connect , OATHAuth (двофакторна автентифікація), може мати складніший процес автентифікації. У цьому разі можуть також знадобитися конкретні поля, опис яких можна отримати з запиту API:Authmanagerinfo .
Step 1: Answer the Captcha and select OpenID authentication
This documentation is an example and does not reflect the behavior of any specific currently-available OpenID extension.
redirecttarget
. The OpenID provider would authenticate, and redirect to Special:OpenIDConnectReturn on the wiki, which would validate the OpenID response and then redirect to the loginreturnurl
provided in the first POST to the API with the code
and state
parameters added. У цей час клієнт знову отримує контроль над процесом і виконує наступний запит до API.Відповідь |
---|
{
"clientlogin": {
"status": "REDIRECT",
"redirecttarget": "https://openid.example.net/openid-auth.php?scope=openid&response_type=code&client_id=ABC&redirect_uri=https://wiki.example.org/wiki/Special:OpenIDConnectReturn&state=XYZ123",
"requests": [
{
"id": "OpenIdConnectResponseAuthenticationRequest",
"metadata": {},
"required": "required",
"provider": "OpenID Connect at example.net",
"account": "",
"fields": {
"code": {
"type": "string",
"label": "OpenID Code",
"help": "OpenID Connect code response"
},
"state": {
"type": "string",
"label": "OpenID State",
"help": "OpenID Connect state response"
},
}
}
]
}
}
|
Step 2: Back from OpenID
Відповідь |
---|
{
"clientlogin": {
"status": "UI",
"message": "Two-factor authentication",
"requests": [
{
"id": "TwoFactorAuthenticationRequest",
"metadata": {},
"required": "required",
"provider": "",
"account": "",
"fields": {
"code": {
"type": "string",
"label": "Code",
"help": "Two-factor authentication code"
}
}
}
]
}
}
|
Step 3: Two-factor authentication
RESTART
response, for example if the OpenID Connect extension had no mapping for the OpenID account to any local user. In this case the client might restart the login process from the beginning or might switch to account creation, in either case passing the loginpreservestate
or createpreservestate
parameter to preserve some state.Відповідь |
---|
{
"clientlogin": {
"status": "PASS",
"username": "Alice"
}
}
|
Додаткові примітки
- На вікі, які дозволяють анонімне редагування, можна редагувати за допомогою API без входу, але настійно рекомендується ввійти в систему. На приватних вікі вхід необхідний, щоб використовувати будь-яку функціональність API.
- Рекомендується створити окремий обліковий запис користувача для вашої програми. Це особливо важливо, якщо ваш додаток виконує автоматичне редагування або викликає великі запити, що вимагають великої продуктивності. Завдяки цьому легко відстежувати зміни, внесені програмою, та застосовувати спеціальні права до облікового запису програми. This is especially important if your application is carrying out automated editing or invoking large or performance-intensive queries. With that, it is easy to track changes made by the application and apply special rights to the application's account.
- Якщо ви надсилаєте запит, який повинен зробити зареєстрований користувач, додайте параметр
assert=user
до запиту, який ви надсилаєте, щоб перевірити, чи ввійшов користувач. Якщо користувач не ввійшов у систему, буде повернуто код помилкиassertuserfailed
. See API:Стверджувати for details. - Щоб перевірити, чи має обліковий запис права бота, додайте до запиту параметр
assert=bot
. Якщо обліковий запис не має прав бота, буде повернуто код помилкиassertbotfailed
. See API:Стверджувати for details.
Див. також
- API:Вихід
- API:Userinfo - Повертає інформацію про поточного користувача, який увійшов до системи
- Interactive login with action=clientlogin in mwapi