mwapi_responses 0.5.1

Automatically generate strict types for MediaWiki API responses
Documentation
# mwapi_responses

[![crates.io](https://img.shields.io/crates/v/mwapi_responses.svg)](https://crates.io/crates/mwapi_responses)
[![docs.rs](https://img.shields.io/docsrs/mwapi_responses?label=docs.rs)](https://docs.rs/mwapi_responses)
[![docs (main)](https://img.shields.io/badge/doc.wikimedia.org-green?label=docs%40main)](https://doc.wikimedia.org/mwbot-rs/mwbot/mwapi_responses/)
[![pipeline status](https://gitlab.wikimedia.org/repos/mwbot-rs/mwbot/badges/main/pipeline.svg)](https://gitlab.wikimedia.org/repos/mwbot-rs/mwbot/-/commits/main)
[![coverage report](https://img.shields.io/endpoint?url=https%3A%2F%2Fdoc.wikimedia.org%2Fcover%2Fmwbot-rs%2Fmwbot%2Fcoverage%2Fcoverage.json)](https://doc.wikimedia.org/cover/mwbot-rs/mwbot/coverage)

The `mwapi_responses` crate provides strict typing for dynamic MediaWiki
Action API queries. The goal is to faithfully represent what the API's
JSON structure is while saving people from manually writing out
serde-compatible structs for every query.

A list module:
```rust
use mwapi_responses::prelude::*;
#[query(
    list = "logevents",
    leaction = "newusers/create",
    leprop = "user|type",
    lelimit = "100"
)]
struct Response;
```

This creates a `Response` struct that matches the API response for the given
query. Roughly, it will expand to:

```rust
#[derive(Debug, Clone, serde::Deserialize)]
pub struct Response {
    #[serde(default)]
    pub batchcomplete: bool,
    #[serde(rename = "continue")]
    #[serde(default)]
    pub continue_: HashMap<String, String>,
    pub query: ResponseBody,
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct ResponseBody {
    pub logevents: Vec<ResponseItemlogevents>,
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct ResponseItemlogevents {
    pub user: String,
    #[serde(rename = "type")]
    pub type_: String,
}
```

Or getting various properties from pages:
```rust
use mwapi_responses::prelude::*;
#[query(
    prop="info|revisions",
    inprop="url",
    rvprop="ids"
)]
struct Response;
```
which expands to:
```rust
#[derive(Debug, Clone, serde::Deserialize)]
pub struct Response {
    #[serde(default)]
    pub batchcomplete: bool,
    #[serde(rename = "continue")]
    #[serde(default)]
    pub continue_: HashMap<String, String>,
    pub query: ResponseBody,
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct ResponseBody {
    pub pages: Vec<ResponseItem>,
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct ResponseItem {
    pub canonicalurl: String,
    pub contentmodel: String,
    pub editurl: String,
    pub fullurl: String,
    pub lastrevid: Option<u64>,
    pub length: Option<u32>,
    #[serde(default)]
    pub missing: bool,
    #[serde(default)]
    pub new: bool,
    pub ns: i32,
    pub pageid: Option<u32>,
    pub pagelanguage: String,
    pub pagelanguagedir: String,
    pub pagelanguagehtmlcode: String,
    #[serde(default)]
    pub redirect: bool,
    pub title: String,
    pub touched: Option<String>,
    #[serde(default)]
    pub revisions: Vec<ResponseItemrevisions>,
}

#[derive(Debug, Clone, serde::Deserialize)]
pub struct ResponseItemrevisions {
    pub parentid: u64,
    pub revid: u64,
}
```

In both cases, you can easily iterate over `ResponseItemlogevents`
and `ResponseItem` respectively by calling `Response::items()`.

To avoid repeating the parameters in multiple places, you can call
`Response::params()` to get a `&[(&str, &str)]` of the parameters that
were provided to the `#[query(...)]` macro.

Fields are renamed if they can't be used as fields in Rust, like `continue`
or `type`. In these cases, an underscore is appended.

### Supported modules
The metadata that powers this crate is manually gathered. To see if
a specific module is supported, look at the [Git repository](https://gitlab.wikimedia.org/repos/mwbot-rs/mwbot/-/tree/main/mwapi_responses_derive/data).
Contributions for missing modules or parameters are always welcome.

### Library agnostic
This crate does not implement or support any one specific API or HTTP
library, rather it aims to just provide types and helpers to enable you to
run and execute your API requests however you'd like.

The [`mwapi`](https://docs.rs/mwapi) crate provides a convenience function
to execute a query using these generated responses: `query_response()`.

### Future plans
There is no special support for continuing queries. In the future some
merge()-like function might be provided.

Some other ideas are outlined in [a blog post by Legoktm](https://blog.legoktm.com/2021/11/01/generating-rust-types-for-mediawiki-api-responses.html).

### Contributing
`mwapi_responses` is a part of the [`mwbot-rs` project](https://www.mediawiki.org/wiki/Mwbot-rs).
We're always looking for new contributors, please [reach out](https://www.mediawiki.org/wiki/Mwbot-rs#Contributing)
if you're interested!

## License
This crate is released under GPL-3.0-or-later.
See [COPYING](./COPYING) for details.