add: automatically stop all user ads when user cannot afford transfer

This commit is contained in:
trisua 2025-08-11 20:44:16 -04:00
parent 2cb7d08ddc
commit 59bccd9474
4 changed files with 70 additions and 26 deletions

View file

@ -48,7 +48,7 @@
.display_tag {
position: absolute;
bottom: 0.5rem;
top: 0.5rem;
left: 0.5rem;
padding: 0.15rem 0.5rem;
background: hsla(0, 0%, 0%, 50%);
@ -59,4 +59,5 @@
pointer-events: none;
border-radius: 0.4rem;
box-shadow: 0 0 2px hsla(0, 0%, 0%, 25%);
opacity: 25%;
}"))))

View file

@ -17,7 +17,7 @@ use tetratto_core::model::{
};
use super::{CreateAd, UpdateAdIsRunning};
const MAXIMUM_AD_FILE_SIZE: usize = 4_194_304;
const MAXIMUM_AD_FILE_SIZE: usize = 2_097_152;
pub async fn create_request(
jar: CookieJar,
@ -104,6 +104,15 @@ pub async fn update_is_running_request(
None => return Json(Error::NotAllowed.into()),
};
if user.coins < 50 {
return Json(
Error::MiscError(
"You must have a minimum of 50 coins in your balance to run ads".to_string(),
)
.into(),
);
}
match data
.update_ad_is_running(id, &user, if req.is_running { 1 } else { 0 })
.await

View file

@ -257,7 +257,6 @@ pub async fn random_ad_request(
let ad = match data.0.random_ad_charged(props.size.clone()).await {
Ok(x) => x,
Err(_) => UserAd {
// polyfill ad
id: 0,
created: 0,
upload_id: 0,

View file

@ -56,6 +56,30 @@ impl DataManager {
Ok(res.unwrap())
}
/// Disable all ads by the given user.
///
/// # Arguments
/// * `id` - the ID of the user to kill ads from
pub async fn stop_all_ads_by_user(&self, id: usize) -> Result<Vec<UserAd>> {
let conn = match self.0.connect().await {
Ok(c) => c,
Err(e) => return Err(Error::DatabaseConnection(e.to_string())),
};
let res = query_rows!(
&conn,
"UPDATE ads SET is_running = 0 WHERE owner = $1",
&[&(id as i64)],
|x| { Self::get_ad_from_row(x) }
);
if let Err(e) = res {
return Err(Error::DatabaseError(e.to_string()));
}
Ok(res.unwrap())
}
/// Create a new ad in the database.
///
/// # Arguments
@ -161,7 +185,7 @@ impl DataManager {
const MINIMUM_DELTA_FOR_CHARGE: usize = 604_800_000; // 7 days
/// The amount charged to a [`UserAd`] owner each day the ad is running (and is pulled from the pool).
pub const AD_RUN_CHARGE: i32 = 50;
pub const AD_RUN_CHARGE: i32 = 25;
/// The amount charged to a [`UserAd`] owner each time the ad is clicked.
pub const AD_CLICK_CHARGE: i32 = 2;
@ -173,7 +197,8 @@ impl DataManager {
let delta = now - ad.last_charge_time;
if delta >= Self::MINIMUM_DELTA_FOR_CHARGE {
self.create_transfer(
if let Err(e) = self
.create_transfer(
&mut CoinTransfer::new(
ad.owner,
self.0.0.system_user,
@ -183,7 +208,12 @@ impl DataManager {
),
true,
)
.await?;
.await
{
// boo user cannot afford to keep running their ads
self.stop_all_ads_by_user(ad.owner).await?;
return Err(e);
};
self.update_ad_last_charge_time(ad.id, now as i64).await?;
}
@ -212,7 +242,8 @@ impl DataManager {
}
// create click transfer
self.create_transfer(
if let Err(e) = self
.create_transfer(
&mut CoinTransfer::new(
ad.owner,
host,
@ -222,7 +253,11 @@ impl DataManager {
),
true,
)
.await?;
.await
{
self.stop_all_ads_by_user(ad.owner).await?;
return Err(e);
}
// return
Ok(ad.target)