2 unstable releases

0.2.0 Feb 9, 2023
0.1.0 Apr 10, 2021

#768 in HTTP server

Download history 85/week @ 2023-11-20 108/week @ 2023-11-27 141/week @ 2023-12-04 141/week @ 2023-12-11 70/week @ 2023-12-18 25/week @ 2023-12-25 83/week @ 2024-01-01 82/week @ 2024-01-08 112/week @ 2024-01-15 190/week @ 2024-01-22 133/week @ 2024-01-29 26/week @ 2024-02-05 15/week @ 2024-02-12 63/week @ 2024-02-19 79/week @ 2024-02-26 94/week @ 2024-03-04

252 downloads per month

MIT license

9KB
51 lines

actix-proxy

Build Status Codecov Latest Version Downloads Docs License: MIT

A rust library for the actix-web framework. Glues together the actix-web and awc crates.

This library provides the IntoHttpResponse trait which transforms a awc::ClientResponse into a actix_web::HttpResponse and the SendRequestError type bridging the gap between awc's SendRequestError and actix-web, by implementing actix_web::ResponseError.

Sometimes you want to implement a gateway or proxy, which makes a request to some remote service and forwards the response to the client that made the request. actix-web integrates with the awc::Client HTTP client. Unfortunately, awc::ClientResponse, the response type of the client request, does not implement the Responder trait. Because of that, you can't return awc::ClientResponse from an endpoint of your actix-web server. This makes it hard to forward the response from the remote location through an endpoint of the proxy, requiring you to transform the response into a type that implements Responder.

With the IntoHttpResponse trait offered by actix-proxy, all you need to do is call the into_http_response method on your awc::ClientResponse to forward the response from the remote service through the proxy to the original caller.

Example

In this example we create a basic proxy for the duckduckgo search engine, simply forwarding the called url's path, query and fragment parts to duckduckgo:

use awc::Client;

use actix_web::{get, web, HttpResponse};

use actix_proxy::{IntoHttpResponse, SendRequestError};

#[get("/{url:.*}")]
async fn proxy(
  path: web::Path<(String,)>,
  client: web::Data<Client>,
) -> Result<HttpResponse, SendRequestError> {
  let (url,) = path.into_inner();

  let url = format!("https://duckduckgo.com/{url}");

  // here we use `IntoHttpResponse` to return the request to 
  // duckduckgo back to the client that called this endpoint
  Ok(client.get(&url).send().await?.into_http_response())
}

Alternatively, you can use the into_wrapped_http_response method to avoid having to wrap your result in an Ok(..) by hand:

use awc::Client;

use actix_web::{get, web, HttpResponse};

use actix_proxy::{IntoHttpResponse, SendRequestError};

#[get("/{url:.*}")]
async fn proxy(
  path: web::Path<(String,)>,
  client: web::Data<Client>,
) -> Result<HttpResponse, SendRequestError> {
  let (url,) = path.into_inner();

  let url = format!("https://duckduckgo.com/{url}");

  // here we use `IntoHttpResponse` to return the request to 
  // duckduckgo back to the client that called this endpoint
  client.get(&url).send().await?.into_wrapped_http_response()
}

Dependencies

~20–34MB
~605K SLoC