JavaScript
Node.js
npm
mediawiki

npmにあるMediaWikiライブラリまとめ

MediaWikiを巡回して記事名の読みがなをソートキーに追加するBotを作った時に、node.jsのMediaWiki APIライブラリを探していくつか触ったのでそのメモです。

  • npmにあるもの限定です
  • 部内Wikiで使える必要があったため、Wikipedia専用のものは除外しました

環境

  • macOS 10.12.5
  • node.js v8.1.4
  • npm v5.3.0

使用例について

ライブラリごとの使用感を比べるために、処理内容は全て統一しています。
1. 日本語版ウィキペディアの「ウィキペディア」という記事の所属カテゴリを取得する
2. 同記事の内容を取得する

サンプルコードとしては、各ライブラリのREADMEやドキュメントの方を参考にしていただければと思います。

dijs/wikijs

一番人気があった(月間1000ダウンロード)ライブラリ。

記事の検索や記事情報の取得などができます。デフォルトでは英語版Wikipedia用ですが、apiUrlというオプションにapi.phpのURLを渡せば他のMediaWikiでも使えます。

ただ、ログインや編集ができないため、閲覧にもログインが必要なWikiでは一切使えませんでした。

インストール

npm i wikijs

使用例

const wiki = require('wikijs').default({
  apiUrl : 'http://ja.wikipedia.org/w/api.php'
});

(async() => {
  const page = await wiki.page('ウィキペディア');
  const categories = await page.categories();
  console.log(categories);
  const content = await page.content();
  console.log(content);
})();

pageオブジェクトのメンバを呼ぶことで追加の情報を取得できます。
かなりシンプルに書けるので、情報取得が主目的であれば大いにお勧めです。

macbre/nodemw

MediaWiki公式のクライアント紹介にも載っているライブラリ。実際のWikiでの運用実績もあるとのこと。

ログイン、記事の取得や編集、ファイルアップロードなど機能は圧倒的に豊富です。使用例で使っていませんが、client.api.call()直接APIを呼ぶこともできるため、MediaWiki APIの全機能を使えることになります。

ただ、各メソッドがコールバック形式で、そのまま使うとコールバック地獄に落ちます。util.promisify()などで対策しましょう。

インストール

npm i nodemw

使用例

const nodemw = require('nodemw');
const util = require('util'); // for util.promisify

const client = new nodemw({
  server : 'ja.wikipedia.org',
  path : 'w/'
});

(async() => {
  const categories = await util.promisify(client.getArticleCategories).bind(client) ('ウィキペディア');
  console.log(categories);
  const content = await util.promisify(client.getArticle).bind(client) ('ウィキペディア');
  console.log(content);
})();

promisifyのせいで長くなっていますが、込み入ったことはしていません。

Fannon/mwbot

nodemwと同等かそれ以上に豊富な機能を持ちます。
MediaWiki APIの直接指定により、nodemw同様にAPIの全機能を使うことができます

Promiseにも対応しておりnodemwよりも使いやすい印象でした。強いて言えば、APIのレスポンスそのままを返してくるので、結果を読み取るのに一手間かかる(使用例参照)のが残念です。

インストール

npm i mwbot

使用例

const MWBot = require('mwbot');
const bot = new MWBot({
  apiUrl : 'https://ja.wikipedia.org/w/api.php'
});

(async() => {
  let res, pages;
  res = await bot.request({ action : 'query', prop : 'categories', titles : 'ウィキペディア' , cllimit : 100 });
  pages = Object.values(res.query.pages);
  console.log(pages[0].categories);

  res = await bot.read('ウィキペディア');
  pages = Object.values(res.query.pages);
  console.log(pages[0].revisions[0]['*']);
})();

カテゴリ一覧の専用メソッドがないので、bot.requestで直接APIのオプションを指定しました。
カテゴリはAPIのレスポンスのquery.pages[{ページID}].categoriesに埋まっています。
リファレンスを読みつつ取り出しましょう。

oliver-moran/mediawiki

MediaWiki APIのメソッドを直接指定できます。
また、よく使うメソッドには専用の関数も用意されています。

Queued requstsという機能でリクエストの間隔を勝手に開けてくれますが、デフォルトの6秒は流石に長いのでオプションで短めにします。
async/awaitが使えればよかったものの、Promiseを自前で実装しているため無理でした。

最終コミットが2014年とかなり古く、今あえて選ぶ理由はなさそうです。

インストール

npm i mediawiki

使用例

const MediaWiki = require('mediawiki');
const bot = new MediaWiki.Bot({
  endpoint: 'https://ja.wikipedia.org/w/api.php',
  rate: 5e2, // Queued requsts rate
  userAgent: 'ExampleBot',
  byeline: '(example bot edit)'
});

bot.get({ action : 'query', prop : 'categories', titles : 'ウィキペディア' , cllimit : 100 }).complete((res) => {
  const pages = Object.values(res.query.pages);
  console.log(pages[0].categories);
});
bot.page('ウィキペディア').complete((title, text, date) => {
  console.log(text);
});

APIを直接指定する場合は、mwbot同様無加工のレスポンスが返ります。

まとめ

このほかにもMediaWiki用のライブラリと称するものはいくつかありますが、正常に動作しない・人気(npmサイトに表示されるDL数)がなさすぎるといった理由で省略しました。

記事などを取得・検索できるだけでいいなら、wikijsを使うのが最も楽です。
ログインや編集ができる必要がある場合は、機能がしっかりしているnodemwmwbotを推奨します。

いずれも一長一短あるので、選定する前にやりたい処理がそのライブラリで可能かどうか確認しておくのが良さそうです。