You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by ra...@apache.org on 2015/08/31 12:34:40 UTC
[6/6] git commit: updated refs/heads/pr/689-review to af28a82
CLOUDSTACK-8592: Implement Quota service
Quota service while allowing for scalability will make sure that the cloud is
not exploited by attacks, careless use and program errors. To address this
problem, we propose to employ a quota-enforcement service that allows resource
usage within certain bounds as defined by policies and available quotas for
various entities. Quota service extends the functionality of usage server to
provide a measurement for the resources used by the accounts and domains using a
common unit referred to as cloud currency in this document. It can be configured
to ensure that your usage won’t exceed the budget allocated to accounts/domain
in cloud currency. It will let user know how much of the cloud resources he is
using. It will help the cloud admins, if they want, to ensure that a user does
not go beyond his allocated quota. Per usage cycle if a account is found to be
exceeding its quota then it is locked. Locking an account means that it will not
be able to initiat e a new resource allocation request, whether it is more
storage or an additional ip. Needless to say quota service as well as any action
on the account is configurable.
FS: https://cwiki.apache.org/confluence/display/CLOUDSTACK/Quota+Service+-+FS
Signed-off-by: Rohit Yadav <ro...@shapeblue.com>
Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/dedb351f
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/dedb351f
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/dedb351f
Branch: refs/heads/pr/689-review
Commit: dedb351f090c672b1832b81ca573ddd555829f04
Parents: 1bbd23e
Author: Abhinandan Prateek <ab...@shapeblue.com>
Authored: Thu Aug 13 11:42:30 2015 +0530
Committer: Rohit Yadav <ro...@shapeblue.com>
Committed: Mon Aug 31 15:38:53 2015 +0530
----------------------------------------------------------------------
.../org/apache/cloudstack/api/ApiConstants.java | 1 +
api/src/org/apache/cloudstack/api/BaseCmd.java | 2 +-
.../command/admin/usage/GetUsageRecordsCmd.java | 25 +
.../org/apache/cloudstack/usage/UsageTypes.java | 2 +
.../classes/resources/messages.properties | 7 +
client/pom.xml | 10 +
client/tomcatconf/commands.properties.in | 9 +
.../com/cloud/upgrade/dao/Upgrade452to460.java | 15 +
engine/schema/src/com/cloud/usage/UsageVO.java | 11 +
.../src/com/cloud/usage/dao/UsageDao.java | 2 +
.../src/com/cloud/usage/dao/UsageDaoImpl.java | 74 ++-
framework/pom.xml | 1 +
framework/quota/pom.xml | 41 ++
.../quota/spring-framework-quota-context.xml | 30 ++
.../cloudstack/quota/constant/QuotaConfig.java | 53 +++
.../cloudstack/quota/constant/QuotaTypes.java | 92 ++++
.../cloudstack/quota/dao/QuotaAccountDao.java | 35 ++
.../quota/dao/QuotaAccountDaoImpl.java | 73 +++
.../cloudstack/quota/dao/QuotaBalanceDao.java | 43 ++
.../quota/dao/QuotaBalanceDaoImpl.java | 201 ++++++++
.../cloudstack/quota/dao/QuotaCreditsDao.java | 32 ++
.../quota/dao/QuotaCreditsDaoImpl.java | 72 +++
.../quota/dao/QuotaEmailTemplatesDao.java | 27 ++
.../quota/dao/QuotaEmailTemplatesDaoImpl.java | 64 +++
.../cloudstack/quota/dao/QuotaTariffDao.java | 35 ++
.../quota/dao/QuotaTariffDaoImpl.java | 138 ++++++
.../cloudstack/quota/dao/QuotaUsageDao.java | 40 ++
.../cloudstack/quota/dao/QuotaUsageDaoImpl.java | 106 +++++
.../quota/dao/ServiceOfferingDao.java | 27 ++
.../quota/dao/ServiceOfferingDaoImpl.java | 85 ++++
.../cloudstack/quota/dao/UserVmDetailsDao.java | 31 ++
.../quota/dao/UserVmDetailsDaoImpl.java | 62 +++
.../cloudstack/quota/vo/QuotaAccountVO.java | 142 ++++++
.../cloudstack/quota/vo/QuotaBalanceVO.java | 127 +++++
.../cloudstack/quota/vo/QuotaCreditsVO.java | 117 +++++
.../quota/vo/QuotaEmailTemplatesVO.java | 109 +++++
.../cloudstack/quota/vo/QuotaTariffVO.java | 162 +++++++
.../cloudstack/quota/vo/QuotaUsageVO.java | 172 +++++++
.../cloudstack/quota/vo/ServiceOfferingVO.java | 336 +++++++++++++
.../cloudstack/quota/vo/UserVmDetailVO.java | 83 ++++
plugins/database/quota/pom.xml | 58 +++
.../META-INF/cloudstack/quota/module.properties | 18 +
.../cloudstack/quota/spring-quota-context.xml | 31 ++
.../cloudstack/api/command/QuotaBalanceCmd.java | 136 ++++++
.../cloudstack/api/command/QuotaCreditsCmd.java | 143 ++++++
.../api/command/QuotaEmailTemplateListCmd.java | 56 +++
.../command/QuotaEmailTemplateUpdateCmd.java | 111 +++++
.../api/command/QuotaStatementCmd.java | 143 ++++++
.../api/command/QuotaTariffListCmd.java | 93 ++++
.../api/command/QuotaTariffUpdateCmd.java | 102 ++++
.../api/response/QuotaBalanceResponse.java | 153 ++++++
.../api/response/QuotaCreditsResponse.java | 91 ++++
.../response/QuotaEmailTemplateResponse.java | 90 ++++
.../api/response/QuotaResponseBuilder.java | 62 +++
.../api/response/QuotaResponseBuilderImpl.java | 412 ++++++++++++++++
.../response/QuotaStatementItemResponse.java | 143 ++++++
.../api/response/QuotaStatementResponse.java | 130 +++++
.../api/response/QuotaTariffResponse.java | 134 ++++++
.../api/response/QuotaTypeResponse.java | 58 +++
.../apache/cloudstack/quota/QuotaService.java | 39 ++
.../cloudstack/quota/QuotaServiceImpl.java | 296 ++++++++++++
plugins/hypervisors/ovm3/pom.xml | 2 +-
plugins/pom.xml | 1 +
pom.xml | 3 +-
.../cloud/api/dispatch/ParamProcessWorker.java | 8 +
.../src/com/cloud/user/AccountManagerImpl.java | 3 +-
setup/db/db/schema-451to452.sql | 4 +-
setup/db/db/schema-452to460.sql | 112 +++++
tools/apidoc/gen_toc.py | 2 +
usage/pom.xml | 10 +
usage/resources/usageApplicationContext.xml | 54 ++-
usage/src/com/cloud/usage/UsageManagerImpl.java | 30 +-
.../cloudstack/quota/QuotaAlertManager.java | 27 ++
.../cloudstack/quota/QuotaAlertManagerImpl.java | 471 +++++++++++++++++++
.../apache/cloudstack/quota/QuotaManager.java | 25 +
.../cloudstack/quota/QuotaManagerImpl.java | 465 ++++++++++++++++++
76 files changed, 6355 insertions(+), 55 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/api/src/org/apache/cloudstack/api/ApiConstants.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/ApiConstants.java b/api/src/org/apache/cloudstack/api/ApiConstants.java
index e86e2d4..d371b93 100644
--- a/api/src/org/apache/cloudstack/api/ApiConstants.java
+++ b/api/src/org/apache/cloudstack/api/ApiConstants.java
@@ -273,6 +273,7 @@ public class ApiConstants {
public static final String VIRTUAL_MACHINE_ID_IP = "vmidipmap";
public static final String VIRTUAL_MACHINE_COUNT = "virtualmachinecount";
public static final String USAGE_ID = "usageid";
+ public static final String USAGE_TYPE = "usagetype";
public static final String VLAN = "vlan";
public static final String VLAN_RANGE = "vlanrange";
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/api/src/org/apache/cloudstack/api/BaseCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/BaseCmd.java b/api/src/org/apache/cloudstack/api/BaseCmd.java
index ad3a88c..360b277 100644
--- a/api/src/org/apache/cloudstack/api/BaseCmd.java
+++ b/api/src/org/apache/cloudstack/api/BaseCmd.java
@@ -95,7 +95,7 @@ public abstract class BaseCmd {
GET, POST, PUT, DELETE
}
public static enum CommandType {
- BOOLEAN, DATE, FLOAT, INTEGER, SHORT, LIST, LONG, OBJECT, MAP, STRING, TZDATE, UUID
+ BOOLEAN, DATE, FLOAT, DOUBLE, INTEGER, SHORT, LIST, LONG, OBJECT, MAP, STRING, TZDATE, UUID
}
private Object _responseObject;
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/api/src/org/apache/cloudstack/api/command/admin/usage/GetUsageRecordsCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/admin/usage/GetUsageRecordsCmd.java b/api/src/org/apache/cloudstack/api/command/admin/usage/GetUsageRecordsCmd.java
index fd8173d..76af050 100644
--- a/api/src/org/apache/cloudstack/api/command/admin/usage/GetUsageRecordsCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/admin/usage/GetUsageRecordsCmd.java
@@ -38,6 +38,7 @@ import com.cloud.utils.Pair;
@APICommand(name = "listUsageRecords", description = "Lists usage records for accounts", responseObject = UsageRecordResponse.class,
requestHasSensitiveInfo = false, responseHasSensitiveInfo = false)
public class GetUsageRecordsCmd extends BaseListCmd {
+
public static final Logger s_logger = Logger.getLogger(GetUsageRecordsCmd.class.getName());
private static final String s_name = "listusagerecordsresponse";
@@ -111,6 +112,30 @@ public class GetUsageRecordsCmd extends BaseListCmd {
public String getUsageId() {
return usageId;
}
+ public void setAccountName(String accountName) {
+ this.accountName = accountName;
+ }
+
+ public void setDomainId(Long domainId) {
+ this.domainId = domainId;
+ }
+
+ public void setEndDate(Date endDate) {
+ this.endDate = endDate;
+ }
+
+ public void setStartDate(Date startDate) {
+ this.startDate = startDate;
+ }
+
+ public void setAccountId(Long accountId) {
+ this.accountId = accountId;
+ }
+
+ public void setUsageId(String usageId) {
+ this.usageId = usageId;
+ }
+
/////////////////////////////////////////////////////
/////////////// API Implementation///////////////////
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/api/src/org/apache/cloudstack/usage/UsageTypes.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/usage/UsageTypes.java b/api/src/org/apache/cloudstack/usage/UsageTypes.java
index 3edfd0b..2163df7 100644
--- a/api/src/org/apache/cloudstack/usage/UsageTypes.java
+++ b/api/src/org/apache/cloudstack/usage/UsageTypes.java
@@ -22,6 +22,8 @@ import java.util.List;
import org.apache.cloudstack.api.response.UsageTypeResponse;
public class UsageTypes {
+
+ /* Any changes here should also reflect in cloud_usage.quota_mapping table */
public static final int RUNNING_VM = 1;
public static final int ALLOCATED_VM = 2; // used for tracking how long storage has been allocated for a VM
public static final int IP_ADDRESS = 3;
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/client/WEB-INF/classes/resources/messages.properties
----------------------------------------------------------------------
diff --git a/client/WEB-INF/classes/resources/messages.properties b/client/WEB-INF/classes/resources/messages.properties
index 492b46e..a881a19 100644
--- a/client/WEB-INF/classes/resources/messages.properties
+++ b/client/WEB-INF/classes/resources/messages.properties
@@ -1386,6 +1386,13 @@ label.show.advanced.settings=Show advanced settings
label.delete.OpenDaylight.device=Delete OpenDaylight Controller
label.polling.interval.sec=Polling Interval (in sec)
label.quiet.time.sec=Quiet Time (in sec)
+label.usage.type=Usage Type
+label.usage.unit=Unit
+label.quota.value=Quota Value
+label.quota.description=Quota Description
+label.quota.configuration=Quota Configuration
+label.quota.configure=Configure Quota
+label.quota.remove=Remove Quota
label.destroy.vm.graceperiod=Destroy VM Grace Period
label.SNMP.community=SNMP Community
label.SNMP.port=SNMP Port
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/client/pom.xml
----------------------------------------------------------------------
diff --git a/client/pom.xml b/client/pom.xml
index 3dbc0a0..9b3e211 100644
--- a/client/pom.xml
+++ b/client/pom.xml
@@ -258,6 +258,11 @@
</dependency>
<dependency>
<groupId>org.apache.cloudstack</groupId>
+ <artifactId>cloud-framework-quota</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cloudstack</groupId>
<artifactId>cloud-framework-rest</artifactId>
<version>${project.version}</version>
</dependency>
@@ -366,6 +371,11 @@
<artifactId>cloud-plugin-network-globodns</artifactId>
<version>${project.version}</version>
</dependency>
+ <dependency>
+ <groupId>org.apache.cloudstack</groupId>
+ <artifactId>cloud-plugin-database-quota</artifactId>
+ <version>${project.version}</version>
+ </dependency>
</dependencies>
<build>
<plugins>
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/client/tomcatconf/commands.properties.in
----------------------------------------------------------------------
diff --git a/client/tomcatconf/commands.properties.in b/client/tomcatconf/commands.properties.in
index aec7516..f77e3f0 100644
--- a/client/tomcatconf/commands.properties.in
+++ b/client/tomcatconf/commands.properties.in
@@ -787,3 +787,12 @@ addGloboDnsHost=1
### volume/template post upload
getUploadParamsForVolume=15
getUploadParamsForTemplate=15
+
+### Quota Service
+quotaStatement=15
+quotaBalance=15
+quotaTariffList=15
+quotaTariffUpdate=1
+quotaCredits=1
+quotaEmailTemplateList=1
+quotaEmailTemplateUpdate=1
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/engine/schema/src/com/cloud/upgrade/dao/Upgrade452to460.java
----------------------------------------------------------------------
diff --git a/engine/schema/src/com/cloud/upgrade/dao/Upgrade452to460.java b/engine/schema/src/com/cloud/upgrade/dao/Upgrade452to460.java
index 0ad2603..71e7a7b 100644
--- a/engine/schema/src/com/cloud/upgrade/dao/Upgrade452to460.java
+++ b/engine/schema/src/com/cloud/upgrade/dao/Upgrade452to460.java
@@ -60,10 +60,25 @@ public class Upgrade452to460 implements DbUpgrade {
@Override
public void performDataMigration(final Connection conn) {
+ alterAddColumnToCloudUsage(conn);
updateVMInstanceUserId(conn);
addIndexForVMInstance(conn);
}
+ public void alterAddColumnToCloudUsage(final Connection conn) {
+ final String alterTableSql = "ALTER TABLE `cloud_usage`.`cloud_usage` ADD COLUMN `quota_calculated` tinyint(1) DEFAULT 0 NOT NULL COMMENT 'quota calculation status'";
+ try (PreparedStatement pstmt = conn.prepareStatement(alterTableSql)) {
+ pstmt.executeUpdate();
+ s_logger.debug("Altered usage table and added column quota_calculated");
+ } catch (SQLException e) {
+ if (e.getMessage().contains("quota_calculated")) {
+ s_logger.debug("Usage table already has a column called quota_calculated");
+ } else {
+ throw new CloudRuntimeException("Unable to create column quota_calculated", e);
+ }
+ }
+ }
+
public void updateVMInstanceUserId(final Connection conn) {
// For schemas before this, copy first user from an account_id which
// deployed already running VMs
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/engine/schema/src/com/cloud/usage/UsageVO.java
----------------------------------------------------------------------
diff --git a/engine/schema/src/com/cloud/usage/UsageVO.java b/engine/schema/src/com/cloud/usage/UsageVO.java
index c46abb3..bf5f551 100644
--- a/engine/schema/src/com/cloud/usage/UsageVO.java
+++ b/engine/schema/src/com/cloud/usage/UsageVO.java
@@ -103,6 +103,17 @@ public class UsageVO implements Usage, InternalIdentity {
@Temporal(value = TemporalType.TIMESTAMP)
private Date endDate = null;
+ @Column(name = "quota_calculated")
+ private Integer quotaCalculated = null;
+
+ public Integer getQuotaCalculated() {
+ return quotaCalculated;
+ }
+
+ public void setQuotaCalculated(Integer quotaCalculated) {
+ this.quotaCalculated = quotaCalculated;
+ }
+
public UsageVO() {
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/engine/schema/src/com/cloud/usage/dao/UsageDao.java
----------------------------------------------------------------------
diff --git a/engine/schema/src/com/cloud/usage/dao/UsageDao.java b/engine/schema/src/com/cloud/usage/dao/UsageDao.java
index f9e9d23..bd09049 100644
--- a/engine/schema/src/com/cloud/usage/dao/UsageDao.java
+++ b/engine/schema/src/com/cloud/usage/dao/UsageDao.java
@@ -55,4 +55,6 @@ public interface UsageDao extends GenericDao<UsageVO, Long> {
void saveUsageRecords(List<UsageVO> usageRecords);
void removeOldUsageRecords(int days);
+
+ Pair<List<? extends UsageVO>, Integer> getUsageRecordsPendingQuotaAggregation(long accountId, long domainId);
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/engine/schema/src/com/cloud/usage/dao/UsageDaoImpl.java
----------------------------------------------------------------------
diff --git a/engine/schema/src/com/cloud/usage/dao/UsageDaoImpl.java b/engine/schema/src/com/cloud/usage/dao/UsageDaoImpl.java
index 93ddf9b..287843e 100644
--- a/engine/schema/src/com/cloud/usage/dao/UsageDaoImpl.java
+++ b/engine/schema/src/com/cloud/usage/dao/UsageDaoImpl.java
@@ -40,36 +40,31 @@ import java.util.List;
import java.util.TimeZone;
@Component
-@Local(value = {UsageDao.class})
+@Local(value = { UsageDao.class })
public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements UsageDao {
public static final Logger s_logger = Logger.getLogger(UsageDaoImpl.class.getName());
private static final String DELETE_ALL = "DELETE FROM cloud_usage";
private static final String DELETE_ALL_BY_ACCOUNTID = "DELETE FROM cloud_usage WHERE account_id = ?";
private static final String DELETE_ALL_BY_INTERVAL = "DELETE FROM cloud_usage WHERE end_date < DATE_SUB(CURRENT_DATE(), INTERVAL ? DAY)";
private static final String INSERT_ACCOUNT = "INSERT INTO cloud_usage.account (id, account_name, type, domain_id, removed, cleanup_needed) VALUES (?,?,?,?,?,?)";
- private static final String INSERT_USER_STATS =
- "INSERT INTO cloud_usage.user_statistics (id, data_center_id, account_id, public_ip_address, device_id, device_type, network_id, net_bytes_received,"
- + " net_bytes_sent, current_bytes_received, current_bytes_sent, agg_bytes_received, agg_bytes_sent) VALUES (?,?,?,?,?,?,?,?,?,?, ?, ?, ?)";
+ private static final String INSERT_USER_STATS = "INSERT INTO cloud_usage.user_statistics (id, data_center_id, account_id, public_ip_address, device_id, device_type, network_id, net_bytes_received,"
+ + " net_bytes_sent, current_bytes_received, current_bytes_sent, agg_bytes_received, agg_bytes_sent) VALUES (?,?,?,?,?,?,?,?,?,?, ?, ?, ?)";
private static final String UPDATE_ACCOUNT = "UPDATE cloud_usage.account SET account_name=?, removed=? WHERE id=?";
- private static final String UPDATE_USER_STATS =
- "UPDATE cloud_usage.user_statistics SET net_bytes_received=?, net_bytes_sent=?, current_bytes_received=?, current_bytes_sent=?, agg_bytes_received=?, agg_bytes_sent=? WHERE id=?";
+ private static final String UPDATE_USER_STATS = "UPDATE cloud_usage.user_statistics SET net_bytes_received=?, net_bytes_sent=?, current_bytes_received=?, current_bytes_sent=?, agg_bytes_received=?, agg_bytes_sent=? WHERE id=?";
private static final String GET_LAST_ACCOUNT = "SELECT id FROM cloud_usage.account ORDER BY id DESC LIMIT 1";
private static final String GET_LAST_USER_STATS = "SELECT id FROM cloud_usage.user_statistics ORDER BY id DESC LIMIT 1";
private static final String GET_PUBLIC_TEMPLATES_BY_ACCOUNTID = "SELECT id FROM cloud.vm_template WHERE account_id = ? AND public = '1' AND removed IS NULL";
private static final String GET_LAST_VM_DISK_STATS = "SELECT id FROM cloud_usage.vm_disk_statistics ORDER BY id DESC LIMIT 1";
- private static final String INSERT_VM_DISK_STATS =
- "INSERT INTO cloud_usage.vm_disk_statistics (id, data_center_id, account_id, vm_id, volume_id, net_io_read, net_io_write, current_io_read, "
- + "current_io_write, agg_io_read, agg_io_write, net_bytes_read, net_bytes_write, current_bytes_read, current_bytes_write, agg_bytes_read, agg_bytes_write) "
- + " VALUES (?,?,?,?,?,?,?,?,?,?, ?, ?, ?, ?,?, ?, ?)";
- private static final String UPDATE_VM_DISK_STATS =
- "UPDATE cloud_usage.vm_disk_statistics SET net_io_read=?, net_io_write=?, current_io_read=?, current_io_write=?, agg_io_read=?, agg_io_write=?, "
- + "net_bytes_read=?, net_bytes_write=?, current_bytes_read=?, current_bytes_write=?, agg_bytes_read=?, agg_bytes_write=? WHERE id=?";
+ private static final String INSERT_VM_DISK_STATS = "INSERT INTO cloud_usage.vm_disk_statistics (id, data_center_id, account_id, vm_id, volume_id, net_io_read, net_io_write, current_io_read, "
+ + "current_io_write, agg_io_read, agg_io_write, net_bytes_read, net_bytes_write, current_bytes_read, current_bytes_write, agg_bytes_read, agg_bytes_write) "
+ + " VALUES (?,?,?,?,?,?,?,?,?,?, ?, ?, ?, ?,?, ?, ?)";
+ private static final String UPDATE_VM_DISK_STATS = "UPDATE cloud_usage.vm_disk_statistics SET net_io_read=?, net_io_write=?, current_io_read=?, current_io_write=?, agg_io_read=?, agg_io_write=?, "
+ + "net_bytes_read=?, net_bytes_write=?, current_bytes_read=?, current_bytes_write=?, agg_bytes_read=?, agg_bytes_write=? WHERE id=?";
private static final String INSERT_USAGE_RECORDS = "INSERT INTO cloud_usage.cloud_usage (zone_id, account_id, domain_id, description, usage_display, "
- +
- "usage_type, raw_usage, vm_instance_id, vm_name, offering_id, template_id, "
+ + "usage_type, raw_usage, vm_instance_id, vm_name, offering_id, template_id, "
+ "usage_id, type, size, network_id, start_date, end_date, virtual_size) VALUES (?,?,?,?,?,?,?,?,?, ?, ?, ?,?,?,?,?,?,?)";
protected final static TimeZone s_gmtTimeZone = TimeZone.getTimeZone("GMT");
@@ -110,7 +105,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = INSERT_ACCOUNT;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (AccountVO acct : accounts) {
pstmt.setLong(1, acct.getId());
pstmt.setString(2, acct.getAccountName());
@@ -144,7 +141,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = UPDATE_ACCOUNT;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (AccountVO acct : accounts) {
pstmt.setString(1, acct.getAccountName());
@@ -174,7 +173,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = INSERT_USER_STATS;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (UserStatisticsVO userStat : userStats) {
pstmt.setLong(1, userStat.getId());
pstmt.setLong(2, userStat.getDataCenterId());
@@ -215,7 +216,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = UPDATE_USER_STATS;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (UserStatisticsVO userStat : userStats) {
pstmt.setLong(1, userStat.getNetBytesReceived());
pstmt.setLong(2, userStat.getNetBytesSent());
@@ -312,7 +315,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = UPDATE_VM_DISK_STATS;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (VmDiskStatisticsVO vmDiskStat : vmDiskStats) {
pstmt.setLong(1, vmDiskStat.getNetIORead());
pstmt.setLong(2, vmDiskStat.getNetIOWrite());
@@ -346,7 +351,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = INSERT_VM_DISK_STATS;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (VmDiskStatisticsVO vmDiskStat : vmDiskStats) {
pstmt.setLong(1, vmDiskStat.getId());
pstmt.setLong(2, vmDiskStat.getDataCenterId());
@@ -392,7 +399,9 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.start();
String sql = INSERT_USAGE_RECORDS;
PreparedStatement pstmt = null;
- pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just want CLOUD_USAGE dataSource connection
+ pstmt = txn.prepareAutoCloseStatement(sql); // in reality I just
+ // want CLOUD_USAGE
+ // dataSource connection
for (UsageVO usageRecord : usageRecords) {
pstmt.setLong(1, usageRecord.getZoneId());
pstmt.setLong(2, usageRecord.getAccountId());
@@ -469,4 +478,25 @@ public class UsageDaoImpl extends GenericDaoBase<UsageVO, Long> implements Usage
txn.close();
}
}
+
+ @SuppressWarnings("deprecation")
+ public Pair<List<? extends UsageVO>, Integer> getUsageRecordsPendingQuotaAggregation(final long accountId, final long domainId) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ s_logger.debug("getting usage records for account: " + accountId + ", domainId: " + domainId);
+ Filter usageFilter = new Filter(UsageVO.class, "startDate", true, 0L, 10000L);
+ SearchCriteria<UsageVO> sc = createSearchCriteria();
+ if (accountId != -1) {
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ }
+ if (domainId != -1) {
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ }
+ sc.addAnd("quotaCalculated", SearchCriteria.Op.NULL);
+ sc.addOr("quotaCalculated", SearchCriteria.Op.EQ, 0);
+ s_logger.debug("Getting usage records" + usageFilter.getOrderBy());
+ Pair<List<UsageVO>, Integer> usageRecords = searchAndCountAllRecords(sc, usageFilter);
+ TransactionLegacy.open(opendb).close();
+ return new Pair<List<? extends UsageVO>, Integer>(usageRecords.first(), usageRecords.second());
+ }
}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/pom.xml
----------------------------------------------------------------------
diff --git a/framework/pom.xml b/framework/pom.xml
index b45f603..3bf5e61 100644
--- a/framework/pom.xml
+++ b/framework/pom.xml
@@ -47,6 +47,7 @@
<module>rest</module>
<module>events</module>
<module>jobs</module>
+ <module>quota</module>
<module>cluster</module>
<module>db</module>
<module>config</module>
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/pom.xml
----------------------------------------------------------------------
diff --git a/framework/quota/pom.xml b/framework/quota/pom.xml
new file mode 100644
index 0000000..af4cf56
--- /dev/null
+++ b/framework/quota/pom.xml
@@ -0,0 +1,41 @@
+<!--
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+ <modelVersion>4.0.0</modelVersion>
+ <artifactId>cloud-framework-quota</artifactId>
+ <name>Apache CloudStack Framework - Quota</name>
+ <parent>
+ <groupId>org.apache.cloudstack</groupId>
+ <artifactId>cloudstack-framework</artifactId>
+ <version>4.6.0-SNAPSHOT</version>
+ <relativePath>../pom.xml</relativePath>
+ </parent>
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.cloudstack</groupId>
+ <artifactId>cloud-utils</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cloudstack</groupId>
+ <artifactId>cloud-engine-schema</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ </dependencies>
+</project>
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/resources/META-INF/cloudstack/quota/spring-framework-quota-context.xml
----------------------------------------------------------------------
diff --git a/framework/quota/resources/META-INF/cloudstack/quota/spring-framework-quota-context.xml b/framework/quota/resources/META-INF/cloudstack/quota/spring-framework-quota-context.xml
new file mode 100644
index 0000000..bac81df
--- /dev/null
+++ b/framework/quota/resources/META-INF/cloudstack/quota/spring-framework-quota-context.xml
@@ -0,0 +1,30 @@
+<!-- Licensed to the Apache Software Foundation (ASF) under one or more contributor
+ license agreements. See the NOTICE file distributed with this work for additional
+ information regarding copyright ownership. The ASF licenses this file to
+ you under the Apache License, Version 2.0 (the "License"); you may not use
+ this file except in compliance with the License. You may obtain a copy of
+ the License at http://www.apache.org/licenses/LICENSE-2.0 Unless required
+ by applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS
+ OF ANY KIND, either express or implied. See the License for the specific
+ language governing permissions and limitations under the License. -->
+<beans xmlns="http://www.springframework.org/schema/beans"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"
+ xmlns:aop="http://www.springframework.org/schema/aop"
+ xsi:schemaLocation="http://www.springframework.org/schema/beans
+ http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
+ http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
+ http://www.springframework.org/schema/context
+ http://www.springframework.org/schema/context/spring-context-3.0.xsd">
+
+ <bean id="QuotaTariffDao" class="org.apache.cloudstack.quota.dao.QuotaTariffDaoImpl" />
+ <bean id="QuotaAccountDao" class="org.apache.cloudstack.quota.dao.QuotaAccountDaoImpl" />
+ <bean id="QuotaBalanceDao" class="org.apache.cloudstack.quota.dao.QuotaBalanceDaoImpl" />
+ <bean id="QuotaCreditsDao" class="org.apache.cloudstack.quota.dao.QuotaCreditsDaoImpl" />
+ <bean id="QuotaEmailTemplatesDao"
+ class="org.apache.cloudstack.quota.dao.QuotaEmailTemplatesDaoImpl" />
+ <bean id="QuotaUsageDao" class="org.apache.cloudstack.quota.dao.QuotaUsageDaoImpl" />
+ <bean id="ServiceOfferingDao" class="org.apache.cloudstack.quota.dao.ServiceOfferingDaoImpl" />
+ <bean id="UserVmDetailsDao" class="org.apache.cloudstack.quota.dao.UserVmDetailsDaoImpl" />
+
+</beans>
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaConfig.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaConfig.java b/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaConfig.java
new file mode 100644
index 0000000..518310c
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaConfig.java
@@ -0,0 +1,53 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+
+package org.apache.cloudstack.quota.constant;
+
+import org.apache.cloudstack.framework.config.ConfigKey;
+
+public interface QuotaConfig {
+
+ public static final ConfigKey<Boolean> QuotaPluginEnabled = new ConfigKey<Boolean>("Advanced", Boolean.class, "quota.enable.service", "false", "Indicates whether Quota plugin is enabled or not",
+ true);
+
+ public static final ConfigKey<String> QuotaEnableEnforcement = new ConfigKey<String>("Advanced", String.class, "quota.enable.enforcement", "false",
+ "Enable the usage quota enforcement, i.e. on true when exceeding quota the respective account will be locked.", true);
+
+ public static final ConfigKey<String> QuotaCurrencySymbol = new ConfigKey<String>("Advanced", String.class, "quota.currency.symbol", "R", "The symbol for the currency in use to measure usage.",
+ true);
+
+ public static final ConfigKey<String> QuotaSmtpHost = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.host", "", "Quota SMTP host for quota related emails", true);
+
+ public static final ConfigKey<String> QuotaSmtpTimeout = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.connection.timeout", "60",
+ "Quota SMTP server connection timeout duration", true);
+
+ public static final ConfigKey<String> QuotaSmtpUser = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.user", "", "Quota SMTP server username", true);
+
+ public static final ConfigKey<String> QuotaSmtpPassword = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.password", "", "Quota SMTP server password", true);
+
+ public static final ConfigKey<String> QuotaSmtpPort = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.port", "", "Quota SMTP port", true);
+
+ public static final ConfigKey<String> QuotaSmtpAuthType = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.useAuth", "",
+ "If true, use secure SMTP authentication when sending emails.", true);
+
+ public static final ConfigKey<String> QuotaSmtpSender = new ConfigKey<String>("Advanced", String.class, "quota.usage.smtp.sender", "",
+ "Sender of quota alert email (will be in the From header of the email)", true);
+
+ enum QuotaEmailTemplateTypes {
+ QUOTA_LOW, QUOTA_EMPTY, QUOTA_UNLOCK_ACCOUNT, QUOTA_STATEMENT
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaTypes.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaTypes.java b/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaTypes.java
new file mode 100644
index 0000000..483ecef
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/constant/QuotaTypes.java
@@ -0,0 +1,92 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package org.apache.cloudstack.quota.constant;
+
+import org.apache.cloudstack.usage.UsageTypes;
+
+import java.util.HashMap;
+
+public class QuotaTypes extends UsageTypes {
+ public static final int CPU_CLOCK_RATE = 15;
+ public static final int CPU_NUMBER = 16;
+ public static final int MEMORY = 17;
+
+ private Integer quotaType;
+ private String quotaName;
+ private String quotaUnit;
+ private String description;
+ private String discriminator;
+
+ public QuotaTypes(Integer quotaType, String name, String unit, String description) {
+ this.quotaType = quotaType;
+ this.description = description;
+ this.quotaName = name;
+ this.quotaUnit = unit;
+ this.discriminator = "None";
+ }
+
+ public static HashMap<Integer, QuotaTypes> listQuotaTypes() {
+ final HashMap<Integer, QuotaTypes> quotaTypeList = new HashMap<Integer, QuotaTypes>();
+ quotaTypeList.put(new Integer(RUNNING_VM), new QuotaTypes(new Integer(RUNNING_VM), "RUNNING_VM", "Compute-Month", "Running Vm Usage"));
+ quotaTypeList.put(new Integer(ALLOCATED_VM), new QuotaTypes(new Integer(ALLOCATED_VM), "ALLOCATED_VM", "Compute-Month", "Allocated Vm Usage"));
+ quotaTypeList.put(new Integer(IP_ADDRESS), new QuotaTypes(new Integer(IP_ADDRESS), "IP_ADDRESS", "IP-Month", "IP Address Usage"));
+ quotaTypeList.put(new Integer(NETWORK_BYTES_SENT), new QuotaTypes(new Integer(NETWORK_BYTES_SENT), "NETWORK_BYTES_SENT", "GB", "Network Usage (Bytes Sent)"));
+ quotaTypeList.put(new Integer(NETWORK_BYTES_RECEIVED), new QuotaTypes(new Integer(NETWORK_BYTES_RECEIVED), "NETWORK_BYTES_RECEIVED", "GB", "Network Usage (Bytes Received)"));
+ quotaTypeList.put(new Integer(VOLUME), new QuotaTypes(new Integer(VOLUME), "VOLUME", "GB-Month", "Volume Usage"));
+ quotaTypeList.put(new Integer(TEMPLATE), new QuotaTypes(new Integer(TEMPLATE), "TEMPLATE", "GB-Month", "Template Usage"));
+ quotaTypeList.put(new Integer(ISO), new QuotaTypes(new Integer(ISO), "ISO", "GB-Month", "ISO Usage"));
+ quotaTypeList.put(new Integer(SNAPSHOT), new QuotaTypes(new Integer(SNAPSHOT), "SNAPSHOT", "GB-Month", "Snapshot Usage"));
+ quotaTypeList.put(new Integer(SECURITY_GROUP), new QuotaTypes(new Integer(SECURITY_GROUP), "SECURITY_GROUP", "Policy-Month", "Security Group Usage"));
+ quotaTypeList.put(new Integer(LOAD_BALANCER_POLICY), new QuotaTypes(new Integer(LOAD_BALANCER_POLICY), "LOAD_BALANCER_POLICY", "Policy-Month", "Load Balancer Usage"));
+ quotaTypeList.put(new Integer(PORT_FORWARDING_RULE), new QuotaTypes(new Integer(PORT_FORWARDING_RULE), "PORT_FORWARDING_RULE", "Policy-Month", "Port Forwarding Usage"));
+ quotaTypeList.put(new Integer(NETWORK_OFFERING), new QuotaTypes(new Integer(NETWORK_OFFERING), "NETWORK_OFFERING", "Policy-Month", "Network Offering Usage"));
+ quotaTypeList.put(new Integer(VPN_USERS), new QuotaTypes(new Integer(VPN_USERS), "VPN_USERS", "Policy-Month", "VPN users usage"));
+ quotaTypeList.put(new Integer(VM_DISK_IO_READ), new QuotaTypes(new Integer(VM_DISK_IO_READ), "VM_DISK_IO_READ", "GB", "VM Disk usage(I/O Read)"));
+ quotaTypeList.put(new Integer(VM_DISK_IO_WRITE), new QuotaTypes(new Integer(VM_DISK_IO_WRITE), "VM_DISK_IO_WRITE", "GB", "VM Disk usage(I/O Write)"));
+ quotaTypeList.put(new Integer(VM_DISK_BYTES_READ), new QuotaTypes(new Integer(VM_DISK_BYTES_READ), "VM_DISK_BYTES_READ", "GB", "VM Disk usage(Bytes Read)"));
+ quotaTypeList.put(new Integer(VM_DISK_BYTES_WRITE), new QuotaTypes(new Integer(VM_DISK_BYTES_WRITE), "VPN_USERS", "GB", "VM Disk usage(Bytes Write)"));
+ quotaTypeList.put(new Integer(VM_SNAPSHOT), new QuotaTypes(new Integer(VM_SNAPSHOT), "VM_SNAPSHOT", "GB-Month", "VM Snapshot storage usage"));
+ quotaTypeList.put(new Integer(CPU_CLOCK_RATE), new QuotaTypes(new Integer(CPU_CLOCK_RATE), "CPU_CLOCK_RATE", "Compute-Month", "Quota tariff for using 1 CPU of clock rate 100MHz"));
+ quotaTypeList.put(new Integer(CPU_NUMBER), new QuotaTypes(new Integer(CPU_NUMBER), "CPU_NUMBER", "Compute-Month", "Quota tariff for running VM that has 1vCPU"));
+ quotaTypeList.put(new Integer(MEMORY), new QuotaTypes(new Integer(MEMORY), "MEMORY", "Compute-Month", "Quota tariff for using 1MB or RAM for 1 hour"));
+ return quotaTypeList;
+ }
+
+ public String getDiscriminator() {
+ return discriminator;
+ }
+
+ public String getQuotaName() {
+ return quotaName;
+ }
+
+ public String getQuotaUnit() {
+ return quotaUnit;
+ }
+
+ public String getDescription() {
+ return description;
+ }
+
+ public Integer getQuotaType() {
+ return quotaType;
+ }
+
+ static public String getDescription(int quotaType) {
+ return listQuotaTypes().get(quotaType).getDescription();
+ }
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDao.java
new file mode 100644
index 0000000..06df664
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDao.java
@@ -0,0 +1,35 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.util.List;
+
+import org.apache.cloudstack.quota.vo.QuotaAccountVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface QuotaAccountDao extends GenericDao<QuotaAccountVO, Long> {
+
+ List<QuotaAccountVO> listAll();
+
+ QuotaAccountVO findById(Long id);
+
+ QuotaAccountVO persist(QuotaAccountVO entity);
+
+ boolean update(Long id, QuotaAccountVO entity);
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDaoImpl.java
new file mode 100644
index 0000000..e2c5e5a
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaAccountDaoImpl.java
@@ -0,0 +1,73 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.apache.cloudstack.quota.vo.QuotaAccountVO;
+import org.springframework.stereotype.Component;
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.TransactionLegacy;
+
+@Component
+@Local(value = { QuotaAccountDao.class })
+public class QuotaAccountDaoImpl extends GenericDaoBase<QuotaAccountVO, Long> implements QuotaAccountDao {
+
+ @Override
+ public List<QuotaAccountVO> listAll() {
+ List<QuotaAccountVO> result = null;
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ result = super.listAll();
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+
+ @Override
+ public QuotaAccountVO findById(Long id) {
+ QuotaAccountVO result = null;
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ result = super.findById(id);
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+
+ @Override
+ public QuotaAccountVO persist(QuotaAccountVO entity) {
+ QuotaAccountVO result = null;
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ result = super.persist(entity);
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+
+ @Override
+ public boolean update(Long id, QuotaAccountVO entity) {
+ boolean result = false;
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ result = super.update(id, entity);
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDao.java
new file mode 100644
index 0000000..8bf07ec
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDao.java
@@ -0,0 +1,43 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.math.BigDecimal;
+import java.util.Date;
+import java.util.List;
+
+import org.apache.cloudstack.quota.vo.QuotaBalanceVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface QuotaBalanceDao extends GenericDao<QuotaBalanceVO, Long> {
+
+ void saveQuotaBalance(List<QuotaBalanceVO> credits);
+
+ List<QuotaBalanceVO> findCreditBalance(long accountId, long domainId, Date startDate, Date endDate);
+
+ QuotaBalanceVO findLastBalanceEntry(long accountId, long domainId, Date beforeThis);
+
+ QuotaBalanceVO findLaterBalanceEntry(long accountId, long domainId, Date afterThis);
+
+ List<QuotaBalanceVO> findQuotaBalance(Long accountId, Long domainId, Date startDate, Date endDate);
+
+ List<QuotaBalanceVO> lastQuotaBalanceVO(Long accountId, Long domainId, Date startDate);
+
+ BigDecimal lastQuotaBalance(Long accountId, Long domainId, Date startDate);
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDaoImpl.java
new file mode 100644
index 0000000..628777e
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaBalanceDaoImpl.java
@@ -0,0 +1,201 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.math.BigDecimal;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.springframework.stereotype.Component;
+import org.apache.cloudstack.quota.vo.QuotaBalanceVO;
+import org.apache.log4j.Logger;
+
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.TransactionLegacy;
+
+@Component
+@Local(value = { QuotaBalanceDao.class })
+public class QuotaBalanceDaoImpl extends GenericDaoBase<QuotaBalanceVO, Long> implements QuotaBalanceDao {
+ private static final Logger s_logger = Logger.getLogger(QuotaBalanceDaoImpl.class.getName());
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public QuotaBalanceVO findLastBalanceEntry(final long accountId, final long domainId, final Date beforeThis) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ Filter filter = new Filter(QuotaBalanceVO.class, "updatedOn", false, 0L, 1L);
+ SearchCriteria<QuotaBalanceVO> sc = createSearchCriteria();
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ sc.addAnd("creditsId", SearchCriteria.Op.EQ, 0);
+ sc.addAnd("updatedOn", SearchCriteria.Op.LT, beforeThis);
+ List<QuotaBalanceVO> quotab = this.search(sc, filter);
+ TransactionLegacy.open(opendb).close();
+ return quotab.size() > 0 ? quotab.get(0) : null;
+ }
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public QuotaBalanceVO findLaterBalanceEntry(final long accountId, final long domainId, final Date afterThis) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ Filter filter = new Filter(QuotaBalanceVO.class, "updatedOn", true, 0L, 1L);
+ SearchCriteria<QuotaBalanceVO> sc = createSearchCriteria();
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ sc.addAnd("creditsId", SearchCriteria.Op.EQ, 0);
+ sc.addAnd("updatedOn", SearchCriteria.Op.GT, afterThis);
+ List<QuotaBalanceVO> quotab = this.search(sc, filter);
+ TransactionLegacy.open(opendb).close();
+ return quotab.size() > 0 ? quotab.get(0) : null;
+ }
+
+ @Override
+ public void saveQuotaBalance(final List<QuotaBalanceVO> credits) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ try {
+ for (QuotaBalanceVO credit : credits) {
+ persist(credit);
+ }
+ } finally {
+ txn.close();
+ }
+ TransactionLegacy.open(opendb).close();
+ }
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public List<QuotaBalanceVO> findCreditBalance(final long accountId, final long domainId, final Date lastbalancedate, final Date beforeThis) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB).close();
+ Filter filter = new Filter(QuotaBalanceVO.class, "updatedOn", true, 0L, Long.MAX_VALUE);
+ SearchCriteria<QuotaBalanceVO> sc = createSearchCriteria();
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ sc.addAnd("creditsId", SearchCriteria.Op.GT, 0);
+ if ((lastbalancedate != null) && (beforeThis != null) && lastbalancedate.before(beforeThis)) {
+ sc.addAnd("updatedOn", SearchCriteria.Op.BETWEEN, lastbalancedate, beforeThis);
+ } else {
+ return new ArrayList<QuotaBalanceVO>();
+ }
+ List<QuotaBalanceVO> qb = search(sc, filter);
+ TransactionLegacy.open(opendb).close();
+ return qb;
+ }
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public List<QuotaBalanceVO> findQuotaBalance(final Long accountId, final Long domainId, final Date startDate, final Date endDate) {
+ // TODO account for series of credits around boundaries
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ List<QuotaBalanceVO> quotaUsageRecords = null;
+ try {
+ SearchCriteria<QuotaBalanceVO> sc = createSearchCriteria();
+ if (accountId != null) {
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ }
+ if (domainId != null) {
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ }
+ if ((startDate != null) && (endDate != null) && startDate.before(endDate)) {
+ sc.addAnd("updatedOn", SearchCriteria.Op.BETWEEN, startDate, endDate);
+ } else {
+ return new ArrayList<QuotaBalanceVO>();
+ }
+ quotaUsageRecords = listBy(sc);
+ if (quotaUsageRecords.size() == 0) {
+ quotaUsageRecords.addAll(lastQuotaBalanceVO(accountId, domainId, startDate));
+ }
+ } finally {
+ txn.close();
+ }
+
+ TransactionLegacy.open(opendb).close();
+ return quotaUsageRecords;
+ }
+
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public List<QuotaBalanceVO> lastQuotaBalanceVO(final Long accountId, final Long domainId, final Date pivotDate) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ List<QuotaBalanceVO> quotaUsageRecords = null;
+ List<QuotaBalanceVO> trimmedRecords = new ArrayList<QuotaBalanceVO>();
+ try {
+ Filter filter = new Filter(QuotaBalanceVO.class, "updatedOn", false, 0L, 100L);
+ // ASSUMPTION there will be less than 100 continuous credit
+ // transactions
+ SearchCriteria<QuotaBalanceVO> sc = createSearchCriteria();
+ if (accountId != null) {
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ }
+ if (domainId != null) {
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ }
+ if ((pivotDate != null)) {
+ sc.addAnd("updatedOn", SearchCriteria.Op.LTEQ, pivotDate);
+ }
+ quotaUsageRecords = search(sc, filter);
+
+ // get records before startDate to find start balance
+ for (Iterator<QuotaBalanceVO> it = quotaUsageRecords.iterator(); it.hasNext();) {
+ QuotaBalanceVO entry = it.next();
+ s_logger.info("findQuotaBalance Date=" + entry.getUpdatedOn().toGMTString() + " balance=" + entry.getCreditBalance() + " credit=" + entry.getCreditsId());
+ if (entry.getCreditsId() > 0) {
+ trimmedRecords.add(entry);
+ } else {
+ trimmedRecords.add(entry);
+ break; // add only consecutive credit entries and last balance entry
+ }
+ }
+
+ } finally {
+ txn.close();
+ }
+
+ TransactionLegacy.open(opendb).close();
+ return trimmedRecords;
+ }
+
+ @Override
+ public BigDecimal lastQuotaBalance(final Long accountId, final Long domainId, Date startDate) {
+ List<QuotaBalanceVO> quotaBalance = lastQuotaBalanceVO(accountId, domainId, startDate);
+ if (quotaBalance.size() == 0) {
+ new InvalidParameterValueException("There are no balance entries on or before the requested date.");
+ }
+ BigDecimal finalBalance = new BigDecimal(0);
+ for (Iterator<QuotaBalanceVO> it = quotaBalance.iterator(); it.hasNext();) {
+ QuotaBalanceVO entry = it.next();
+ s_logger.info("lastQuotaBalance Date=" + entry.getUpdatedOn().toGMTString() + " balance=" + entry.getCreditBalance() + " credit=" + entry.getCreditsId());
+ finalBalance.add(entry.getCreditBalance());
+ }
+ return finalBalance;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDao.java
new file mode 100644
index 0000000..f08d8f9
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDao.java
@@ -0,0 +1,32 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.util.Date;
+import java.util.List;
+
+import org.apache.cloudstack.quota.vo.QuotaCreditsVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface QuotaCreditsDao extends GenericDao<QuotaCreditsVO, Long> {
+
+ List<QuotaCreditsVO> findCredits(long accountId, long domainId, Date startDate, Date endDate);
+
+ QuotaCreditsVO saveCredits(QuotaCreditsVO credits);
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDaoImpl.java
new file mode 100644
index 0000000..05e48b0
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaCreditsDaoImpl.java
@@ -0,0 +1,72 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+
+import org.springframework.stereotype.Component;
+import org.apache.cloudstack.quota.vo.QuotaBalanceVO;
+import org.apache.cloudstack.quota.vo.QuotaCreditsVO;
+
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.TransactionLegacy;
+
+@Component
+@Local(value = { QuotaCreditsDao.class })
+public class QuotaCreditsDaoImpl extends GenericDaoBase<QuotaCreditsVO, Long> implements QuotaCreditsDao {
+ @Inject
+ QuotaBalanceDao _quotaBalanceDao;
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public List<QuotaCreditsVO> findCredits(final long accountId, final long domainId, final Date startDate, final Date endDate) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ Filter filter = new Filter(QuotaCreditsVO.class, "updatedOn", true, 0L, Long.MAX_VALUE);
+ SearchCriteria<QuotaCreditsVO> sc = createSearchCriteria();
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ if ((startDate != null) && (endDate != null) && startDate.before(endDate)) {
+ sc.addAnd("updatedOn", SearchCriteria.Op.BETWEEN, startDate, endDate);
+ } else {
+ return new ArrayList<QuotaCreditsVO>();
+ }
+ List<QuotaCreditsVO> qc = search(sc, filter);
+ TransactionLegacy.open(opendb).close();
+ return qc;
+ }
+
+ @Override
+ public QuotaCreditsVO saveCredits(final QuotaCreditsVO credits) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ persist(credits);
+ // make an entry in the balance table
+ QuotaBalanceVO bal = new QuotaBalanceVO(credits);
+ _quotaBalanceDao.persist(bal);
+ TransactionLegacy.open(opendb).close();
+ return credits;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDao.java
new file mode 100644
index 0000000..573a753
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDao.java
@@ -0,0 +1,27 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import com.cloud.utils.db.GenericDao;
+import org.apache.cloudstack.quota.vo.QuotaEmailTemplatesVO;
+
+import java.util.List;
+
+public interface QuotaEmailTemplatesDao extends GenericDao<QuotaEmailTemplatesVO, Long> {
+ List<QuotaEmailTemplatesVO> listAllQuotaEmailTemplates(String templateName);
+ boolean updateQuotaEmailTemplate(QuotaEmailTemplatesVO template);
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDaoImpl.java
new file mode 100644
index 0000000..c7b4908
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaEmailTemplatesDaoImpl.java
@@ -0,0 +1,64 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.TransactionLegacy;
+import org.apache.cloudstack.quota.vo.QuotaEmailTemplatesVO;
+import org.springframework.stereotype.Component;
+
+import javax.ejb.Local;
+import java.util.List;
+
+@Component
+@Local(value = { QuotaEmailTemplatesDao.class })
+public class QuotaEmailTemplatesDaoImpl extends GenericDaoBase<QuotaEmailTemplatesVO, Long> implements QuotaEmailTemplatesDao {
+
+ protected SearchBuilder<QuotaEmailTemplatesVO> QuotaEmailTemplateSearch;
+
+ public QuotaEmailTemplatesDaoImpl() {
+ super();
+
+ QuotaEmailTemplateSearch = createSearchBuilder();
+ QuotaEmailTemplateSearch.and("template_name", QuotaEmailTemplateSearch.entity().getTemplateName(), SearchCriteria.Op.EQ);
+ QuotaEmailTemplateSearch.done();
+ }
+
+ @Override
+ public List<QuotaEmailTemplatesVO> listAllQuotaEmailTemplates(String templateName) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ SearchCriteria<QuotaEmailTemplatesVO> sc = QuotaEmailTemplateSearch.create();
+ if (templateName != null) {
+ sc.setParameters("template_name", templateName);
+ }
+ List<QuotaEmailTemplatesVO> result = this.listBy(sc);
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+
+ @Override
+ public boolean updateQuotaEmailTemplate(QuotaEmailTemplatesVO template) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ final boolean result = this.update(template.getId(), template);
+ TransactionLegacy.open(opendb).close();
+ return result;
+ }
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDao.java
new file mode 100644
index 0000000..7977f28
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDao.java
@@ -0,0 +1,35 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import com.cloud.utils.db.GenericDao;
+
+import org.apache.cloudstack.quota.vo.QuotaTariffVO;
+
+import java.util.Date;
+import java.util.List;
+
+public interface QuotaTariffDao extends GenericDao<QuotaTariffVO, Long> {
+
+ QuotaTariffVO findTariffPlanByUsageType(int quotaType, Date onOrBefore);
+
+ List<QuotaTariffVO> listAllTariffPlans(Date onOrBefore);
+
+ boolean updateQuotaTariff(QuotaTariffVO plan);
+
+ QuotaTariffVO addQuotaTariff(QuotaTariffVO plan);
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDaoImpl.java
new file mode 100644
index 0000000..38aad15
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaTariffDaoImpl.java
@@ -0,0 +1,138 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.TransactionLegacy;
+
+import org.apache.cloudstack.quota.constant.QuotaTypes;
+import org.apache.cloudstack.quota.vo.QuotaTariffVO;
+import org.apache.log4j.Logger;
+import org.springframework.stereotype.Component;
+
+import javax.ejb.Local;
+
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+@Component
+@Local(value = { QuotaTariffDao.class })
+public class QuotaTariffDaoImpl extends GenericDaoBase<QuotaTariffVO, Long> implements QuotaTariffDao {
+ private static final Logger s_logger = Logger.getLogger(QuotaTariffDaoImpl.class.getName());
+
+ private final SearchBuilder<QuotaTariffVO> searchUsageType;
+ private final SearchBuilder<QuotaTariffVO> listAllIncludedUsageType;
+
+ public QuotaTariffDaoImpl() {
+ super();
+ searchUsageType = createSearchBuilder();
+ searchUsageType.and("usage_type", searchUsageType.entity().getUsageType(), SearchCriteria.Op.EQ);
+ searchUsageType.done();
+
+ listAllIncludedUsageType = createSearchBuilder();
+ listAllIncludedUsageType.and("onorbefore", listAllIncludedUsageType.entity().getEffectiveOn(), SearchCriteria.Op.LTEQ);
+ listAllIncludedUsageType.and("quotatype", listAllIncludedUsageType.entity().getUsageType(), SearchCriteria.Op.EQ);
+ listAllIncludedUsageType.done();
+ }
+
+ @Override
+ public QuotaTariffVO findTariffPlanByUsageType(final int quotaType, final Date effectiveDate) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ List<QuotaTariffVO> result = null;
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ try {
+ final Filter filter = new Filter(QuotaTariffVO.class, "effectiveOn", false, 0L, 1L);
+ final SearchCriteria<QuotaTariffVO> sc = listAllIncludedUsageType.create();
+ sc.setParameters("onorbefore", effectiveDate);
+ sc.setParameters("quotatype", quotaType);
+ result = search(sc, filter);
+ } finally {
+ txn.close();
+ }
+ // Switch back
+ TransactionLegacy.open(opendb).close();
+ if (result.size() > 0) {
+ //s_logger.info("findTariffPlanByUsageType: " + effectiveDate + "quota type " + quotaType + " val=" + result.get(0).getCurrencyValue());
+ return result.get(0);
+ } else {
+ //s_logger.info("Missing quota type " + quotaType);
+ return null;
+ }
+ }
+
+ @Override
+ public List<QuotaTariffVO> listAllTariffPlans(final Date effectiveDate) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ List<QuotaTariffVO> tariffs = new ArrayList<QuotaTariffVO>();
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ try {
+ final Filter filter = new Filter(QuotaTariffVO.class, "effectiveOn", false, 0L, 1L);
+ final SearchCriteria<QuotaTariffVO> sc = listAllIncludedUsageType.create();
+ sc.setParameters("onorbefore", effectiveDate);
+ for (Integer quotaType : QuotaTypes.listQuotaTypes().keySet()) {
+ sc.setParameters("quotatype", quotaType);
+ List<QuotaTariffVO> result = search(sc, filter);
+ if (result.size() > 0) {
+ tariffs.add(result.get(0));
+ s_logger.info("listAllTariffPlans onorbefore" + effectiveDate + "quota type " + result.get(0).getDescription() + " , effective Date=" + result.get(0).getEffectiveOn() + " val=" + result.get(0).getCurrencyValue());
+ }
+ }
+ } finally {
+ txn.close();
+ }
+ // Switch back
+ TransactionLegacy.open(opendb).close();
+ return tariffs;
+ }
+
+ @Override
+ public boolean updateQuotaTariff(QuotaTariffVO plan) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB); // Switch
+ // to
+ boolean result = false;
+ try {
+ // Usage DB
+ result = this.update(plan.getId(), plan);
+ } finally {
+ txn.close();
+ }
+ TransactionLegacy.open(opendb).close(); // Switch back
+ return result;
+ }
+
+ @Override
+ public QuotaTariffVO addQuotaTariff(QuotaTariffVO plan) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB); // Switch
+ // to
+ QuotaTariffVO result = null;
+ try {
+ // Usage DB
+ plan.setId(null);
+ result = this.persist(plan);
+ } finally {
+ txn.close();
+ }
+ TransactionLegacy.open(opendb).close(); // Switch back
+ return result;
+ }
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDao.java
new file mode 100644
index 0000000..79c55ce
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDao.java
@@ -0,0 +1,40 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.math.BigDecimal;
+import java.util.Date;
+import java.util.List;
+
+import org.apache.cloudstack.quota.vo.QuotaUsageVO;
+
+import com.cloud.utils.Pair;
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDao;
+import com.cloud.utils.db.SearchCriteria;
+
+public interface QuotaUsageDao extends GenericDao<QuotaUsageVO, Long> {
+
+ List<QuotaUsageVO> findQuotaUsage(Long accountId, Long domainId, Integer usageType, Date startDate, Date endDate);
+
+ Pair<List<QuotaUsageVO>, Integer> searchAndCountAllRecords(SearchCriteria<QuotaUsageVO> sc, Filter filter);
+
+ void saveQuotaUsage(List<QuotaUsageVO> credits);
+
+ BigDecimal findTotalQuotaUsage(Long accountId, Long domainId, Integer usageType, Date startDate, Date endDate);
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDaoImpl.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDaoImpl.java b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDaoImpl.java
new file mode 100644
index 0000000..bff43d0
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/QuotaUsageDaoImpl.java
@@ -0,0 +1,106 @@
+//Licensed to the Apache Software Foundation (ASF) under one
+//or more contributor license agreements. See the NOTICE file
+//distributed with this work for additional information
+//regarding copyright ownership. The ASF licenses this file
+//to you under the Apache License, Version 2.0 (the
+//"License"); you may not use this file except in compliance
+//with the License. You may obtain a copy of the License at
+//
+//http://www.apache.org/licenses/LICENSE-2.0
+//
+//Unless required by applicable law or agreed to in writing,
+//software distributed under the License is distributed on an
+//"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+//KIND, either express or implied. See the License for the
+//specific language governing permissions and limitations
+//under the License.
+package org.apache.cloudstack.quota.dao;
+
+import java.math.BigDecimal;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.springframework.stereotype.Component;
+import org.apache.cloudstack.quota.vo.QuotaUsageVO;
+
+import com.cloud.utils.Pair;
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.TransactionLegacy;
+
+@Component
+@Local(value = { QuotaUsageDao.class })
+public class QuotaUsageDaoImpl extends GenericDaoBase<QuotaUsageVO, Long> implements QuotaUsageDao {
+
+ @Override
+ public Pair<List<QuotaUsageVO>, Integer> searchAndCountAllRecords(SearchCriteria<QuotaUsageVO> sc, Filter filter) {
+ return listAndCountIncludingRemovedBy(sc, filter);
+ }
+
+ @Override
+ public void saveQuotaUsage(List<QuotaUsageVO> records) {
+ for (QuotaUsageVO usageRecord : records) {
+ persist(usageRecord);
+ }
+ }
+
+ @Override
+ public BigDecimal findTotalQuotaUsage(final Long accountId, final Long domainId, final Integer usageType, final Date startDate, final Date endDate) {
+ List<QuotaUsageVO> quotaUsage = findQuotaUsage(accountId, domainId, null, startDate, endDate);
+ BigDecimal total = new BigDecimal(0);
+ for (final QuotaUsageVO quotaRecord : quotaUsage) {
+ total = total.add(quotaRecord.getQuotaUsed());
+ }
+ return total;
+ }
+
+ @SuppressWarnings("deprecation")
+ @Override
+ public List<QuotaUsageVO> findQuotaUsage(final Long accountId, final Long domainId, final Integer usageType, final Date startDate, final Date endDate) {
+ final short opendb = TransactionLegacy.currentTxn().getDatabaseId();
+ TransactionLegacy txn = TransactionLegacy.open(TransactionLegacy.USAGE_DB);
+ List<QuotaUsageVO> quotaUsageRecords = null;
+ try {
+ // TODO instead of max value query with reasonable number and
+ // iterate
+ SearchCriteria<QuotaUsageVO> sc = createSearchCriteria();
+ if (accountId != null) {
+ sc.addAnd("accountId", SearchCriteria.Op.EQ, accountId);
+ }
+ /*
+ * if (isDomainAdmin) { SearchCriteria<DomainVO> sdc =
+ * _domainDao.createSearchCriteria(); sdc.addOr("path",
+ * SearchCriteria.Op.LIKE,
+ * _domainDao.findById(caller.getDomainId()).getPath() + "%");
+ * List<DomainVO> domains = _domainDao.search(sdc, null); List<Long>
+ * domainIds = new ArrayList<Long>(); for (DomainVO domain :
+ * domains) domainIds.add(domain.getId()); sc.addAnd("domainId",
+ * SearchCriteria.Op.IN, domainIds.toArray());
+ * s_logger.debug("Account ID=" + accountId); }
+ */
+ if (domainId != null) {
+ sc.addAnd("domainId", SearchCriteria.Op.EQ, domainId);
+ }
+ if (usageType != null) {
+ sc.addAnd("usageType", SearchCriteria.Op.EQ, usageType);
+ }
+ if ((startDate != null) && (endDate != null) && startDate.before(endDate)) {
+ sc.addAnd("startDate", SearchCriteria.Op.BETWEEN, startDate, endDate);
+ sc.addAnd("endDate", SearchCriteria.Op.BETWEEN, startDate, endDate);
+ } else {
+ return new ArrayList<QuotaUsageVO>();
+ }
+ quotaUsageRecords = listBy(sc);
+ } finally {
+ txn.close();
+ }
+
+ TransactionLegacy.open(opendb).close();
+ return quotaUsageRecords;
+ }
+
+}
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/dedb351f/framework/quota/src/org/apache/cloudstack/quota/dao/ServiceOfferingDao.java
----------------------------------------------------------------------
diff --git a/framework/quota/src/org/apache/cloudstack/quota/dao/ServiceOfferingDao.java b/framework/quota/src/org/apache/cloudstack/quota/dao/ServiceOfferingDao.java
new file mode 100644
index 0000000..5d340e3
--- /dev/null
+++ b/framework/quota/src/org/apache/cloudstack/quota/dao/ServiceOfferingDao.java
@@ -0,0 +1,27 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package org.apache.cloudstack.quota.dao;
+
+import org.apache.cloudstack.quota.vo.ServiceOfferingVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface ServiceOfferingDao extends GenericDao<ServiceOfferingVO, Long> {
+
+ ServiceOfferingVO findServiceOffering(Long vmId, long serviceOfferingId);
+
+}