/* * ProActive Parallel Suite(TM): * The Open Source library for parallel and distributed * Workflows & Scheduling, Orchestration, Cloud Automation * and Big Data Analysis on Enterprise Grids & Clouds. * * Copyright (c) 2007 - 2017 ActiveEon * Contact: contact@activeeon.com * * This library is free software: you can redistribute it and/or * modify it under the terms of the GNU Affero General Public License * as published by the Free Software Foundation: version 3 of * the License. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. * * If needed, contact us to obtain a release under GPL Version 2 or 3 * or a different license than the AGPL. */ package org.ow2.proactive.resourcemanager.core.account; import java.util.List; import javax.persistence.Column; import javax.persistence.Table; import org.apache.log4j.Logger; import org.ow2.proactive.account.AbstractAccountsManager; import org.ow2.proactive.resourcemanager.core.history.NodeHistory; import org.ow2.proactive.resourcemanager.core.properties.PAResourceManagerProperties; import org.ow2.proactive.resourcemanager.db.RMDBManager; /** * This class represents the Resource Manager accounts manager. * * @author The ProActive Team * @since ProActive Scheduling 2.1 */ public final class RMAccountsManager extends AbstractAccountsManager<RMAccount> { /** Scheduler database manager used to submit SQL requests */ private final RMDBManager dbmanager; /** * Create a new instance of this class. */ public RMAccountsManager() { super("Resource Manager Accounts Refresher", Logger.getLogger(RMAccountsManager.class)); // Get the database manager this.dbmanager = RMDBManager.getInstance(); } /** * {@inheritDoc} */ @Override public int getDefaultCacheValidityTimeInSeconds() { int value = PAResourceManagerProperties.RM_ACCOUNT_REFRESH_RATE.getValueAsInt(); return value; } /** * * Computes user account data by scanning the data base. * */ public RMAccount readAccount(final String user) { try { RMAccount account = new RMAccount(); account.username = user; String history = NodeHistory.class.getAnnotation(Table.class).name(); String endTime = NodeHistory.class.getDeclaredField("endTime").getAnnotation(Column.class).name(); String startTime = NodeHistory.class.getDeclaredField("startTime").getAnnotation(Column.class).name(); String nodeState = NodeHistory.class.getDeclaredField("nodeState").getAnnotation(Column.class).name(); String userName = NodeHistory.class.getDeclaredField("userName").getAnnotation(Column.class).name(); String providerName = NodeHistory.class.getDeclaredField("providerName").getAnnotation(Column.class).name(); String nodeUrl = NodeHistory.class.getDeclaredField("nodeUrl").getAnnotation(Column.class).name(); // counting the time of finished actions // select SUM(endTime-startTime) from History where endTime <> 0 and nodeState = 1 and userName='NAME' String wereBusy = "SELECT SUM(" + endTime + "-" + startTime + ") " + "FROM " + history + " WHERE " + userName + "='" + user + "' AND " + endTime + " <> 0 AND " + nodeState + " = 1"; List<?> rows = dbmanager.executeSqlQuery(wereBusy); account.usedNodeTime += aggregateNodeUsageTime(rows); String areBusy = "SELECT SUM(" + System.currentTimeMillis() + "-" + startTime + ") " + "FROM " + history + " WHERE " + userName + "='" + user + "' AND " + endTime + " = 0 AND " + nodeState + " = 1"; rows = dbmanager.executeSqlQuery(areBusy); account.usedNodeTime += aggregateNodeUsageTime(rows); // select SUM(endTime-startTime), COUNT(DISTINCT nodeUrl) from History where endTime <> 0 and nodeState in (0,1,3,6) and providerName='rm' String wereProvided = "SELECT COUNT(DISTINCT " + nodeUrl + "), SUM(" + endTime + "-" + startTime + ") " + "FROM " + history + " WHERE " + providerName + "='" + user + "' AND " + endTime + " <> 0 AND " + nodeState + " in (0,1,3,6)"; // select SUM(CURRNET_TIME-startTime), COUNT(DISTINCT nodeUrl) from History where endTime = 0 and nodeState in (0,1,3,6) and providerName='rm' String areProvided = "SELECT 0, SUM(" + System.currentTimeMillis() + "-" + startTime + ") " + "FROM " + history + " WHERE " + providerName + "='" + user + "' AND " + endTime + " = 0 AND " + nodeState + " in (0,1,3,6)"; rows = dbmanager.executeSqlQuery(wereProvided); account.providedNodesCount += aggregateProvidedNodesCount(rows); account.providedNodeTime += aggregateProvidedNodeTime(rows); rows = dbmanager.executeSqlQuery(areProvided); account.providedNodesCount += aggregateProvidedNodesCount(rows); account.providedNodeTime += aggregateProvidedNodeTime(rows); return account; } catch (Exception e) { throw new RuntimeException(e); } } private int aggregateNodeUsageTime(List<?> rows) { int usedNodeTime = 0; for (Object row : rows) { try { if (row != null) { // result could be empty or null usedNodeTime += Long.parseLong(row.toString()); } } catch (RuntimeException e) { logger.warn(e.getMessage(), e); usedNodeTime = 0; } } return usedNodeTime; } private int aggregateProvidedNodesCount(List<?> rows) { int providedNodesCount = 0; for (Object row : rows) { Object[] columns = (Object[]) row; if (columns.length > 0 && columns[0] != null) { try { // result could be empty or null providedNodesCount += Integer.parseInt(columns[0].toString()); } catch (RuntimeException e) { logger.warn(e.getMessage(), e); providedNodesCount = 0; } } } return providedNodesCount; } private int aggregateProvidedNodeTime(List<?> rows) { int providedNodeTime = 0; for (Object row : rows) { Object[] columns = (Object[]) row; if (columns.length > 1 && columns[1] != null) { try { // result could be empty or null providedNodeTime += Long.parseLong(columns[1].toString()); } catch (RuntimeException e) { logger.warn(e.getMessage(), e); providedNodeTime = 0; } } } return providedNodeTime; } }