... | ... | @@ -48,9 +48,15 @@ To provide this simple and intuitive access to the supercomputing infrastructure |
|
|
* **GetUserResourceUsageReport** – the used core-hours for the user
|
|
|
* **ListAdaptorUserGroups** – a list of all users in the specified group
|
|
|
|
|
|
## Command Template Prepareation
|
|
|
## Command Template Preparation
|
|
|
|
|
|
TODO
|
|
|
For security purposes *HEAppE* enables the users to run only pre-prepared set of so-called *Command Templates*. Each template defines arbitrary script or executable file that will be executed on the cluster, any dependencies or third-party software it might require and the type queue that should be used for the processing (type of computing nodes to be used on the cluster). The template also contains the set of input parameters that will be passed to the executable script during run-time. Thus, the users are only able to execute pre-prepared command templates with the pre-defined set of input parameters. The actual value of each parameter (input from the user) can be changed by the user for each job submission.
|
|
|
|
|
|
| Id | Name | Description | Code | Executable File | Command Parameters | Preparation Script | Cluster Node Type |
|
|
|
|----|------|-------------|------|------|------|------|------|
|
|
|
| 1 | TestTemplate | Desc | Code | /scratch/temp/ HaasTestScript/test.sh | "%%{inputParam}" | module load Python/2.7.9-intel-2015b; | 7 |
|
|
|
|
|
|
{: .custom-class #custom-id}
|
|
|
|
|
|
## Workflow
|
|
|
|
... | ... | @@ -58,4 +64,200 @@ TODO |
|
|
|
|
|
## HEAppE Integration Example (C#)
|
|
|
|
|
|
TODO |
|
|
\ No newline at end of file |
|
|
```csharp
|
|
|
//web references for HaaS services
|
|
|
using WsClient.test_ClusterInformationWs;
|
|
|
using WsClient.test_FileTransferWs;
|
|
|
using WsClient.test_JobManagementWs;
|
|
|
using WsClient.test_JobReportingWs;
|
|
|
using WsClient.test_UserAndLimitationManagementWs;
|
|
|
|
|
|
namespace WsClient
|
|
|
{
|
|
|
class Program
|
|
|
{
|
|
|
static ClusterInformationWs wsClusterInformation = new ClusterInformationWs();
|
|
|
static FileTransferWs wsFileTransfer = new FileTransferWs();
|
|
|
static JobManagementWs wsJobManagement = new JobManagementWs();
|
|
|
static JobReportingWs wsJobReporting = new JobReportingWs();
|
|
|
static UserAndLimitationManagementWs wsUserAndLimitationManagement = new
|
|
|
UserAndLimitationManagementWs();
|
|
|
|
|
|
private static string sessionCode; //code acquired via authentication
|
|
|
|
|
|
static void Main(string[] args)
|
|
|
{
|
|
|
AuthenticateUserPassword();
|
|
|
CreateAndSubmitTestJob();
|
|
|
}
|
|
|
|
|
|
private static void CreateAndSubmitTestJob()
|
|
|
{
|
|
|
//each submitted job must contain at least one task
|
|
|
TaskSpecificationExt testTask = new TaskSpecificationExt();
|
|
|
testTask.name = "TestJob";
|
|
|
testTask.minCores = 1; //minimum number of cores required
|
|
|
testTask.maxCores = 1; //maximum number of cores required
|
|
|
testTask.walltimeLimit = 600; //maximum time for task to run (seconds)
|
|
|
testTask.standardOutputFile = "console_Stdout";
|
|
|
testTask.standardErrorFile = "console_Stderr";
|
|
|
testTask.progressFile = "console_Stdprog";
|
|
|
testTask.logFile = "console_Stdlog";
|
|
|
testTask.commandTemplateId = 1; //commandTemplateID
|
|
|
//custom environment variables for the task
|
|
|
testTask.environmentVariables = new EnvironmentVariableExt[0];
|
|
|
//fill the command template parameters (see Table1 for “inputParam”)
|
|
|
testTask.templateParameterValues = new CommandTemplateParameterValueExt[] {
|
|
|
new CommandTemplateParameterValueExt() { commandParameterIdentifier =
|
|
|
"inputParam", parameterValue = "someStringParam" }
|
|
|
};
|
|
|
|
|
|
//create job specification with the task above
|
|
|
JobSpecificationExt testJob = new JobSpecificationExt();
|
|
|
testJob.name = "TestJob"; //job name
|
|
|
testJob.minCores = 1; //minimum number of cores required
|
|
|
testJob.maxCores = 1; //maximum number of cores required
|
|
|
testJob.priority = WsClient.test_JobManagementWs.JobPriorityExt.Average;
|
|
|
testJob.project = "ExpTests"; //accounting project
|
|
|
testJob.waitingLimit = null; //limit for the waiting time in cluster queue
|
|
|
testJob.walltimeLimit = 600; //maximum time for job to run (seconds)
|
|
|
testJob.clusterNodeTypeId = 7; //Salomon express queue (1h limit)
|
|
|
//custom environment variables for the job
|
|
|
testJob.environmentVariables = new EnvironmentVariableExt[0];
|
|
|
//assign created task to job specification
|
|
|
testJob.tasks = new TaskSpecificationExt[] { testTask };
|
|
|
|
|
|
//create job
|
|
|
SubmittedJobInfoExt submittedTestJob = wsJobManagement.CreateJob(testJob, sessionCode);
|
|
|
Console.WriteLine("Created job ID {0}.", submittedTestJob.id);
|
|
|
|
|
|
//upload input files
|
|
|
FileTransferMethodExt ft = wsFileTransfer.GetFileTransferMethod(
|
|
|
(long)submittedTestJob.id, sessionCode);
|
|
|
using (MemoryStream pKeyStream = new MemoryStream(
|
|
|
Encoding.UTF8.GetBytes(ft.credentials.privateKey)))
|
|
|
{
|
|
|
using (ScpClient scpClient = new ScpClient(ft.serverHostname,
|
|
|
ft.credentials.username, new PrivateKeyFile(pKeyStream)))
|
|
|
{
|
|
|
scpClient.Connect();
|
|
|
DirectoryInfo di = new DirectoryInfo(@"C:\InputFiles\");
|
|
|
foreach (FileInfo fi in di.GetFiles())
|
|
|
{
|
|
|
Console.WriteLine("Uploading file: " + fi.Name);
|
|
|
scpClient.Upload(fi, ft.sharedBasepath + "//" + fi.Name);
|
|
|
Console.WriteLine("File uploaded.");
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
wsFileTransfer.EndFileTransfer((long)submittedTestJob.id, ft, sessionCode);
|
|
|
|
|
|
//submit the job to a cluster queue for processing
|
|
|
submittedTestJob = wsJobManagement.SubmitJob((long)submittedTestJob.id, sessionCode);
|
|
|
Console.WriteLine("Submitted job ID: {0}", submittedTestJob.id);
|
|
|
|
|
|
//check status of running job (submitted/configuring/queued/running)
|
|
|
SubmittedJobInfoExt submittedJob;
|
|
|
long jobId = (long)submittedTestJob.id;
|
|
|
do
|
|
|
{
|
|
|
//wait 30s before the next status check
|
|
|
System.Threading.Thread.Sleep(30000);
|
|
|
//get info for the job
|
|
|
submittedJob = wsJobManagement.GetCurrentInfoForJob(jobId, sessionCode);
|
|
|
Console.WriteLine(submittedJob.state);
|
|
|
//set offsets for the stdout, stderr, stdprog, stdlog files
|
|
|
//offsets can be used for the partial download of files
|
|
|
List<TaskFileOffsetExt> offsets = new List<TaskFileOffsetExt>();
|
|
|
foreach (SubmittedTaskInfoExt taskInfo in submittedJob.tasks)
|
|
|
{
|
|
|
TaskFileOffsetExt off = new TaskFileOffsetExt();
|
|
|
off.fileType = SynchronizableFilesExt.LogFile;
|
|
|
off.submittedTaskInfoId = taskInfo.id;
|
|
|
off.offset = 0;
|
|
|
offsets.Add(off);
|
|
|
|
|
|
off = new TaskFileOffsetExt();
|
|
|
off.fileType = SynchronizableFilesExt.ProgressFile;
|
|
|
off.submittedTaskInfoId = taskInfo.id;
|
|
|
off.offset = 0;
|
|
|
offsets.Add(off);
|
|
|
|
|
|
off = new TaskFileOffsetExt();
|
|
|
off.fileType = SynchronizableFilesExt.StandardErrorFile;
|
|
|
off.submittedTaskInfoId = taskInfo.id;
|
|
|
off.offset = 0;
|
|
|
offsets.Add(off);
|
|
|
|
|
|
off = new TaskFileOffsetExt();
|
|
|
off.fileType = SynchronizableFilesExt.StandardOutputFile;
|
|
|
off.submittedTaskInfoId = taskInfo.id;
|
|
|
off.offset = 0;
|
|
|
offsets.Add(off);
|
|
|
}
|
|
|
|
|
|
//donwload stdouts based on the offsets
|
|
|
JobFileContentExt[] result = wsFileTransfer.DownloadPartsOfJobFilesFromCluster(
|
|
|
jobId, offsets.ToArray(), sessionCode);
|
|
|
//print each file
|
|
|
foreach (JobFileContentExt file in result)
|
|
|
{
|
|
|
Console.WriteLine("File: " + file.fileType + ", " + file.relativePath);
|
|
|
Console.WriteLine("TaskInfoId: " + file.submittedTaskInfoId);
|
|
|
Console.WriteLine("Offset: " + file.offset);
|
|
|
Console.WriteLine("Content: " + file.content);
|
|
|
}
|
|
|
}
|
|
|
While (submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Submitted
|
|
|
|| submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Configuring
|
|
|
|| submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Queued
|
|
|
|| submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Running);
|
|
|
|
|
|
//job computation is done (finished/failed/canceled)
|
|
|
submittedJob = wsJobManagement.GetCurrentInfoForJob(jobId, sessionCode);
|
|
|
// job finished successfully, download result files from the cluster
|
|
|
if (submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Finished)
|
|
|
{
|
|
|
ft = wsFileTransfer.GetFileTransferMethod(jobId, sessionCode);
|
|
|
using (MemoryStream pKeyStream = new MemoryStream(Encoding.UTF8.GetBytes(
|
|
|
ft.credentials.privateKey)))
|
|
|
{
|
|
|
using (ScpClient scpClient = new ScpClient(ft.serverHostname,
|
|
|
ft.credentials.username, new PrivateKeyFile(pKeyStream)))
|
|
|
{
|
|
|
scpClient.Connect();
|
|
|
|
|
|
// changed result files
|
|
|
string[] changedFiles = wsFileTransfer.ListChangedFilesForJob(
|
|
|
jobId, sessionCode);
|
|
|
foreach (string file in changedFiles)
|
|
|
{
|
|
|
Console.WriteLine("Downloading file: " + file);
|
|
|
FileInfo fi = new FileInfo(@"C:\OutputFiles\" + file);
|
|
|
scpClient.Download(ft.sharedBasepath + "//" + file, fi);
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
wsFileTransfer.EndFileTransfer(jobId, ft, sessionCode);
|
|
|
}
|
|
|
// job failed or was canceled
|
|
|
else if (submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Failed
|
|
|
|| submittedJob.state == WsClient.test_JobManagementWs.JobStateExt.Canceled)
|
|
|
{
|
|
|
// do nothing
|
|
|
}
|
|
|
}
|
|
|
|
|
|
private static void AuthenticateUserPassword()
|
|
|
{
|
|
|
Console.WriteLine("Authenticating user [{0}]...", "[testuser]");
|
|
|
PasswordCredentialsExt credentials = new PasswordCredentialsExt();
|
|
|
credentials.username = "[testuser]";
|
|
|
credentials.password = "[testpass]";
|
|
|
sessionCode = wsUserAndLimitationManagement.AuthenticateUserPassword(credentials);
|
|
|
Console.WriteLine("\tAuth OK (Session GUID: {0})", sessionCode);
|
|
|
}
|
|
|
|
|
|
}
|
|
|
}
|
|
|
``` |