hackerone-api 0.2.0

Unofficial, dependency-light Rust client for the HackerOne API (v1): submit reports, read your reports, hacktivity, balance, and earnings.
Documentation
//! # hackerone-api
//!
//! Unofficial, dependency-light Rust client for the [HackerOne API][api] (v1).
//!
//! Built for the boring, reliable half of bug-bounty tooling: sign in, browse
//! your programs and their scopes, read your reports, **submit** a report,
//! search hacktivity, and read your balance and earnings — with HTTP Basic
//! auth and no async runtime.
//!
//! ## Hacker surface
//!
//! Report *submission* is a **hacker** operation. It lives under
//! `/v1/hackers/…`, not the customer `/v1/reports` surface. These endpoints
//! work with a researcher's API token:
//!
//! | Method | Endpoint |
//! |---|---|
//! | [`Client::create_report`] | `POST /v1/hackers/reports` |
//! | [`Client::my_reports`] | `GET /v1/hackers/me/reports` |
//! | [`Client::my_report`] | `GET /v1/hackers/reports/{id}` |
//! | [`Client::hacktivity`] | `GET /v1/hackers/hacktivity` |
//! | [`Client::balance`] | `GET /v1/hackers/payments/balance` |
//! | [`Client::earnings`] | `GET /v1/hackers/payments/earnings` |
//!
//! ## Customer surface
//!
//! [`Client::me`], [`Client::programs`], [`Client::program`],
//! [`Client::structured_scopes`], [`Client::reports`], [`Client::report`],
//! [`Client::add_comment`], [`Client::change_state`] and
//! [`Client::weaknesses`] are the **customer/program** API. A hacker-only API
//! token receives `401` on those routes (they require program access), even
//! though the token is valid.
//!
//! ## Submit a report
//!
//! ```no_run
//! use hackerone_api::{Client, CreateHackerReport, SeverityRating};
//!
//! fn main() -> Result<(), hackerone_api::Error> {
//!     let client = Client::new("api-identifier", "api-token");
//!
//!     let report = CreateHackerReport::new("sec", "Stored XSS in the profile page")
//!         .vulnerability_information("## Steps\n1. …")
//!         .impact("Session theft for any user who views the profile.")
//!         .severity(SeverityRating::High)
//!         .weakness_id(1337)
//!         .structured_scope_id(57);
//!
//!     let created = client.create_report(&report)?;
//!     println!("filed: {} [{}]", created.title.unwrap_or_default(), created.state.unwrap_or_default());
//!     Ok(())
//! }
//! ```
//!
//! The created report's numeric id is returned on the response envelope's
//! `data.id`; [`Client::create_report`] returns the report attributes
//! ([`Report`]), matching [`Client::report`]. To read ids for existing
//! reports, use [`Client::my_reports`] and [`Page::ids`].
//!
//! ## Auth
//!
//! The API uses HTTP Basic auth: the *username* is your API token
//! **identifier** and the *password* is the token **value**. Create one in
//! your HackerOne account settings. The examples read them from the
//! `HACKERONE_API_IDENTIFIER` / `HACKERONE_API_TOKEN` environment variables.
//!
//! ## Design
//!
//! - **Blocking, no async runtime.** [`ureq`] under the hood.
//! - **Injectable transport.** The client is generic over [`Transport`], so
//!   tests use a mock and embedders can swap the HTTP stack.
//! - **Forward-compatible types.** Domain structs keep the documented fields
//!   and stash unknown ones in a flattened `extra` map.
//!
//! ## Disclaimer
//!
//! This crate is unofficial and not affiliated with or endorsed by
//! HackerOne. "HackerOne" is a trademark of its owner; the name is used only
//! to describe what the library talks to.
//!
//! [api]: https://api.hackerone.com/

#![forbid(unsafe_code)]
#![warn(missing_docs)]

mod client;
mod error;
mod transport;
mod types;

pub use client::{Client, DEFAULT_BASE_URL};
pub use error::{ApiError, Error, Result};
pub use transport::{Method, Request, Response, Transport, UreqTransport};
pub use types::{
    Balance, CollectionDoc, CreateHackerReport, DataDoc, Earning, Hacktivity, HacktivityQuery,
    Links, Meta, Page, PageQuery, Program, Report, ReportQuery, ReportState, Resource, Severity,
    SeverityRating, SingleDoc, StructuredScope, User, Weakness,
};