steam_user/services/
license.rs1use base64::Engine;
2use prost::Message;
3use steam_protos::messages::loyalty_rewards::{CLoyaltyRewardsRedeemPointsRequest, CLoyaltyRewardsRedeemPointsResponse};
4
5use crate::{client::SteamUser, endpoint::steam_endpoint, error::SteamUserError};
6
7impl SteamUser {
8 #[steam_endpoint(POST, host = Store, path = "/freelicense/addfreelicense/{package_id}", kind = Write)]
18 pub async fn add_free_license(&self, package_id: u32) -> Result<bool, SteamUserError> {
19 let response = self.post_path(format!("/freelicense/addfreelicense/{}", package_id)).form(&[("ajax", "true")]).send().await?;
20
21 let status = response.status();
22 let data: serde_json::Value = response.json().await?;
23
24 Ok(status.is_success() && data.is_array() && data.as_array().map(|a| a.is_empty()).unwrap_or(false))
26 }
27
28 #[steam_endpoint(POST, host = Store, path = "/checkout/addfreelicense/", kind = Write)]
35 pub async fn add_sub_free_license(&self, sub_id: u32) -> Result<bool, SteamUserError> {
36 let response = self.post_path("/checkout/addfreelicense/").form(&[("snr", "1_5_9__403"), ("originating_snr", "1_store-navigation__"), ("action", "add_to_cart"), ("subid", &sub_id.to_string())]).send().await?;
37
38 let data = response.text().await?;
39 if data.contains("There was a problem adding this product to your Steam account.") {
40 return Ok(false);
41 }
42
43 Ok(true)
44 }
45
46 #[steam_endpoint(POST, host = Api, path = "/ILoyaltyRewardsService/RedeemPoints/v1", kind = Write)]
54 pub async fn redeem_points(&self, definition_id: u32) -> Result<CLoyaltyRewardsRedeemPointsResponse, SteamUserError> {
55 let access_token = self.session.access_token.as_ref().ok_or_else(|| SteamUserError::Other("Access token is required for redeem_points".into()))?;
56
57 let request = CLoyaltyRewardsRedeemPointsRequest { defid: Some(definition_id), expected_points_cost: Some(0) };
58
59 let mut body = Vec::new();
60 request.encode(&mut body).map_err(|e| SteamUserError::Other(e.to_string()))?;
61
62 let params = [("access_token", access_token.as_str()), ("spoof_steamid", ""), ("origin", "https://store.steampowered.com")];
63
64 let response = self.post_path("/ILoyaltyRewardsService/RedeemPoints/v1").query(¶ms).form(&[("input_protobuf_encoded", base64::engine::general_purpose::STANDARD.encode(body))]).send().await?;
65
66 if !response.status().is_success() {
67 return Err(SteamUserError::Other(format!("HTTP error {}", response.status())));
68 }
69
70 let bytes = response.bytes().await?;
71 let result = CLoyaltyRewardsRedeemPointsResponse::decode(bytes).map_err(|e| SteamUserError::Other(e.to_string()))?;
72
73 Ok(result)
74 }
75}