Skip to content

Commit de7a424

Browse files
committed
docs(readme): expand usage, features, and examples; update install guide
chore(ci): add publish step for hpx-transport and index wait
1 parent a79a520 commit de7a424

2 files changed

Lines changed: 198 additions & 13 deletions

File tree

.github/workflows/release.yml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,3 +73,11 @@ jobs:
7373
run: cargo publish -p hpx-util
7474
env:
7575
CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
76+
77+
- name: Wait for index update
78+
run: sleep 30
79+
80+
- name: Publish hpx-transport
81+
run: cargo publish -p hpx-transport
82+
env:
83+
CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}

README.md

Lines changed: 190 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -14,14 +14,18 @@ An ergonomic all-in-one HTTP client for browser emulation with TLS, JA3/JA4, and
1414
## Features
1515

1616
- **Browser Emulation**: Simulate various browser TLS/HTTP2 fingerprints (JA3/JA4).
17-
- **Content Handling**: Plain bodies, JSON, urlencoded, multipart.
17+
- **Content Handling**: Plain bodies, JSON, urlencoded, multipart, streaming.
1818
- **Advanced Features**:
1919
- Cookies Store
2020
- Redirect Policy
2121
- Original Header Preservation
2222
- Rotating Proxies
2323
- Certificate Store
2424
- Tower Middleware Support
25+
- Request/Response Hooks
26+
- Retry Configuration
27+
- Compression (gzip, brotli, deflate, zstd)
28+
- Character Encoding Support
2529
- **WebSocket**: Upgrade support for WebSockets.
2630
- **TLS Backends**: Support for both BoringSSL (default) and Rustls.
2731

@@ -30,10 +34,10 @@ An ergonomic all-in-one HTTP client for browser emulation with TLS, JA3/JA4, and
3034
```text
3135
+-----------------------------------------------------------+
3236
| User API |
33-
| (HpxClient, HpxBuilder, RequestBuilder, WsConnection) |
37+
| (Client, ClientBuilder, RequestBuilder, Response) |
3438
+-----------------------------------------------------------+
3539
| Tower Middleware Stack |
36-
| (AuthLayer, RetryLayer, TimeoutLayer, DecompressionLayer) |
40+
| (HooksLayer, RetryLayer, TimeoutLayer, DecompressionLayer)|
3741
+---------------------------+-------------------------------+
3842
| hpx-core | hpx-ws (fastwebsockets) |
3943
+---------------------------+ |
@@ -47,12 +51,35 @@ An ergonomic all-in-one HTTP client for browser emulation with TLS, JA3/JA4, and
4751

4852
## Installation
4953

50-
Add `hpx` to your `Cargo.toml`:
54+
Add `hpx` and related crates to your `Cargo.toml`:
5155

5256
```toml
5357
[dependencies]
54-
hpx = "0.1.0"
55-
hpx-util = "0.1.0"
58+
hpx = "0.1.4"
59+
hpx-util = "0.1.4"
60+
hpx-transport = "0.1.4" # Optional: for transport layer access
61+
```
62+
63+
### Feature Flags
64+
65+
`hpx` provides extensive feature flags for customization:
66+
67+
```toml
68+
[dependencies]
69+
hpx = { version = "0.1.4", features = [
70+
"json", # JSON request/response support
71+
"stream", # Streaming request/response bodies
72+
"cookies", # Cookie store support
73+
"charset", # Character encoding support
74+
"gzip", # Gzip compression
75+
"brotli", # Brotli compression
76+
"zstd", # Zstandard compression
77+
"multipart", # Multipart form data
78+
"ws", # WebSocket support
79+
"socks", # SOCKS proxy support
80+
"hickory-dns", # Alternative DNS resolver
81+
"tracing", # Logging support
82+
] }
5683
```
5784

5885
## TLS Backend Configuration
@@ -101,21 +128,128 @@ async fn main() -> hpx::Result<()> {
101128
}
102129
```
103130

104-
### Browser Emulation
105-
106-
The `emulation` module allows you to simulate specific browser fingerprints.
131+
### JSON Requests
107132

