Example #1
0
        /// <summary>
        ///   <para>
        /// Initializes session parameters and calls open session. Only for cluster computation.
        /// </para>
        /// </summary>
        /// <param name="headNode">
        ///   <para>Name of cluster head node</para>
        /// </param>
        /// <param name="remoteWorkbookPath">
        ///   <para>Workbook location relative to compute node</para>
        /// </param>
        /// <param name="minResources">
        ///   <para>minimum number of resources requested</para>
        /// </param>
        /// <param name="maxResources">
        ///   <para>Maximum number of resources required</para>
        /// </param>
        /// <param name="resourceType">
        ///   <para>Name of resource requested (core, node, or socket)</para>
        /// </param>
        /// <param name="jobTemplate">
        ///   <para> Name of the job template to be used </para>
        /// </param>
        /// <param name="serviceName">
        ///   <para> Name of the service to use </para>
        /// </param>
        /// <param name="jobName">
        ///   <para>Specify the job name</para>
        /// </param>
        /// <param name="projectName">
        ///   <para>Specify the project name</para>
        /// </param>
        /// <param name="transportScheme">
        ///   <para>The transport scheme (Http or NetTcp)</para>
        /// </param>
        /// <param name="useAzureQueue">
        ///   <para>Specify if Azure storage queue is used (True or False)</para>
        /// </param>
        /// <param name="username">
        ///   <para>Specify the user name</para>
        /// </param>
        /// <param name="password">
        ///   <para>Specify the password</para>
        /// </param>
        /// <param name="jobPriority">
        ///   <para>Specify the job priority</para>
        /// </param>
        /// <returns>
        ///   <para> ID of opened session </para>
        /// </returns>
        public int OpenSession(string headNode, string remoteWorkbookPath, [Optional] object minResources, [Optional] object maxResources, [Optional] object resourceType, [Optional] string jobTemplate, [Optional] string serviceName, [Optional] string jobName, [Optional] string projectName, [Optional] string transportScheme, [Optional] object useAzureQueue, [Optional] string username, [Optional] string password, [Optional] object jobPriority)
        {
            // Check if workbook path has been provided (ExcelClient initialize called)
            if (!this.initialized)
            {
                Tracing.WriteDebugTextError(Tracing.ComponentId.ExcelClient, Resources.ExcelClientOpenSessionBeforeInit);
                throw new InvalidOperationException(Resources.ExcelClientOpenSessionBeforeInit);
            }
            SessionStartInfo info;
            bool             useWebApi = false;

            if (headNode.StartsWith("d:", StringComparison.OrdinalIgnoreCase))
            {
                // HACK: using head node string to pass actual parameters
                var      param = headNode.Split('?');
                string   serviceRegDirectory = null;
                string[] computeNodeIpList   = null;
                string   storageCredential   = null;
                string[] dependFiles         = null;

                bool CheckParameterSwitch(string parameter, string switchStr)
                {
                    return(parameter.StartsWith(switchStr, StringComparison.OrdinalIgnoreCase));
                }

                foreach (var p in param)
                {
                    if (CheckParameterSwitch(p, "d:"))
                    {
                        serviceRegDirectory = p.Substring(p.IndexOf(":") + 1);
                    }
                    else if (CheckParameterSwitch(p, "c:"))
                    {
                        computeNodeIpList = p.Substring(p.IndexOf(":") + 1).Split(',');
                    }
                    else if (CheckParameterSwitch(p, "s:"))
                    {
                        storageCredential = p.Substring(p.IndexOf(":") + 1);
                    }
                    else if (CheckParameterSwitch(p, "f:"))
                    {
                        dependFiles = p.Substring(p.IndexOf(":") + 1).Split(',');
                    }
                }

                if (serviceRegDirectory == null || computeNodeIpList == null)
                {
                    throw new ArgumentNullException();
                }


                // Standalone mode
                if (string.IsNullOrEmpty(serviceName))
                {
                    info = new SessionStartInfo(Microsoft.Hpc.Excel.ExcelClient.SERVICE, serviceRegDirectory, null, computeNodeIpList);
                }
                else
                {
                    info = new SessionStartInfo(serviceName, serviceRegDirectory, null, computeNodeIpList);
                }

                if (dependFiles != null && dependFiles.Any())
                {
                    // Start data client related logic
                    // TODO: move logic into ExcelClient
                    try
                    {
                        if (string.IsNullOrEmpty(storageCredential))
                        {
                            throw new ArgumentNullException(nameof(storageCredential));
                        }

                        StandaloneDataClient dataClient = new StandaloneDataClient(storageCredential);
                        var sasTokens = dataClient.UploadFilesAsync(dependFiles).GetAwaiter().GetResult();

                        if (sasTokens.Length != dependFiles.Length)
                        {
                            throw new InvalidOperationException($"Number of sas token ({sasTokens.Length}) does not equal to depend files ({dependFiles.Length})");
                        }

                        var depFileInfo = new Dictionary <string, string>();
                        for (int i = 0; i != sasTokens.Length; ++i)
                        {
                            depFileInfo[Path.GetFileName(dependFiles[i])] = sasTokens[i];
                        }

                        info.DependFilesStorageInfo = depFileInfo;
                        remoteWorkbookPath          = Path.GetFileName(remoteWorkbookPath);
                    }
                    catch (Exception ex)
                    {
                        Tracing.SoaTrace(
                            XlTraceLevel.Error, "error when uploading files {0}", ex.ToString());
                        throw;
                    }

                    // End data client related logic
                }

                info.UseInprocessBroker = true;
                info.IsNoSession        = true;
            }
            else
            {
                // If https prefix from head node name
                useWebApi = Microsoft.Hpc.Excel.ExcelClient.TryRemoveWebApiPrefix(ref headNode);

                // If the service name is provided, use it rather than the default in ExcelClient
                if (string.IsNullOrEmpty(serviceName))
                {
                    info = new SessionStartInfo(headNode, Microsoft.Hpc.Excel.ExcelClient.SERVICE);
                }
                else
                {
                    info = new SessionStartInfo(headNode, serviceName);
                }
            }

            if (useWebApi)
            {
                info.TransportScheme = TransportScheme.WebAPI;
            }

            if (!string.IsNullOrEmpty(transportScheme))
            {
                if (transportScheme.Equals("Http", StringComparison.InvariantCultureIgnoreCase))
                {
                    info.TransportScheme = TransportScheme.Http;
                }
                else if (transportScheme.Equals("NetTcp", StringComparison.InvariantCultureIgnoreCase))
                {
                    info.TransportScheme = TransportScheme.NetTcp;
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidTransportScheme, transportScheme), "transportScheme");
                }
            }

            if (!(useAzureQueue == null || System.Reflection.Missing.Value.Equals(useAzureQueue) || DBNull.Value.Equals(useAzureQueue)))
            {
                bool useAQ;
                if (bool.TryParse(useAzureQueue.ToString(), out useAQ))
                {
                    info.UseAzureQueue = useAQ;
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidBoolParamValue, "useAzureQueue", useAzureQueue), "useAzureQueue");
                }
            }

            if (!string.IsNullOrEmpty(username))
            {
                info.Username = username;
            }

            if (!string.IsNullOrEmpty(password))
            {
                info.Password = password;
            }

            if (!string.IsNullOrEmpty(jobName))
            {
                info.ServiceJobName = jobName;
            }

            if (!string.IsNullOrEmpty(projectName))
            {
                info.Project = projectName;
            }

            // If jobPriority is specified, try to parse it into an integer.
            if (!(jobPriority == null || System.Reflection.Missing.Value.Equals(jobPriority) || DBNull.Value.Equals(jobPriority)))
            {
                int priority;
                if (int.TryParse(jobPriority.ToString(), out priority))
                {
                    info.SessionPriority = priority;
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidMinCores, jobPriority), "minResources");
                }
            }

            // If minResources is specified, try to parse it into an integer.
            if (!(minResources == null || System.Reflection.Missing.Value.Equals(minResources) || DBNull.Value.Equals(minResources)))
            {
                int minUnits;
                if (int.TryParse(minResources.ToString(), out minUnits))
                {
                    info.MinimumUnits = minUnits;
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidMinCores, minResources), "minResources");
                }
            }

            // If maxResources is specified, try to parse it into an integer
            if (!(maxResources == null || System.Reflection.Missing.Value.Equals(maxResources) || DBNull.Value.Equals(maxResources)))
            {
                int maxUnits;
                if (int.TryParse(maxResources.ToString(), out maxUnits))
                {
                    info.MaximumUnits = maxUnits;
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidMaxCores, maxResources), "maxResources");
                }
            }

            // If job template is specified, set it
            if (!string.IsNullOrEmpty(jobTemplate))
            {
                info.JobTemplate = jobTemplate;
            }

            // Set resource type (defaults to core)
            if (!(resourceType == null || System.Reflection.Missing.Value.Equals(resourceType) || DBNull.Value.Equals(resourceType)))
            {
                int resIndex;
                if (int.TryParse(resourceType.ToString(), out resIndex))
                {
                    info.SessionResourceUnitType = ResourceToSessionUnitType((Microsoft.Hpc.Excel.Com.SessionUnitType)resIndex);
                }
                else
                {
                    throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, Resources.ExcelClient_InvalidResType, resourceType), "resourceType");
                }
            }

            // Set interface mode to UI to ensure that Excel asks for credentials in the UI when not cached
            SessionBase.SetInterfaceMode(false, new IntPtr(this.client.Driver.App.Hwnd));

            return(this.client.OpenSession(info, remoteWorkbookPath));
        }