diff --git a/classes/DataWarehouse/Query/Jobs/JobDataset.php b/classes/DataWarehouse/Query/Jobs/JobDataset.php new file mode 100644 index 0000000000..bdfda9ad84 --- /dev/null +++ b/classes/DataWarehouse/Query/Jobs/JobDataset.php @@ -0,0 +1,127 @@ +getDataTable(); + $joblistTable = new Table($dataTable->getSchema(), $dataTable->getName() . "_joblist", "jl"); + $factTable = new Table(new Schema('modw'), 'job_tasks', 'jt'); + + $this->addTable($joblistTable ); + $this->addTable($factTable ); + + $this->addWhereCondition(new WhereCondition( + new TableField($joblistTable, "agg_id"), + "=", + new TableField($dataTable, "id") + )); + $this->addWhereCondition(new WhereCondition( + new TableField($joblistTable, "jobid"), + "=", + new TableField($factTable, "job_id") + )); + + if (isset($parameters['primary_key'])) { + $this->addPdoWhereCondition(new WhereCondition(new TableField($factTable, 'job_id'), "=", $parameters['primary_key'])); + } else { + $matches = array(); + if (preg_match('/^(\d+)(?:[\[_](\d+)\]?)?$/', $parameters['job_identifier'], $matches)) { + $this->addPdoWhereCondition(new WhereCondition(new TableField($factTable, 'resource_id'), '=', $parameters['resource_id'])); + if (isset($matches[2])) { + $this->addPdoWhereCondition(new WhereCondition(new TableField($factTable, 'local_jobid'), '=', $matches[1])); + $this->addPdoWhereCondition(new WhereCondition(new TableField($factTable, 'local_job_array_index'), '=', $matches[2])); + } else { + $this->addPdoWhereCondition(new WhereCondition(new TableField($factTable, 'local_job_id_raw'), '=', $matches[1])); + } + } else { + throw new \Exception('invalid query parameters'); + } + } + + if ($stat == "accounting") { + $i = 0; + foreach ($config['rawstatistics']['modw.job_tasks'] as $sdata) { + $sfield = $sdata['key']; + if ($sdata['dtype'] == 'accounting') { + $this->addField(new TableField($factTable, $sfield)); + $this->documentation[$sfield] = $sdata; + } elseif ($sdata['dtype'] == 'foreignkey') { + if (isset($sdata['join'])) { + $info = $sdata['join']; + $i += 1; + $tmptable = new Table(new Schema($info['schema']), $info['table'], "ft$i"); + $this->addTable($tmptable); + $this->addWhereCondition(new WhereCondition(new TableField($factTable, $sfield), '=', new TableField($tmptable, "id"))); + $fcol = isset($info['column']) ? $info['column'] : 'name'; + $this->addField(new TableField($tmptable, $fcol, $sdata['name'])); + + $this->documentation[ $sdata['name'] ] = $sdata; + } + } + } + $rf = new Table(new Schema('modw'), 'resourcefact', 'rf'); + $this->addTable($rf); + $this->addWhereCondition(new WhereCondition(new TableField($factTable, 'resource_id'), '=', new TableField($rf, 'id'))); + $this->addField(new TableField($rf, 'timezone')); + $this->documentation['timezone'] = array( + "name" => "Timezone", + "documentation" => "The timezone of the resource.", + "group" => "Administration", + 'visibility' => 'public', + "per" => "resource"); + } + else + { + $this->addField(new TableField($factTable, "job_id", "jobid")); + $this->addField(new TableField($factTable, "local_jobid", "local_job_id")); + + $rt = new Table(new Schema("modw"), "resourcefact", "rf"); + $this->joinTo($rt, "task_resource_id", "code", "resource"); + + $pt = new Table(new Schema('modw'), 'person', 'p'); + $this->joinTo($pt, "person_id", "long_name", "name"); + + $st = new Table(new Schema('modw'), 'systemaccount', 'sa'); + $this->joinTo($st, "systemaccount_id", "username", "username"); + } + } + + /** + * helper function to join the data table to another table + */ + private function joinTo($othertable, $joinkey, $otherkey, $colalias, $idcol = "id") + { + $this->addTable($othertable); + $this->addWhereCondition(new WhereCondition(new TableField($this->getDataTable(), $joinkey), '=', new TableField($othertable, $idcol))); + $this->addField(new TableField($othertable, $otherkey, $colalias)); + } + + public function getColumnDocumentation() + { + return $this->documentation; + } +} diff --git a/classes/DataWarehouse/Query/Jobs/JobMetadata.php b/classes/DataWarehouse/Query/Jobs/JobMetadata.php new file mode 100644 index 0000000000..c52b86f175 --- /dev/null +++ b/classes/DataWarehouse/Query/Jobs/JobMetadata.php @@ -0,0 +1,93 @@ +lookupJob($user, $jobid); + if ($job == null) { + return array(); + } + + return array( + \DataWarehouse\Query\RawQueryTypes::ACCOUNTING => true + ); + } + + /* + * Note there is no job summary data available in the Jobs realm + */ + public function getJobSummary(XDUser $user, $jobid) + { + return array(); + } + + /* + * Note there is no job executable data available in the Jobs realm + */ + public function getJobExecutableInfo(XDUser $user, $jobid) + { + return array(); + } + + /* + * Note there is no job timeseries data available in the Jobs realm + */ + public function getJobTimeseriesMetaData(XDUser $user, $jobid) + { + return array(); + } + + /* + * Note there is no job timeseries data available in the Jobs realm + */ + public function getJobTimeseriesMetricMeta(XDUser $user, $jobid, $tsid) + { + return array(); + } + + /* + * Note there is no job timeseries data available in the Jobs realm + */ + public function getJobTimeseriesMetricNodeMeta(XDUser $user, $jobid, $tsid, $nodeid) + { + return array(); + } + + /* + * Note there is no job timeseries data available in the Jobs realm + */ + public function getJobTimeseriesData(XDUser $user, $jobid, $tsid, $nodeid, $cpuid) + { + return array(); + } + + /** + * Lookup the job in the datawarehouse to check that it exists and the + * user has permission to view it. + * + * @param XDUser $user The user to lookup the job for. + * @param $jobid the unique identifier for the job. + * + * @return array() the accounting data for the job or null if no job exists or permission denied + */ + private function lookupJob(XDUser $user, $jobid) + { + $query = new \DataWarehouse\Query\Jobs\JobDataset(array('primary_key' => $jobid)); + $query->setMultipleRoleParameters($user->getAllRoles(), $user); + $stmt = $query->getRawStatement(); + + $job = $stmt->fetchAll(\PDO::FETCH_ASSOC); + if (count($job) != 1) { + return null; + } + return $job[0]; + } +} diff --git a/classes/DataWarehouse/Query/Jobs/RawData.php b/classes/DataWarehouse/Query/Jobs/RawData.php new file mode 100644 index 0000000000..55038b23fb --- /dev/null +++ b/classes/DataWarehouse/Query/Jobs/RawData.php @@ -0,0 +1,163 @@ +getDataTable(); + $joblistTable = new Table($dataTable->getSchema(), $dataTable->getName() . "_joblist", "jl"); + $factTable = new Table(new Schema('modw'), "job_tasks", "jt" ); + + $resourcefactTable = new Table(new Schema('modw'), 'resourcefact', 'rf'); + $this->addTable($resourcefactTable); + + $this->addWhereCondition(new WhereCondition( + new TableField($dataTable, "task_resource_id"), + '=', + new TableField($resourcefactTable, "id") + )); + + $personTable = new Table(new Schema('modw'), 'person', 'p'); + + $this->addTable($personTable); + $this->addWhereCondition(new WhereCondition( + new TableField($dataTable, "person_id"), + '=', + new TableField($personTable, "id") + )); + + $this->addField(new TableField($resourcefactTable, "code", 'resource')); + $this->addField(new TableField($personTable, "long_name", "name")); + + $this->addField(new TableField($factTable, "job_id", "jobid") ); + $this->addField(new TableField($factTable, "local_jobid", "local_job_id") ); + + $this->addTable($joblistTable ); + $this->addTable($factTable ); + + $this->addWhereCondition(new WhereCondition( + new TableField($joblistTable, "agg_id"), + "=", + new TableField($dataTable, "id") + )); + $this->addWhereCondition(new WhereCondition( + new TableField($joblistTable, "jobid"), + "=", + new TableField($factTable, "job_id") + )); + + switch($stat) { + case "job_count": + $this->addWhereCondition(new WhereCondition("jt.end_time_ts", "between", "d.day_start_ts and d.day_end_ts") ); + break; + case "started_job_count": + $this->addWhereCondition(new WhereCondition("jt.start_time_ts", "between", "d.day_start_ts and d.day_end_ts") ); + break; + default: + // All other metrics show running job count + break; + } + } + + /** + * The query differs from the base class query because the same fact table row + * may correspond to multiple rows in the aggregate table (e.g. a job that runs over + * two days). Therefore the DISTINCT keyword is added to dedupliate. + */ + public function getQueryString($limit = null, $offset = null, $extraHavingClause = null) + { + $wheres = $this->getWhereConditions(); + $groups = $this->getGroups(); + + $select_tables = $this->getSelectTables(); + $select_fields = $this->getSelectFields(); + + $select_order_by = $this->getSelectOrderBy(); + + $data_query = "SELECT DISTINCT ".implode(", ", $select_fields). + " FROM ".implode(", ", $select_tables). + " WHERE ".implode(" AND ", $wheres); + + if(count($groups) > 0) + { + $data_query .= " GROUP BY \n".implode(",\n", $groups); + } + if($extraHavingClause != null) + { + $data_query .= " HAVING " . $extraHavingClause . "\n"; + } + if(count($select_order_by) > 0) + { + $data_query .= " ORDER BY \n".implode(",\n", $select_order_by); + } + + if($limit !== null && $offset !== null) + { + $data_query .= " LIMIT $limit OFFSET $offset"; + } + return $data_query; + } + + /** + * The query differs from the base class query because the same fact table row + * may correspond to multiple rows in the aggregate table (e.g. a job that runs over + * two days). Therefore the DISTINCT keyword is added to dedupliate. + */ + public function getCountQueryString() + { + $wheres = $this->getWhereConditions(); + $groups = $this->getGroups(); + + $select_tables = $this->getSelectTables(); + $select_fields = $this->getSelectFields(); + + $data_query = "SELECT COUNT(*) AS row_count FROM (SELECT DISTINCT ".implode(", ", $select_fields). + " FROM ".implode(", ", $select_tables). + " WHERE ".implode(" AND ", $wheres); + + if(count($groups) > 0) + { + $data_query .= " GROUP BY \n".implode(",\n", $groups); + } + return $data_query . ') as a'; + } +} diff --git a/classes/OpenXdmod/Migration/DatabasesMigration.php b/classes/OpenXdmod/Migration/DatabasesMigration.php index 991f20699b..2edddf9f8f 100644 --- a/classes/OpenXdmod/Migration/DatabasesMigration.php +++ b/classes/OpenXdmod/Migration/DatabasesMigration.php @@ -150,4 +150,39 @@ protected function requestMysqlAdminCredentials() return self::$mysqlAdminCredentials; } + + /** + * Run an etlv2 action. + * + * This helper function provides the necessary boilerplate to execute + * an etlv2 pipeline. + * + * @param array $scriptOptions the options to pass to the etlv2 class + */ + protected function runEtlv2(array $scriptOptions) { + if (empty($scriptOptions['chunk-size-days'])) { + $scriptOptions['chunk-size-days'] = 365; + } + if (empty($scriptOptions['default-module-name'])) { + $scriptOptions['default-module-name'] = 'xdmod'; + } + if(empty($scriptOptions['start-date'])){ + $scriptOptions['start-date'] = date('Y-m-d', strtotime('2000-01-01')); + } + if(empty($scriptOptions['end-date'])){ + $scriptOptions['end-date'] = date('Y-m-d', strtotime('2038-01-18')); + } + if(empty($scriptOptions['last-modified-start-date'])){ + $scriptOptions['last-modified-start-date'] = date('Y-m-d'); + } + + $etlConfig = new \ETL\Configuration\EtlConfiguration(CONFIG_DIR . '/etl/etl.json', null, $this->logger, array('default_module_name' => $scriptOptions['default-module-name'])); + $etlConfig->initialize(); + \ETL\Utilities::setEtlConfig($etlConfig); + + $overseerOptions = new \ETL\EtlOverseerOptions($scriptOptions, $this->logger); + + $overseer = new \ETL\EtlOverseer($overseerOptions, $this->logger); + $overseer->execute($etlConfig); + } } diff --git a/classes/OpenXdmod/Migration/Version800To810/DatabasesMigration.php b/classes/OpenXdmod/Migration/Version800To810/DatabasesMigration.php new file mode 100644 index 0000000000..d42113ece6 --- /dev/null +++ b/classes/OpenXdmod/Migration/Version800To810/DatabasesMigration.php @@ -0,0 +1,67 @@ +displayMessage(<<<"EOT" +This release includes an update that enables the Job Viewer tab and the 'show raw +data' drilldown in the Metric Explorer for Jobs realm data. It is recommended +to reaggregate all jobs. Depending on the amount of data this could take multiple +hours. If the job data is not reaggregated then existing jobs will not be viewable +in the Job Viewer. +EOT + ); + $runaggregation = $console->promptBool( + 'Do you want to run aggregation now?', + false + ); + if (true === $runaggregation) { + $this->runEtlv2( + array( + 'process-sections' => array('jobs-xdw-aggregate'), + 'last-modified-start-date' => date('Y-m-d', strtotime('2000-01-01')), + ) + ); + $this->logger->notice('Rebuilding filter lists'); + try { + $builder = new FilterListBuilder(); + $builder->setLogger($this->logger); + $builder->buildRealmLists('Jobs'); + } catch (Exception $e) { + $this->logger->notice('Failed BuildAllLists: ' . $e->getMessage()); + $this->logger->crit(array( + 'message' => 'Filter list building failed: ' . $e->getMessage(), + 'stacktrace' => $e->getTraceAsString(), + )); + throw new \Exception('Filter list building failed: ' . $e->getMessage()); + } + $this->logger->notice('Done building filter lists'); + } + else { + $console->displayMessage(<<<"EOT" +Aggregation not run. Aggregation may be run manually with the following command: +xdmod-ingestor --aggregate --last-modified-start-date '2000-01-01' +EOT + ); + } + } +} diff --git a/configuration/etl/etl.d/xdmod-migration-8_0_0-8_1_0.json b/configuration/etl/etl.d/xdmod-migration-8_0_0-8_1_0.json new file mode 100644 index 0000000000..b9be4b990b --- /dev/null +++ b/configuration/etl/etl.d/xdmod-migration-8_0_0-8_1_0.json @@ -0,0 +1,24 @@ +{ + "module": "xdmod", + "migration-8_0_0-8_1_0": [ + { + "name": "update-modw_aggregates-tables", + "description": "Update modw_aggregates tables", + "namespace": "ETL\\Maintenance", + "class": "ManageTables", + "options_class": "MaintenanceOptions", + "definition_file_list": [ + "jobs/xdw/jobfact_by_day.json", + "jobs/xdw/jobfact_by_day_joblist.json" + ], + "endpoints": { + "destination": { + "type": "mysql", + "name": "Aggregate tables", + "config": "database", + "schema": "modw_aggregates" + } + } + } + ] +} diff --git a/configuration/etl/etl_action_defs.d/jobs/hpc-aggregation-day.json b/configuration/etl/etl_action_defs.d/jobs/hpc-aggregation-day.json new file mode 100644 index 0000000000..7107ff1c82 --- /dev/null +++ b/configuration/etl/etl_action_defs.d/jobs/hpc-aggregation-day.json @@ -0,0 +1,163 @@ +{ + "#": "Aggregation of HPC job records and tasks ingested from the XDCDB", + "table_definition": { + "$ref": "${table_definition_dir}/jobs/xdw/jobfact_by_day.json#/table_definition" + }, + + "#": "The aggregation period query determines which periods need to be aggregated based on added or modified", + "#": "records. The overseer_restrictions block specifies the criteria for selecting periods requiring", + "#": "aggregation. If this clause is not specified or no restrictions match then all records will be", + "#": "considered. The first table specified in source_query.joins will be used to determine periods that", + "#": "need aggregation.", + "aggregation_period_query": { + "overseer_restrictions": { + "last_modified_start_date": "last_modified >= ${VALUE}", + "last_modified_end_date": "last_modified <= ${VALUE}", + "include_only_resource_codes": "resource_id IN ${VALUE}", + "exclude_resource_codes": "resource_id NOT IN ${VALUE}" + } + }, + + "#": "The destination query block allows us to specify overseer restrictions that apply to operations on", + "#": "the destination table (e.g., deleting records from the table during aggregation). If no restrictions", + "#": "are specified then the entire aggregation period will be deleted. Note that if there is a restriction", + "#": "on the source_query block it is possible to delete an aggregation period from the destination table", + "#": "with no restictions and replace it with aggregated data that has been restricted.", + "destination_query": { + "overseer_restrictions": { + "include_only_resource_codes": "record_resource_id IN ${VALUE}", + "exclude_resource_codes": "record_resource_id NOT IN ${VALUE}" + } + }, + "source_query": { + "overseer_restrictions": { + "include_only_resource_codes": "record.resource_id IN ${VALUE}", + "exclude_resource_codes": "record.resource_id NOT IN ${VALUE}" + }, + "query_hint": "SQL_NO_CACHE", + "records": { + "${AGGREGATION_UNIT}_id": "${:PERIOD_ID}", + "year": "${:YEAR_VALUE}", + "${AGGREGATION_UNIT}": "${:PERIOD_VALUE}", + "record_resource_id": "record.resource_id", + "task_resource_id": "task.resource_id", + "resource_organization_id": "requested_resource.organization_id", + "resourcetype_id": "requested_resource.resourcetype_id", + "systemaccount_id": "task.systemaccount_id", + "submission_venue_id": "record.submission_venue_id", + "job_record_type_id": "record.job_record_type_id", + "job_task_type_id": "task.job_task_type_id", + "queue": "record.queue", + "allocation_id": "record.allocation_id", + "account_id": "record.account_id", + "requesting_person_id": "record.person_id", + "person_id": "task.person_id", + "person_organization_id": "task.person_organization_id", + "person_nsfstatuscode_id": "task.person_nsfstatuscode_id", + "fos_id": "record.fos_id", + "principalinvestigator_person_id": "record.principalinvestigator_person_id", + "piperson_organization_id": "COALESCE(record.piperson_organization_id, 0)", + "job_time_bucket_id": "(SELECT id FROM ${UTILITY_SCHEMA}.job_times jt WHERE task.wallduration >= jt.min_duration AND task.wallduration <= jt.max_duration)", + "job_wait_time_bucket_id": "(SELECT id FROM ${UTILITY_SCHEMA}.job_wait_times jt WHERE task.waitduration >= jt.min_duration AND task.waitduration <= jt.max_duration)", + "node_count": "task.node_count", + "processor_count": "task.processor_count", + "processorbucket_id": "(SELECT id FROM ${UTILITY_SCHEMA}.processor_buckets pb WHERE task.processor_count BETWEEN pb.min_processors AND pb.max_processors)", + "submitted_job_count": "SUM( IF(task.submit_time_ts BETWEEN ${:PERIOD_START_TS} AND ${:PERIOD_END_TS}, 1, 0) )", + "ended_job_count": "SUM( IF(task.end_day_id BETWEEN ${:PERIOD_START_DAY_ID} AND ${:PERIOD_END_DAY_ID}, 1, 0) )", + "started_job_count": "SUM( IF(task.start_day_id BETWEEN ${:PERIOD_START_DAY_ID} AND ${:PERIOD_END_DAY_ID}, 1, 0) )", + "running_job_count": "SUM(1)", + "wallduration": "COALESCE(SUM( ${wallduration_case_statement}), 0)", + "sum_wallduration_squared": "COALESCE(SUM( CAST(POW(${wallduration_case_statement}, 2) AS DECIMAL(36,4)) ), 0)", + "waitduration": "SUM( IF(task.start_day_id BETWEEN ${:PERIOD_START_DAY_ID} AND ${:PERIOD_END_DAY_ID}, task.waitduration, NULL) )", + "sum_waitduration_squared": "SUM( CAST(IF(task.start_day_id BETWEEN ${:PERIOD_START_DAY_ID} AND ${:PERIOD_END_DAY_ID}, pow(task.waitduration, 2), NULL) AS DECIMAL(36,4)) )", + "local_charge_xdsu": "SUM(${local_charge_xdsu_case_statement})", + "sum_local_charge_xdsu_squared": "SUM( CAST(POW(${local_charge_xdsu_case_statement}, 2) AS DECIMAL(36,4)) )", + "cpu_time": "COALESCE(SUM(task.processor_count * ${wallduration_case_statement}), 0)", + "sum_cpu_time_squared": "COALESCE(SUM( CAST(POW(task.processor_count * ${wallduration_case_statement}, 2) AS DECIMAL(36,4)) ), 0)", + "node_time": "COALESCE(SUM(task.node_count * ${wallduration_case_statement}), 0)", + "sum_node_time_squared": "COALESCE(SUM( CAST(POW(task.node_count * ${wallduration_case_statement}, 2) AS DECIMAL(36,4)) ), 0)", + "sum_weighted_expansion_factor": "SUM( ((task.wallduration + task.waitduration) / task.wallduration) * task.node_count * COALESCE(${wallduration_case_statement}, 0))", + "sum_job_weights": "SUM(task.node_count * COALESCE(${wallduration_case_statement}, 0))", + "job_id_list": "GROUP_CONCAT(task.job_id)" + }, + "groupby": [ + "${AGGREGATION_UNIT}_id", + "year", + "${AGGREGATION_UNIT}", + "piperson_organization_id", + "job_time_bucket_id", + "job_wait_time_bucket_id", + "node_count", + "processor_count", + "person_id", + "resource_organization_id", + "person_organization_id", + "person_nsfstatuscode_id", + "record_resource_id", + "resourcetype_id", + "queue", + "fos_id", + "account_id", + "systemaccount_id", + "allocation_id", + "principalinvestigator_person_id" + ], + "joins": [ + { + "name": "job_tasks", + "schema": "${SOURCE_SCHEMA}", + "alias": "task" + }, + { + "name": "job_records", + "schema": "${SOURCE_SCHEMA}", + "alias": "record", + "on": "record.job_record_id = task.job_record_id", + "type": "STRAIGHT" + }, + { + "name": "resourcefact", + "schema": "${UTILITY_SCHEMA}", + "alias": "requested_resource", + "on": "requested_resource.id = record.resource_id" + }, + { + "name": "resourcefact", + "schema": "${UTILITY_SCHEMA}", + "alias": "task_resource", + "on": "task_resource.id = task.resource_id" + } + ], + "where": [ + "task.start_day_id <= ${:PERIOD_END_DAY_ID} AND task.end_day_id >= ${:PERIOD_START_DAY_ID}", + "task.is_deleted = 0" + ], + "macros": [ + { + "name": "wallduration_case_statement", + "file": "statistic_ratio_case.sql", + "args": { + "statistic": "task.wallduration", + "max": "${:PERIOD_SECONDS}", + "src_start_ts": "task.start_time_ts", + "src_end_ts": "task.end_time_ts", + "dest_start_ts": "${:PERIOD_START_TS}", + "dest_end_ts": "${:PERIOD_END_TS}" + } + }, + { + "name": "local_charge_xdsu_case_statement", + "file": "statistic_ratio_as_datatype_case.sql", + "args": { + "data_type": "DECIMAL(18,3)", + "statistic": "task.local_charge_xdsu", + "max": "${:PERIOD_SECONDS}", + "src_start_ts": "task.start_time_ts", + "src_end_ts": "task.end_time_ts", + "dest_start_ts": "${:PERIOD_START_TS}", + "dest_end_ts": "${:PERIOD_END_TS}" + } + } + ] + } +} diff --git a/configuration/etl/etl_action_defs.d/jobs/xdw/jobfact_by_day_joblist.json b/configuration/etl/etl_action_defs.d/jobs/xdw/jobfact_by_day_joblist.json new file mode 100644 index 0000000000..701e577156 --- /dev/null +++ b/configuration/etl/etl_action_defs.d/jobs/xdw/jobfact_by_day_joblist.json @@ -0,0 +1,29 @@ +{ + "table_definition": { + "$ref": "${table_definition_dir}/jobs/xdw/jobfact_by_day_joblist.json#/table_definition" + }, + "source_query": { + "overseer_restrictions": { + "last_modified_start_date": "last_modified >= ${VALUE}", + "last_modified_end_date": "last_modified <= ${VALUE}" + }, + "records": { + "agg_id": "id", + "job_id_list": "job_id_list", + "job_id": -1 + }, + "joins": [ + { + "name": "jobfact_by_day", + "schema": "${SOURCE_SCHEMA}", + "alias": "jf" + } + ] + }, + "destination_record_map": { + "jobfact_by_day_joblist": { + "agg_id": "agg_id", + "jobid": "job_id" + } + } +} diff --git a/configuration/etl/etl_pipelines.d/jobs-xdw.json b/configuration/etl/etl_pipelines.d/jobs-xdw.json index 9d091dea27..6f8da9ea5c 100644 --- a/configuration/etl/etl_pipelines.d/jobs-xdw.json +++ b/configuration/etl/etl_pipelines.d/jobs-xdw.json @@ -156,31 +156,85 @@ } } ], - "aggregate": [{ - "name": "aggregate", - "endpoints": { - "source": { - "type": "mysql", - "name": "Job Record/Task database", - "config": "datawarehouse", - "schema": "modw" + "aggregate": [ + { + "name": "table-create", + "description": "Setup tables", + "class": "ManageTables", + "namespace": "ETL\\Maintenance", + "options_class": "MaintenanceOptions", + "definition_file_list": [ + "jobs/xdw/jobfact_by_day_joblist.json" + ] + }, + { + "name": "aggregate-days", + "endpoints": { + "source": { + "type": "mysql", + "name": "Job Record/Task database", + "config": "datawarehouse", + "schema": "modw" + }, + "destination": { + "type": "mysql", + "name": "Aggregates Database", + "config": "datawarehouse", + "schema": "modw_aggregates", + "create_schema_if_not_exists": true + } }, - "destination": { - "type": "mysql", - "name": "Aggregates Database", - "config": "datawarehouse", - "schema": "modw_aggregates", - "create_schema_if_not_exists": true - } + "namespace": "ETL\\Aggregator", + "options_class": "AggregatorOptions", + "class": "JobListAggregator", + "description": "Aggregate HPC job records", + "definition_file": "jobs/hpc-aggregation-day.json", + "table_prefix": "jobfact_by_", + "aggregation_units": ["day"] }, - "namespace": "ETL\\Aggregator", - "options_class": "AggregatorOptions", - "class": "SimpleAggregator", - "description": "Aggregate HPC job records", - "definition_file": "jobs/hpc-aggregation.json", - "table_prefix": "jobfact_by_", - "aggregation_units": [ - "day", "month", "quarter", "year" - ] - }] + { + "name": "aggregate", + "endpoints": { + "source": { + "type": "mysql", + "name": "Job Record/Task database", + "config": "datawarehouse", + "schema": "modw" + }, + "destination": { + "type": "mysql", + "name": "Aggregates Database", + "config": "datawarehouse", + "schema": "modw_aggregates", + "create_schema_if_not_exists": true + } + }, + "namespace": "ETL\\Aggregator", + "options_class": "AggregatorOptions", + "class": "SimpleAggregator", + "description": "Aggregate HPC job records", + "definition_file": "jobs/hpc-aggregation.json", + "table_prefix": "jobfact_by_", + "aggregation_units": ["month", "quarter", "year"] + }, + { + "name": "aggregation-joblist", + "namespace": "ETL\\Ingestor", + "class": "ExplodeTransformIngestor", + "options_class": "IngestorOptions", + "definition_file": "jobs/xdw/jobfact_by_day_joblist.json", + "description": "Populate the job list table, which contains the back references from the aggregates table to the fact table", + "explode_column": { + "job_id_list": "job_id" + }, + "endpoints": { + "source": { + "type": "mysql", + "name": "modw_aggregates", + "config": "datawarehouse", + "schema": "modw_aggregates" + } + } + } + ] } diff --git a/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day.json b/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day.json new file mode 100644 index 0000000000..54c3fc4cc9 --- /dev/null +++ b/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day.json @@ -0,0 +1,477 @@ +{ + "table_definition": { + "name": "jobfact_by_", + "comment": "Jobfacts aggregated by ${AGGREGATION_UNIT}.", + "engine": "MyISAM", + "columns": [ + { + "name": "id", + "type": "int(11)", + "nullable": false, + "extra": "auto_increment" + }, + { + "name": "${AGGREGATION_UNIT}_id", + "type": "int(10) unsigned", + "nullable": false, + "comment": "DIMENSION: The id related to modw.${AGGREGATION_UNIT}s." + }, + { + "name": "year", + "type": "smallint(5) unsigned", + "nullable": false, + "comment": "DIMENSION: The year of the ${AGGREGATION_UNIT}" + }, + { + "name": "${AGGREGATION_UNIT}", + "type": "smallint(5) unsigned", + "nullable": false, + "comment": "DIMENSION: The ${AGGREGATION_UNIT} of the year." + }, + { + "name": "record_resource_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The resource on which the request was made" + }, + { + "name": "task_resource_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The resource on which the jobs ran" + }, + { + "name": "resource_organization_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The organization of the resource that the jobs ran on." + }, + { + "name": "resourcetype_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The type of the resource on which the jobs ran. References resourcetype.id" + }, + { + "name": "systemaccount_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The id of the resource system account (local username) under which the job ran. References systemaccount.id" + }, + { + "name": "submission_venue_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The method used to submit this job: cli, gateway, ..." + }, + { + "name": "job_record_type_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: Task type or event." + }, + { + "name": "job_task_type_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: Type of job: hpc, cloud, hpc-reservation, ...." + }, + { + "name": "queue", + "type": "char(50)", + "nullable": false, + "comment": "DIMENSION: The queue of the resource on which the jobs ran." + }, + { + "name": "allocation_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The id of allocation these jobs used to run" + }, + { + "name": "account_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The id of the account record from which one can get charge number" + }, + { + "name": "requesting_person_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The id of the person that requested the resources (e.g., made the reservation or submitted the job." + }, + { + "name": "person_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The id of the person that ran the jobs." + }, + { + "name": "person_organization_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The organization of the person that ran the jobs." + }, + { + "name": "person_nsfstatuscode_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The NSF status code of the person that ran the jobs. References person.nsfstatuscode_id" + }, + { + "name": "fos_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The field of science of the project to which the jobs belong." + }, + { + "name": "principalinvestigator_person_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The PI that owns the allocations that these jobs ran under. References principalinvestigator.person_id" + }, + { + "name": "piperson_organization_id", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: The organization of the PI that owns the project that funds these jobs. References piperson.organization_id" + }, + { + "name": "job_time_bucket_id", + "type": "int(4)", + "nullable": false, + "comment": "DIMENSION: Job time is bucketing of wall time based on prechosen intervals in the modw.job_times table." + }, + { + "name": "job_wait_time_bucket_id", + "type": "int(4)", + "nullable": false, + "comment": "DIMENSION: Job wait time is bucketing of wait time based on prechosen intervals in the modw.job_wait_times table." + }, + { + "name": "node_count", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: Number of nodes each of the jobs used." + }, + { + "name": "processor_count", + "type": "int(11)", + "nullable": false, + "comment": "DIMENSION: Number of processors each of the jobs used." + }, + { + "name": "processorbucket_id", + "type": "int(4)", + "comment": "FACT: Pre-determined processor bucket sizes. References processorbucket.id", + "nullable": true + }, + { + "name": "submitted_job_count", + "type": "int(11)", + "comment": "FACT: The number of jobs that started during this day.", + "nullable": true + }, + { + "name": "ended_job_count", + "type": "int(11)", + "comment": "FACT: The number of jobs that ended during this day.", + "nullable": true + }, + { + "name": "started_job_count", + "type": "int(11)", + "comment": "FACT: The number of jobs that started during this day.", + "nullable": true + }, + { + "name": "running_job_count", + "type": "int(11)", + "comment": "FACT: The number of jobs that were running during this day.", + "nullable": true + }, + { + "name": "wallduration", + "type": "decimal(18,0)", + "comment": "FACT: (seconds) The wallduration of the jobs that were running during this period. This will only count the walltime of the jobs that fell during this day. If a job started in the previous day(s) the wall time for that day will be added to that day. Same logic is true if a job ends not in this day, but upcoming days.", + "nullable": true + }, + { + "name": "sum_wallduration_squared", + "type": "double", + "comment": "FACT: (seconds) The sum of the square of wallduration of the jobs that were running during this period. This will only count the walltime of the jobs that fell during this day. If a job started in the previous day(s) the wall time for that day will be added to that day. Same logic is true if a job ends not in this day, but upcoming days.", + "nullable": true + }, + { + "name": "waitduration", + "type": "decimal(18,0)", + "comment": "FACT: (seconds) The amount of time jobs waited to execute during this day.", + "nullable": true + }, + { + "name": "sum_waitduration_squared", + "type": "double", + "comment": "FACT: (seconds) The sum of the square of the amount of time jobs waited to execute during this day.", + "nullable": true + }, + { + "name": "local_charge_su", + "type": "decimal(18,0)", + "comment": "FACT: The amount of local SUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "local_charge_xdsu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of XDSUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "local_charge_nu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of NUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "adjusted_charge_su", + "type": "decimal(18,0)", + "comment": "FACT: The amount of local SUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "adjusted_charge_xdsu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of XDSUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "adjusted_charge_nu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of NUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_local_charge_su", + "type": "decimal(18,0)", + "comment": "FACT: The amount of local SUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_local_charge_xdsu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of XDSUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_local_charge_nu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of NUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_adjusted_charge_su", + "type": "decimal(18,0)", + "comment": "FACT: The amount of local SUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_adjusted_charge_xdsu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of XDSUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "task_adjusted_charge_nu", + "type": "decimal(18,0)", + "comment": "FACT: The amount of NUs charged to jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "sum_local_charge_xdsu_squared", + "type": "double", + "comment": "FACT: The sum of the square of local_charge of jobs pertaining to this day. If a job took more than one day, its local_charge is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "cpu_time", + "type": "decimal(18,0)", + "comment": "FACT: (seconds) The amount of the cpu time (processor_count * wallduration) of the jobs pertaining to this day. If a job took more than one day, its cpu_time is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "sum_cpu_time_squared", + "type": "double", + "comment": "FACT: (seconds) The sum of the square of the amount of the cpu_time of the jobs pertaining to this day. If a job took more than one day, its cpu_time is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "node_time", + "type": "decimal(18,0)", + "comment": "FACT: (seconds) The amount of the node time (nodes * wallduration) of the jobs pertaining to this day. If a job took more than one day, its node_time is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "sum_node_time_squared", + "type": "double", + "comment": "FACT: (seconds) The sum of the square of the amount of the node_time of the jobs pertaining to this day. If a job took more than one day, its node_time is distributed linearly across the days it used.", + "nullable": true + }, + { + "name": "sum_weighted_expansion_factor", + "type": "decimal(18,0)", + "comment": "FACT: This is the sum of expansion factor per job multiplied by node_count and the [adjusted] duration of jobs that ran in this days.", + "nullable": true + }, + { + "name": "sum_job_weights", + "type": "decimal(18,0)", + "comment": "FACT: this is the sum of (node_count multipled by the [adjusted] duration) for jobs that ran in this days.", + "nullable": true + }, + { + "name": "job_id_list", + "type": "mediumtext", + "nullable": false, + "comment": "METADATA: the ids in the fact table for the rows that went into this row" + }, + { + "name": "last_modified", + "type": "timestamp", + "default": "CURRENT_TIMESTAMP", + "nullable": false, + "extra": "ON UPDATE CURRENT_TIMESTAMP" + } + ], + "indexes": [ + { + "name": "PRIMARY", + "columns": [ + "id" + ], + "type": "BTREE", + "is_unique": true + }, + { + "name": "index_account", + "columns": [ + "account_id" + ] + }, + { + "name": "index_allocation", + "columns": [ + "allocation_id" + ] + }, + { + "name": "index_fos", + "columns": [ + "fos_id" + ] + }, + { + "name": "index_job_time_bucket_id", + "columns": [ + "job_time_bucket_id" + ] + }, + { + "name": "index_job_wait_time_bucket_id", + "columns": [ + "job_wait_time_bucket_id" + ] + }, + { + "name": "index_node_count", + "columns": [ + "node_count" + ] + }, + { + "name": "index_resource_organization", + "columns": [ + "resource_organization_id" + ] + }, + { + "name": "index_person", + "columns": [ + "person_id" + ] + }, + { + "name": "index_person_nsf_status_code", + "columns": [ + "person_nsfstatuscode_id" + ] + }, + { + "name": "index_last_modified", + "columns": [ + "last_modified" + ] + }, + { + "name": "index_person_organization", + "columns": [ + "person_organization_id" + ] + }, + { + "name": "index_pi_organization", + "columns": [ + "piperson_organization_id" + ] + }, + { + "name": "index_pi_person", + "columns": [ + "principalinvestigator_person_id" + ] + }, + { + "name": "index_processor_count", + "columns": [ + "processor_count" + ] + }, + { + "name": "index_queue", + "columns": [ + "queue" + ] + }, + { + "name": "index_resource_type", + "columns": [ + "resourcetype_id" + ] + }, + { + "name": "index_resource", + "columns": [ + "record_resource_id" + ] + }, + { + "name": "index_system_account", + "columns": [ + "systemaccount_id" + ] + }, + { + "name": "index_period_value", + "columns": [ + "${AGGREGATION_UNIT}" + ] + }, + { + "name": "index_period", + "columns": [ + "${AGGREGATION_UNIT}_id" + ] + } + ], + "table_prefix": "jobfact_by_" + } +} diff --git a/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day_joblist.json b/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day_joblist.json new file mode 100644 index 0000000000..583f73c25b --- /dev/null +++ b/configuration/etl/etl_tables.d/jobs/xdw/jobfact_by_day_joblist.json @@ -0,0 +1,31 @@ +{ + "table_definition": { + "name": "jobfact_by_day_joblist", + "engine": "InnoDB", + "columns": [ + { + "name": "agg_id", + "type": "int(11)", + "nullable": false + }, + { + "name": "jobid", + "type": "int(11)", + "nullable": false + } + ], + "indexes": [ + { + "name": "PRIMARY", + "columns": [ + "agg_id", + "jobid" + ], + "type": "BTREE", + "is_unique": true + } + ], + "triggers": [] + } +} + diff --git a/configuration/rawstatistics.d/20_jobs.json b/configuration/rawstatistics.d/20_jobs.json new file mode 100644 index 0000000000..899544700a --- /dev/null +++ b/configuration/rawstatistics.d/20_jobs.json @@ -0,0 +1,210 @@ +{ + "+realms": { + "Jobs": { + "name": "Jobs" + } + }, + "modw.job_tasks": [ + { + "key": "local_jobid", + "name": "Local Job Id", + "dtype": "accounting", + "group": "Administration", + "documentation": "The unique identifier assigned to the job by the job scheduler." + }, + { + "key": "resource_id", + "name": "Resource", + "group": "Administration", + "dtype": "foreignkey", + "join": { + "schema": "modw", + "table": "resourcefact" + }, + "documentation": "The resource that ran the job." + }, + { + "key": "systemaccount_id", + "name": "System Username", + "group": "Administration", + "dtype": "foreignkey", + "join": { + "schema": "modw", + "table": "systemaccount", + "column": "username" + }, + "documentation": "The username on the resource of the user that ran the job. May be a UID or string username depending on the resource." + }, + { + "key": "person_id", + "name": "User", + "group": "Administration", + "dtype": "foreignkey", + "join": { + "schema": "modw", + "table": "person", + "column": "long_name" + }, + "documentation": "The name of the job owner." + }, + { + "key": "person_organization_id", + "name": "Organization", + "group": "Administration", + "dtype": "foreignkey", + "join": { + "schema": "modw", + "table": "organization" + }, + "documentation": "The organization of the person who ran the task" + }, + { + "key": "name", + "name": "Name", + "documentation": "The name of the job as reported by the job scheduler.", + "dtype": "accounting", + "group": "Executable" + }, + { + "key": "submit_time_ts", + "name": "Submit Time", + "dtype": "accounting", + "group": "Timing", + "units": "ts", + "documentation": "Task submission time" + }, + { + "key": "start_time_ts", + "name": "Start Time", + "dtype": "accounting", + "group": "Timing", + "units": "ts", + "documentation": "The time that the job started running." + }, + { + "key": "end_time_ts", + "name": "End Time", + "units": "ts", + "dtype": "accounting", + "group": "Timing", + "documentation": "The time that the job ended." + }, + { + "key": "eligible_time_ts", + "name": "Eligible Time", + "units": "ts", + "dtype": "accounting", + "group": "Timing", + "documentation": "The time that the job was eligible for scheduling by the resource manager." + }, + { + "key": "node_count", + "name": "Nodes", + "dtype": "foreignkey", + "group": "Allocated Resource", + "join": { + "schema": "modw", + "table": "nodecount", + "column": "nodes" + }, + "documentation": "The number of nodes that were assigned to the job." + }, + { + "key": "processor_count", + "name": "Cores", + "dtype": "accounting", + "group": "Allocated Resource", + "documentation": "The number of cores that were assigned to the job." + }, + { + "key": "memory_kb", + "name": "Memory Used", + "dtype": "accounting", + "group": "Allocated resource", + "units": "kilobyte", + "documentation": "Memory consumed as reported by the resource manager." + }, + { + "key": "wallduration", + "name": "Wall Time", + "dtype": "accounting", + "group": "Timing", + "units": "seconds", + "documentation": "Overall job duration." + }, + { + "key": "waitduration", + "name": "Wait Time", + "dtype": "accounting", + "group": "Timing", + "units": "seconds", + "documentation": "Time the job waited in the queue" + }, + { + "key": "cpu_time", + "name": "Core Time", + "dtype": "accounting", + "group": "Allocated resource", + "units": "seconds", + "documentation": "The amount of CPU core time (Core Count * Wall Time)" + }, + { + "key": "group_name", + "name": "UNIX group name", + "dtype": "accounting", + "group": "Administration", + "documentation": "The name of the group that ran the job." + }, + { + "key": "gid_number", + "name": "UNIX group GID", + "dtype": "accounting", + "group": "Administration", + "documentation": "The GID of the group that ran the job." + }, + { + "key": "uid_number", + "name": "UNIX UID", + "dtype": "accounting", + "group": "Administration", + "documentation": "The UID of the user that ran the job." + }, + { + "key": "exit_code", + "name": "Exit Code", + "dtype": "accounting", + "group": "Executable", + "documentation": "The code that the job exited with." + }, + { + "key": "exit_state", + "name": "Exit State", + "dtype": "accounting", + "group": "Executable", + "documentation": "The state of the job when it completed." + }, + { + "key": "cpu_req", + "name": "Requested Cores", + "dtype": "accounting", + "group": "Requested resource", + "documentation": "The number of CPUs required by the job." + }, + { + "key": "mem_req", + "name": "Requested memory", + "dtype": "accounting", + "group": "Requested resource", + "units": "bytes", + "documentation": "The amount of memory required by the job." + }, + { + "key": "timelimit", + "name": "Requested Wall Time", + "dtype": "accounting", + "group": "Requested resource", + "units": "seconds", + "documentation": "The time limit of the job." + } + ] +} diff --git a/configuration/roles.json b/configuration/roles.json index 0ae8c82b66..e8ec94d2a7 100644 --- a/configuration/roles.json +++ b/configuration/roles.json @@ -39,6 +39,15 @@ "userManualSectionName": "Report Generator", "tooltip": "" }, + { + "name": "job_viewer", + "title": "Job Viewer", + "position": 5000, + "javascriptClass": "XDMoD.Module.JobViewer", + "javascriptReference": "CCR.xdmod.ui.jobViewer", + "tooltip": "View detailed job-level metrics", + "userManualSectionName": "Job Viewer" + }, { "name": "about_xdmod", "title": "About", diff --git a/open_xdmod/modules/xdmod/build.json b/open_xdmod/modules/xdmod/build.json index 082d2b5a53..da57f4b049 100644 --- a/open_xdmod/modules/xdmod/build.json +++ b/open_xdmod/modules/xdmod/build.json @@ -71,6 +71,7 @@ "configuration/processor_buckets.json", "configuration/rawstatistics.json", "configuration/rawstatistics.d", + {"configuration/rawstatistics.d/20_jobs.json": "rawstatistics.d/20_jobs.json"}, "configuration/resource_specs.json", "configuration/resource_types.json", "configuration/resources.json", diff --git a/open_xdmod/modules/xdmod/integration_tests/lib/Rest/JobViewerTest.php b/open_xdmod/modules/xdmod/integration_tests/lib/Rest/JobViewerTest.php new file mode 100644 index 0000000000..3c68465c3d --- /dev/null +++ b/open_xdmod/modules/xdmod/integration_tests/lib/Rest/JobViewerTest.php @@ -0,0 +1,295 @@ + true ); + $this->xdmodhelper = new \TestHarness\XdmodTestHelper($xdmodConfig); + } + + private static function getDimensions() { + return array( + 'nsfdirectorate', + 'parentscience', + 'jobsize', + 'jobwaittime', + 'jobwalltime', + 'nodecount', + 'pi', + 'fieldofscience', + 'queue', + 'resource', + 'resource_type', + 'username', + 'person' + ); + } + + /** + * Note that this test intentionally hardcodes the available dimensions so + * that we can confirm that the dimensions are all present and correct for + * fresh installs and for upgrades. Needless to say, the expected results + * must be updated when the SUPReMM schema changes. + */ + public function testDimensions() + { + $this->xdmodhelper->authenticate('cd'); + $queryparams = array( + 'realm' => 'Jobs' + ); + $response = $this->xdmodhelper->get(self::ENDPOINT . 'dimensions', $queryparams); + + $this->assertEquals(200, $response[1]['http_code']); + + $resdata = $response[0]; + + $this->assertArrayHasKey('success', $resdata); + $this->assertEquals(true, $resdata['success']); + + $dimids = array(); + foreach ($resdata['results'] as $dimension) { + $dimids[] = $dimension['id']; + } + + $this->assertEquals(self::getDimensions(), $dimids); + + $this->xdmodhelper->logout(); + } + + public function dimensionsProvider() + { + $xdmodhelper = new \TestHarness\XdmodTestHelper(array('decodetextasjson' => true)); + $xdmodhelper->authenticate('cd'); + + $testCases = array(); + foreach (self::getDimensions() as $dimension) { + $testCases[] = array($xdmodhelper, $dimension); + } + return $testCases; + } + + /** + * Check that all dimensions have at least one dimension value. + * + * @dataProvider dimensionsProvider + */ + public function testDimensionValues($xdmodhelper, $dimension) + { + $queryparams = array( + 'realm' => 'Jobs' + ); + $response = $xdmodhelper->get(self::ENDPOINT . 'dimensions/' . $dimension, $queryparams); + + $this->assertEquals(200, $response[1]['http_code']); + + $resdata = $response[0]; + + $this->assertArrayHasKey('success', $resdata); + $this->assertEquals(true, $resdata['success']); + $this->assertEquals(true, count($resdata['results']) > 0); + } + + public function testResourceEndPoint() + { + $this->xdmodhelper->authenticate('cd'); + + $queryparams = array( + 'realm' => 'Jobs' + ); + + $response = $this->xdmodhelper->get(self::ENDPOINT . 'dimensions/resource', $queryparams); + + $this->assertEquals(200, $response[1]['http_code']); + + $resdata = $response[0]; + + $this->assertArrayHasKey('success', $resdata); + $this->assertEquals(true, $resdata['success']); + + foreach($resdata['results'] as $resource) + { + $this->assertArrayHasKey('id', $resource); + $this->assertArrayHasKey('name', $resource); + $this->assertArrayHasKey('short_name', $resource); + $this->assertArrayHasKey('long_name', $resource); + } + + $this->xdmodhelper->logout(); + } + + public function testResourceNoAuth() + { + $queryparams = array( + 'realm' => 'Jobs' + ); + $response = $this->xdmodhelper->get(self::ENDPOINT . 'dimensions/resource', $queryparams); + + $this->assertEquals(401, $response[1]['http_code']); + } + + private function validateSingleJobSearch($searchparams, $doAuth = true) + { + if ($doAuth) { + $this->xdmodhelper->authenticate('cd'); + } + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', $searchparams); + + $this->assertArrayHasKey('success', $result[0]); + $this->assertEquals($result[0]['success'], true); + $this->assertArrayHasKey('results', $result[0]); + $this->assertCount(1, $result[0]['results']); + + $jobdata = $result[0]['results'][0]; + + $this->assertArrayHasKey('dtype', $jobdata); + $this->assertArrayHasKey($jobdata['dtype'], $jobdata); + + if ($doAuth) { + $this->xdmodhelper->logout(); + } + + return $jobdata; + } + + public function testBasicJobSearch() { + $queryparams = array( + 'realm' => 'Jobs', + 'params' => json_encode( + array( + 'resource_id' => 5, + 'local_job_id' => 6117153 + ) + ) + ); + $this->validateSingleJobSearch($queryparams); + } + + public function testBasicJobSearchNoAuth() { + $searchparams = array( + 'realm' => 'Jobs', + 'params' => json_encode( + array( + 'resource_id' => 5, + 'local_job_id' => 6117153 + ) + ) + ); + + foreach (array('usr', 'pi') as $unpriv) { + $this->xdmodhelper->authenticate($unpriv); + $response = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', $searchparams); + $this->assertEquals(403, $response[1]['http_code']); + $this->assertArrayHasKey('success', $response[0]); + $this->assertEquals(false, $response[0]['success']); + $this->xdmodhelper->logout(); + } + } + + public function testInvalidJobSearch() { + + $this->xdmodhelper->authenticate('cd'); + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', array() ); + + $this->assertArrayHasKey('success', $result[0]); + $this->assertEquals($result[0]['success'], false); + $this->assertEquals($result[1]['http_code'], 400); + + $this->xdmodhelper->logout(); + } + + public function testInvalidJobSearchJson() { + + $searchparams = array( + 'realm' => 'Jobs', + 'params' => 'this is not json data' + ); + + $this->xdmodhelper->authenticate('cd'); + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', $searchparams); + + $this->assertArrayHasKey('success', $result[0]); + $this->assertEquals($result[0]['success'], false); + $this->assertEquals($result[1]['http_code'], 400); + + $this->xdmodhelper->logout(); + } + + public function testInvalidJobSearchMissingParams() { + + $searchparams = array( + 'realm' => 'Jobs', + 'params' => json_encode(array('resource_id' => '2801')) + ); + + $this->xdmodhelper->authenticate('cd'); + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', $searchparams); + + $this->assertArrayHasKey('success', $result[0]); + $this->assertEquals($result[0]['success'], false); + $this->assertEquals($result[1]['http_code'], 400); + + $this->xdmodhelper->logout(); + } + + public function testAdvancedSearchInvalid() { + $searchparams = array( + 'start_date' => '2015-01-01', + 'end_date' => '2015-01-01', + 'realm' => 'Jobs', + 'params' => json_encode( + array( 'non existent dimension 1' => array(0), + 'another invalid dimension' => array(1) ) + ), + 'limit' => 10, + 'start' => 0 + ); + + $this->xdmodhelper->authenticate('cd'); + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/jobs', $searchparams); + $this->assertEquals($result[0]['success'], false); + $this->assertEquals($result[1]['http_code'], 400); + + $this->xdmodhelper->logout(); + } + + public function testJobMetadata() { + $queryparams = array( + 'realm' => 'Jobs', + 'params' => json_encode( + array( + 'resource_id' => 5, + 'local_job_id' => 6112282 + ) + ) + ); + $this->xdmodhelper->authenticate('cd'); + $jobparams = $this->validateSingleJobSearch($queryparams, false); + $searchparams = array( + 'realm' => 'Jobs', + 'recordid' => '-1', // this parameter is not acutally used for anything but needs to be present :-( + $jobparams['dtype'] => $jobparams[$jobparams['dtype']] + ); + + $result = $this->xdmodhelper->get(self::ENDPOINT . 'search/history', $searchparams); + + $types = array(); + + foreach($result[0]['results'] as $datum) { + $this->assertArrayHasKey('dtype', $datum); + $this->assertArrayHasKey($datum['dtype'], $datum); + $this->assertArrayHasKey('text', $datum); + $types[] = $datum['text']; + } + + $expectedTypes = array( + 'Accounting data' + ); + + $this->assertEquals($expectedTypes, $types); + } +} diff --git a/open_xdmod/modules/xdmod/integration_tests/scripts/xdmod-upgrade.tcl b/open_xdmod/modules/xdmod/integration_tests/scripts/xdmod-upgrade.tcl index 5037e9110a..6a3331a7b6 100644 --- a/open_xdmod/modules/xdmod/integration_tests/scripts/xdmod-upgrade.tcl +++ b/open_xdmod/modules/xdmod/integration_tests/scripts/xdmod-upgrade.tcl @@ -19,6 +19,14 @@ proc confirmUpgrade { } { set timeout 180 spawn "xdmod-upgrade" confirmUpgrade +expect { + -re "\nDo you want to run aggregation now.*\\\]" { + send yes\n + } + timeout { + send_user "\nFailed to get prompt\n"; exit 1 + } +} expect { timeout { send_user "\nFailed to get prompt\n"; exit 1 diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/acls/output/roles.json b/tests/artifacts/xdmod-test-artifacts/xdmod/acls/output/roles.json index a9605e8c89..a25f6bd7d6 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/acls/output/roles.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/acls/output/roles.json @@ -38,6 +38,15 @@ "userManualSectionName": "Report Generator", "tooltip": "" }, + { + "name": "job_viewer", + "title": "Job Viewer", + "position": 5000, + "javascriptClass": "XDMoD.Module.JobViewer", + "javascriptReference": "CCR.xdmod.ui.jobViewer", + "userManualSectionName": "Job Viewer", + "tooltip": "View detailed job-level metrics" + }, { "name": "about_xdmod", "title": "About", diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-admin.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-admin.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-admin.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-admin.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerdirector.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerdirector.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerdirector.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerdirector.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerstaff.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerstaff.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerstaff.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-centerstaff.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-normaluser.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-normaluser.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-normaluser.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-normaluser.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-principal.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-principal.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-principal.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-principal.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cd.one-center.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cd.one-center.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cd.one-center.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cd.one-center.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cs.one-center.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cs.one-center.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cs.one-center.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.cs.one-center.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.normal-user.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.normal-user.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.normal-user.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.normal-user.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.pi.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.pi.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.pi.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.pi.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_dev.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_dev.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_dev.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_dev.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +} diff --git a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr_dev.json b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr_dev.json index c62142c819..f01ad9bca9 100644 --- a/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr_dev.json +++ b/tests/artifacts/xdmod-test-artifacts/xdmod/user_admin/output/get_tabs-test.usr_mgr_dev.json @@ -4,7 +4,7 @@ "message": "", "data": [ { - "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" + "tabs": "[{\"tab\":\"tg_summary\",\"isDefault\":true,\"title\":\"Summary\",\"pos\":100,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Summary\",\"javascriptReference\":\"CCR.xdmod.ui.tgSummaryViewer\",\"tooltip\":\"Displays summary information\",\"userManualSectionName\":\"Summary Tab\"},{\"tab\":\"tg_usage\",\"isDefault\":false,\"title\":\"Usage\",\"pos\":200,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.Usage\",\"javascriptReference\":\"CCR.xdmod.ui.chartViewerTGUsage\",\"tooltip\":\"Displays usage\",\"userManualSectionName\":\"Usage Tab\"},{\"tab\":\"metric_explorer\",\"isDefault\":false,\"title\":\"Metric Explorer\",\"pos\":300,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.MetricExplorer\",\"javascriptReference\":\"CCR.xdmod.ui.metricExplorer\",\"tooltip\":\"\",\"userManualSectionName\":\"Metric Explorer\"},{\"tab\":\"report_generator\",\"isDefault\":false,\"title\":\"Report Generator\",\"pos\":1000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.ReportGenerator\",\"javascriptReference\":\"CCR.xdmod.ui.reportGenerator\",\"tooltip\":\"\",\"userManualSectionName\":\"Report Generator\"},{\"tab\":\"job_viewer\",\"isDefault\":false,\"title\":\"Job Viewer\",\"pos\":5000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.JobViewer\",\"javascriptReference\":\"CCR.xdmod.ui.jobViewer\",\"tooltip\":\"View detailed job-level metrics\",\"userManualSectionName\":\"Job Viewer\"},{\"tab\":\"about_xdmod\",\"isDefault\":false,\"title\":\"About\",\"pos\":10000,\"permitted_modules\":null,\"javascriptClass\":\"XDMoD.Module.About\",\"javascriptReference\":\"CCR.xdmod.ui.aboutXD\",\"tooltip\":\"\",\"userManualSectionName\":\"About\"}]" } ] -} \ No newline at end of file +}