108133
```rust
109-
use hpx_util::Emulation;
134+
use serde::{Deserialize, Serialize};
135+
136+
#[derive(Serialize, Deserialize, Debug)]
137+
struct User {
138+
name: String,
139+
email: String,
140+
}
110141

111142
#[tokio::main]
112143
async fn main() -> hpx::Result<()> {
113-
let resp = hpx::get("https://tls.peet.ws/api/all")
114-
.emulation(Emulation::Firefox136)
144+
// POST with JSON body
145+
let user = User {
146+
name: "John Doe".to_string(),
147+
email: "john@example.com".to_string(),
148+
};
149+
150+
let response = hpx::Client::new()
151+
.post("https://jsonplaceholder.typicode.com/users")
152+
.json(&user)
115153
.send()
116154
.await?;
117155

118-
println!("{}", resp.text().await?);
156+
println!("Status: {}", response.status());
157+
Ok(())
158+
}
159+
```
160+
161+
### Request/Response Hooks
162+
163+
Add lifecycle hooks to monitor and modify requests/responses:
164+
165+
```rust
166+
use hpx::client::{layer::hooks::{Hooks, LoggingHook, RequestIdHook}, Client};
167+
168+
#[tokio::main]
169+
async fn main() -> hpx::Result<()> {
170+
let client = Client::builder()
171+
.hooks(Hooks::new()
172+
.before_request(|req| {
173+
println!("Sending request to: {}", req.uri());
174+
async { Ok(()) }
175+
})
176+
.after_response(|res| {
177+
println!("Received response: {}", res.status());
178+
async { Ok(()) }
179+
})
180+
)
181+
.build()?;
182+
183+
let _response = client.get("https://httpbin.org/get").send().await?;
184+
Ok(())
185+
}
186+
```
187+
188+
### Retry Configuration
189+
190+
Configure retry behavior for failed requests:
191+
192+
```rust
193+
use hpx::{client::http::ClientBuilder, retry::RetryConfig};
194+
use std::time::Duration;
195+
196+
#[tokio::main]
197+
async fn main() -> hpx::Result<()> {
198+
let client = ClientBuilder::new()
199+
.retry(RetryConfig::new()
200+
.max_attempts(3)
201+
.backoff(Duration::from_millis(100))
202+
.max_backoff(Duration::from_secs(10))
203+
)
204+
.build()?;
205+
206+
let response = client.get("https://httpbin.org/status/500").send().await?;
207+
println!("Final status: {}", response.status());
208+
Ok(())
209+
}
210+
```
211+
212+
### Streaming Response Bodies
213+
214+
Efficiently stream large response bodies:
215+
216+
```rust
217+
use tokio::io::AsyncReadExt;
218+
219+
#[tokio::main]
220+
async fn main() -> hpx::Result<()> {
221+
let mut reader = hpx::get("https://httpbin.org/stream/100")
222+
.send()
223+
.await?
224+
.reader();
225+
226+
let mut buffer = Vec::new();
227+
reader.read_to_end(&mut buffer).await?;
228+
println!("Read {} bytes", buffer.len());
229+
Ok(())
230+
}
231+
```
232+
233+
### Cookies
234+
235+
Automatic cookie handling:
236+
237+
```rust
238+
use hpx::cookie::Jar;
239+
240+
#[tokio::main]
241+
async fn main() -> hpx::Result<()> {
242+
let jar = Jar::default();
243+
244+
let client = hpx::Client::builder()
245+
.cookie_provider(jar.clone())
246+
.build()?;
247+
248+
// Cookies will be automatically stored and sent
249+
let _resp = client.get("https://httpbin.org/cookies/set/session/123").send().await?;
250+
251+
// Check stored cookies
252+
println!("Cookies: {:?}", jar.cookies("https://httpbin.org"));
119253
Ok(())
120254
}
121255
```
@@ -153,6 +287,49 @@ async fn main() -> hpx::Result<()> {
153287
}
154288
```
155289

290+
### Browser Emulation
291+
292+
The `emulation` module allows you to simulate specific browser fingerprints.
293+
294+
```rust
295+
use hpx_util::Emulation;
296+
297+
#[tokio::main]
298+
async fn main() -> hpx::Result<()> {
299+
let resp = hpx::get("https://tls.peet.ws/api/all")
300+
.emulation(Emulation::Firefox136)
301+
.send()
302+
.await?;
303+
304+
println!("{}", resp.text().await?);
305+
Ok(())
306+
}
307+
```
308+
309+
### Transport Layer
310+
311+
For advanced use cases, you can work directly with the transport layer:
312+
313+
```rust
314+
use hpx_transport::{HttpClient, typed::TypedRequestBuilder};
315+
use std::time::Duration;
316+
317+
#[tokio::main]
318+
async fn main() -> hpx_transport::Result<()> {
319+
let client = HttpClient::builder()
320+
.timeout(Duration::from_secs(30))
321+
.build()?;
322+
323+
let request = TypedRequestBuilder::get("https://httpbin.org/get")
324+
.header("User-Agent", "hpx-transport")
325+
.build()?;
326+
327+
let response = client.send_request(request).await?;
328+
println!("Status: {}", response.status());
329+
Ok(())
330+
}
331+
```
332+
156333
## License
157334

158335
Apache-2.0

0 commit comments

Comments
 (0)