raspisms/models/Quota.php

201 lines
6.2 KiB
PHP
Raw Permalink Normal View History

2021-06-08 02:00:48 +02:00
<?php
/*
* This file is part of RaspiSMS.
*
* (c) Pierre-Lin Bonnemaison <plebwebsas@gmail.com>
*
* This source file is subject to the GPL-3.0 license that is bundled
* with this source code in the file LICENSE.
*/
namespace models;
class Quota extends StandardModel
{
2021-06-12 23:23:15 +02:00
/**
* Return the quota for a user if it exists.
*
* @param int $id_user : user id
*
* @return array : quota if found, else empty array
*/
public function get_user_quota(int $id_user)
{
return $this->_select_one($this->get_table_name(), ['id_user' => $id_user]);
}
2021-06-08 02:00:48 +02:00
/**
* Get remaining credit for a date
2021-06-17 00:51:33 +02:00
* if no quota for this user return max int.
*
* @param int $id_user : User id
* @param \DateTime $at : date to get credit at
*
2021-06-08 02:00:48 +02:00
* @return int : number of remaining credits
*/
2021-06-17 00:51:33 +02:00
public function get_remaining_credit(int $id_user, \DateTime $at): int
2021-06-08 02:00:48 +02:00
{
$query = '
SELECT (credit + additional - consumed) AS remaining_credit
FROM quota
WHERE id_user = :id_user
AND start_date <= :at
AND expiration_date > :at';
2021-06-08 02:00:48 +02:00
$params = [
'id_user' => $id_user,
'at' => $at->format('Y-m-d H:i:s'),
];
$result = $this->_run_query($query, $params);
2021-06-17 00:51:33 +02:00
return $result[0]['remaining_credit'] ?? PHP_INT_MAX;
2021-06-08 02:00:48 +02:00
}
2021-06-17 00:51:33 +02:00
2021-06-08 02:00:48 +02:00
/**
* Get credit usage percent for a date
2021-06-17 00:51:33 +02:00
* if no quota for this user return 0.
*
* @param int $id_user : User id
* @param \DateTime $at : date to get usage percent at
*
2021-06-08 02:00:48 +02:00
* @return float : percent of used credits
*/
2021-06-17 00:51:33 +02:00
public function get_usage_percentage(int $id_user, \DateTime $at): float
2021-06-08 02:00:48 +02:00
{
$query = '
SELECT (consumed / (credit + additional)) AS usage_percentage
FROM quota
WHERE id_user = :id_user
AND start_date <= :at
2021-06-13 00:14:54 +02:00
AND expiration_date > :at';
2021-06-08 02:00:48 +02:00
$params = [
'id_user' => $id_user,
'at' => $at->format('Y-m-d H:i:s'),
];
$result = $this->_run_query($query, $params);
2021-06-13 00:14:54 +02:00
return (float) ($result[0]['usage_percentage'] ?? 0);
2021-06-08 02:00:48 +02:00
}
2021-06-17 00:51:33 +02:00
2021-06-08 02:00:48 +02:00
/**
2021-06-17 00:51:33 +02:00
* Consume some credit for a user.
*
* @param int $id_user : User id
2021-06-08 02:00:48 +02:00
* @param int $quantity : Number of credits to consume
2021-06-17 00:51:33 +02:00
*
2021-06-08 02:00:48 +02:00
* @return bool
*/
2021-06-17 00:51:33 +02:00
public function consume_credit(int $id_user, int $quantity): int
2021-06-08 02:00:48 +02:00
{
$query = '
UPDATE quota
SET consumed = consumed + :quantity
WHERE id_user = :id_user';
$params = [
'id_user' => $id_user,
'quantity' => $quantity,
];
return (bool) $this->_run_query($query, $params, \descartes\Model::ROWCOUNT);
}
2021-06-08 21:01:26 +02:00
/**
* Get all quotas we need to send an alert for close limit to users they belongs to
2021-06-17 00:51:33 +02:00
* do not return quotas when user already had an event QUOTA_LIMIT_CLOSE since quota start_date.
2021-06-08 21:01:26 +02:00
*/
2021-06-17 00:51:33 +02:00
public function get_quotas_for_limit_close(): array
2021-06-08 21:01:26 +02:00
{
$query = '
SELECT quota.*
FROM quota
INNER JOIN setting
ON (
quota.id_user = setting.id_user
AND setting.NAME = :setting_name
AND setting.value != 0
)
WHERE
quota.consumed / ( quota.credit + quota.additional ) >= setting.value
AND (
SELECT COUNT(id)
FROM event
WHERE
id_user = quota.id_user
AND type = :event_type
AND at >= quota.start_date
) = 0;
';
$params = [
'setting_name' => 'alert_quota_limit_close',
'event_type' => 'QUOTA_LIMIT_CLOSE',
];
2021-06-17 00:51:33 +02:00
2021-06-08 21:01:26 +02:00
return $this->_run_query($query, $params);
}
2021-06-17 00:51:33 +02:00
2021-06-08 21:01:26 +02:00
/**
* Get all quotas we need to send an alert for limit reached to users they belongs to
2021-06-17 00:51:33 +02:00
* do not return quotas when user already had an event QUOTA_LIMIT_REACHED since quota start_date.
2021-06-08 21:01:26 +02:00
*/
2021-06-17 00:51:33 +02:00
public function get_quotas_for_limit_reached(): array
2021-06-08 21:01:26 +02:00
{
$query = '
SELECT quota.*
FROM quota
INNER JOIN setting
ON (
quota.id_user = setting.id_user
AND setting.NAME = :setting_name
AND setting.value = 1
)
WHERE
quota.consumed >= (quota.credit + quota.additional)
AND (
SELECT COUNT(id)
FROM event
WHERE
id_user = quota.id_user
AND type = :event_type
AND at >= quota.start_date
) = 0;
';
2021-06-17 00:51:33 +02:00
2021-06-08 21:01:26 +02:00
$params = [
'setting_name' => 'alert_quota_limit_reached',
'event_type' => 'QUOTA_LIMIT_REACHED',
];
2021-06-17 00:51:33 +02:00
2021-06-08 21:01:26 +02:00
return $this->_run_query($query, $params);
}
2021-06-10 01:31:53 +02:00
/**
2021-06-17 00:51:33 +02:00
* Get list of quotas to be renewed as to a date.
*
2021-06-10 01:31:53 +02:00
* @param \DateTime $at : Date to get quotas to be renewed before
*/
2021-06-17 00:51:33 +02:00
public function get_quotas_to_be_renewed(\DateTime $at): array
2021-06-10 01:31:53 +02:00
{
$at = $at->format('Y-m-d H:i:s');
$where = [
'<=expiration_date' => $at,
'auto_renew' => true,
];
return $this->_select('quota', $where);
}
2021-06-08 02:00:48 +02:00
/**
* Return table name.
*/
protected function get_table_name(): string
{
return 'quota';
}
}