mwapi/lib.rs
1/*
2Copyright (C) 2021 Kunal Mehta <legoktm@debian.org>
3
4This program is free software: you can redistribute it and/or modify
5it under the terms of the GNU General Public License as published by
6the Free Software Foundation, either version 3 of the License, or
7(at your option) any later version.
8
9This program is distributed in the hope that it will be useful,
10but WITHOUT ANY WARRANTY; without even the implied warranty of
11MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12GNU General Public License for more details.
13
14You should have received a copy of the GNU General Public License
15along with this program. If not, see <https://www.gnu.org/licenses/>.
16 */
17
18//! A MediaWiki API client library.
19//!
20//! `mwapi` is a low-level library for the [MediaWiki Action API](https://www.mediawiki.org/wiki/API:Main_page).
21//! If you intend to edit pages or want a higher-level interface, it's recommended to use [`mwbot`](https://docs.rs/mwbot/),
22//! which builds on top of this crate.
23//!
24//! ## Goals
25//! * generic to fit any application, whether for interactive usage
26//! or writing a bot
27//! * fully compatible with concurrent use cases
28//! * turns MediaWiki errors into Rust errors for you
29//! * logging (using the `tracing` crate) for visiblity into errors
30//! * follow all [best practices](https://www.mediawiki.org/wiki/API:Etiquette)
31//!
32//! ## Quick start
33//! ```
34//! # #[tokio::main]
35//! # async fn main() -> mwapi::Result<()> {
36//! let client = mwapi::Client::builder("https://en.wikipedia.org/w/api.php")
37//! .set_user_agent("mwapi demo")
38//! // Provide credentials for login:
39//! // .set_botpassword("username", "password")
40//! .build().await?;
41//! let resp = client.get_value(&[
42//! ("action", "query"),
43//! ("prop", "info"),
44//! ("titles", "Taylor Swift"),
45//! ]).await?;
46//! let info = resp["query"]["pages"][0].clone();
47//! assert_eq!(info["ns"].as_u64().unwrap(), 0);
48//! assert_eq!(info["title"].as_str().unwrap(), "Taylor Swift");
49//! # Ok(())
50//! # }
51//!
52//! ```
53//!
54//! ## Functionality
55//! * authentication, using [OAuth2](https://www.mediawiki.org/wiki/OAuth/Owner-only_consumers#OAuth_2) (recommended) or BotPasswords
56//! * error handling, transforming MediaWiki errors into Rust ones
57//! * CSRF [token](https://www.mediawiki.org/wiki/API:Tokens) handling with `post_with_token`
58//! * rate limiting and concurrency controls
59//! * file uploads (needs `upload` feature)
60//!
61//! ## See also
62//! * [`mwbot`](https://docs.rs/mwbot/) provides a higher level interface to
63//! interacting with MediaWiki
64//! * [`mwapi_responses`](https://docs.rs/mwapi_responses/) is a macro to
65//! generate strict types for dynamic API queries
66//!
67//! ## Contributing
68//! `mwapi` is a part of the [`mwbot-rs` project](https://www.mediawiki.org/wiki/Mwbot-rs).
69//! We're always looking for new contributors, please [reach out](https://www.mediawiki.org/wiki/Mwbot-rs#Contributing)
70//! if you're interested!
71#![deny(clippy::all)]
72#![deny(rustdoc::all)]
73#![cfg_attr(docsrs, feature(doc_cfg))]
74
75mod client;
76mod error;
77mod params;
78mod responses;
79mod time;
80mod tokens;
81#[cfg(feature = "upload")]
82mod upload;
83
84const VERSION: &str = env!("CARGO_PKG_VERSION");
85
86pub use client::{Builder, Client, HttpClientProvider};
87pub use error::{ApiError, Error};
88pub use params::Params;
89use std::fmt::{Display, Formatter};
90
91pub type Result<T> = std::result::Result<T, Error>;
92
93/// Assert that your account has the specified login state, see
94/// [API:Assert](https://www.mediawiki.org/wiki/API:Assert) for more details.
95#[derive(Copy, Clone, Debug, Eq, PartialEq)]
96pub enum Assert {
97 /// Not logged in, aka anonymous
98 Anonymous,
99 /// Logged in to a bot account
100 Bot,
101 /// Logged in (to any account)
102 User,
103 /// Do not add any assert
104 None,
105}
106
107impl Assert {
108 fn value(&self) -> Option<&'static str> {
109 match self {
110 Assert::Anonymous => Some("anon"),
111 Assert::Bot => Some("bot"),
112 Assert::User => Some("user"),
113 Assert::None => None,
114 }
115 }
116}
117
118impl Default for Assert {
119 fn default() -> Self {
120 Self::None
121 }
122}
123
124#[derive(Clone, Copy, Debug)]
125pub enum ErrorFormat {
126 Html,
127 Wikitext,
128 Plaintext,
129}
130
131impl Display for ErrorFormat {
132 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
133 let val = match &self {
134 ErrorFormat::Html => "html",
135 ErrorFormat::Wikitext => "wikitext",
136 ErrorFormat::Plaintext => "plaintext",
137 };
138 write!(f, "{val}")
139 }
140}
141
142impl Default for ErrorFormat {
143 fn default() -> Self {
144 Self::Plaintext
145 }
146}
147
148#[derive(Debug, Copy, Clone, Eq, PartialEq)]
149pub(crate) enum Method {
150 Get,
151 Post,
152}