Exemple #1
0
        public static string GetDeadlineExcludeFromLimitGroupsString(this PoolConfigurationModel poolConfiguration, DeadlineConfig deadlineConfig)
        {
            if (poolConfiguration == null)
            {
                return(null);
            }

            // Get pool limit groups, or environment limitgroups, if specified.
            var limitgroups = !string.IsNullOrWhiteSpace(poolConfiguration.ExcludeFromLimitGroups)
                ? poolConfiguration.ExcludeFromLimitGroups
                : deadlineConfig != null && !string.IsNullOrWhiteSpace(deadlineConfig.ExcludeFromLimitGroups) ? deadlineConfig.ExcludeFromLimitGroups : null;

            if (!string.IsNullOrWhiteSpace(limitgroups))
            {
                var trimmed = limitgroups
                              .Split(',', StringSplitOptions.RemoveEmptyEntries)
                              .Select(lg => lg.Trim());

                if (trimmed.Any())
                {
                    // Multiple limit groups are separated by a space
                    return(string.Join(';', trimmed));
                }
            }

            return(null);
        }
        public async Task <ActionResult <PoolConfigurationModel> > New(string envId)
        {
            var environment = await _environmentCoordinator.GetEnvironment(envId);

            if (environment == null)
            {
                return(RedirectToAction("Index", "Environments"));
            }

            var result = new PoolConfigurationModel {
                EnvironmentName = envId
            };

            try
            {
                await PopulateSelectableProperties(environment, result);
            }
            catch (CloudException cEx)
            {
                // TODO: Log somewhere
                Console.WriteLine(cEx);
                ModelState.AddModelError("", $"Failed to configure pool creation form with error: {cEx.Message}");
            }

            return(View(result));
        }
 private void ValidateImageRefOrCustomAndSku(PoolConfigurationModel poolConfiguration)
 {
     if (string.IsNullOrWhiteSpace(poolConfiguration.ImageReference) && string.IsNullOrWhiteSpace(poolConfiguration.CustomImageReference))
     {
         ModelState.AddModelError(nameof(PoolConfigurationModel.ImageReference), Validation.Errors.Custom.ImageRefOrCustom);
         ModelState.AddModelError(nameof(PoolConfigurationModel.CustomImageReference), Validation.Errors.Custom.ImageRefOrCustom);
     }
 }
        public void CanUseGroupsInsteadOfPoolsAndSpecifyAdditionalGroups()
        {
            var poolConfig = new PoolConfigurationModel {
                PoolName = "mypool", UseDeadlineGroups = true, AdditionalGroups = "group1,group2"
            };

            Assert.Equal("mypool,group1,group2", poolConfig.GetDeadlineGroupsString());
        }
        public void CanSpecifyAdditionalGroups()
        {
            var poolConfig = new PoolConfigurationModel {
                PoolName = "mypool", AdditionalGroups = "group1,group2"
            };

            Assert.Equal("group1,group2", poolConfig.GetDeadlineGroupsString());
        }
Exemple #6
0
        public void LimitGroupsAreTrimmed()
        {
            var poolConfig = new PoolConfigurationModel {
                ExcludeFromLimitGroups = "limitgroup,  limitgroup2"
            };
            var deadlineConfig = new DeadlineConfig();

            Assert.Equal("limitgroup;limitgroup2", poolConfig.GetDeadlineExcludeFromLimitGroupsString(deadlineConfig));
        }
        public void DefaultsToPoolName()
        {
            var poolConfig = new PoolConfigurationModel {
                PoolName = "mypool"
            };

            Assert.Equal("mypool", poolConfig.GetDeadlinePoolsString());
            Assert.Null(poolConfig.GetDeadlineGroupsString());
        }
        public void UseGroupInsteadOfPool()
        {
            var poolConfig = new PoolConfigurationModel {
                PoolName = "mypool", UseDeadlineGroups = true,
            };

            Assert.Equal("mypool", poolConfig.GetDeadlineGroupsString());
            Assert.Null(poolConfig.GetDeadlinePoolsString());
        }
        public void CanSpecifyAdditionalPools()
        {
            var poolConfig = new PoolConfigurationModel {
                PoolName = "mypool", AdditionalPools = "pool1,pool2"
            };

            Assert.Equal("mypool,pool1,pool2", poolConfig.GetDeadlinePoolsString());
            Assert.Null(poolConfig.GetDeadlineGroupsString());
        }
Exemple #10
0
        public void EmptyExcludeFromLimitGroupsReturnsNull()
        {
            var poolConfig = new PoolConfigurationModel {
                ExcludeFromLimitGroups = ""
            };
            var deadlineConfig = new DeadlineConfig();

            Assert.Null(poolConfig.GetDeadlineExcludeFromLimitGroupsString(deadlineConfig));
        }
Exemple #11
0
        public void EnvironmentLimitGroupsIsUsedWhenNoPoolLimitGroup()
        {
            var poolConfig = new PoolConfigurationModel {
                ExcludeFromLimitGroups = null
            };
            var envDeadlineConfig = new DeadlineConfig {
                ExcludeFromLimitGroups = "environmentLimitGroup"
            };

            Assert.Equal("environmentLimitGroup", poolConfig.GetDeadlineExcludeFromLimitGroupsString(envDeadlineConfig));
        }
Exemple #12
0
        public void PoolLimitGroupsOverrideEnvironment()
        {
            var poolConfig = new PoolConfigurationModel {
                ExcludeFromLimitGroups = "limitgroup"
            };
            var envDeadlineConfig = new DeadlineConfig {
                ExcludeFromLimitGroups = "environmentLimitGroup"
            };

            Assert.Equal("limitgroup", poolConfig.GetDeadlineExcludeFromLimitGroupsString(envDeadlineConfig));
        }
Exemple #13
0
        private void AppendOpenCueParamsToStartTask(
            PoolConfigurationModel poolConfiguration,
            RenderingEnvironment environment,
            StartTask startTask,
            OpenCueConfig openCueConfig,
            InstallationPackage openCuePackage,
            bool isWindows)
        {
            var commandLine   = startTask.CommandLine;
            var resourceFiles = new List <ResourceFile>(startTask.ResourceFiles);

            if (environment.KeyVaultServicePrincipal != null)
            {
                commandLine += GetParameterSet(isWindows, "tenantId", environment.KeyVaultServicePrincipal.TenantId.ToString());
                commandLine += GetParameterSet(isWindows, "applicationId", environment.KeyVaultServicePrincipal.ApplicationId.ToString());
                commandLine += GetParameterSet(isWindows, "keyVaultCertificateThumbprint", environment.KeyVaultServicePrincipal.Thumbprint);
                commandLine += GetParameterSet(isWindows, "keyVaultName", environment.KeyVault.Name);
            }

            if (!string.IsNullOrWhiteSpace(openCueConfig.CuebotHostnameOrIp))
            {
                commandLine += GetParameterSet(isWindows, "cuebotHost", openCueConfig.CuebotHostnameOrIp);
            }

            if (!string.IsNullOrWhiteSpace(openCueConfig.Facility))
            {
                commandLine += GetParameterSet(isWindows, "facility", openCueConfig.Facility);
            }

            var groups = $"azure,{poolConfiguration.PoolName}";

            if (poolConfiguration.AdditionalGroups != null && poolConfiguration.AdditionalGroups.Any())
            {
                groups += $",{string.Join(',', poolConfiguration.AdditionalGroups)}";
            }

            if (!string.IsNullOrWhiteSpace(groups))
            {
                commandLine += GetParameterSet(isWindows, "groups", groups);
            }

            if (openCuePackage != null && !string.IsNullOrEmpty(openCuePackage.Container))
            {
                resourceFiles.Add(GetContainerResourceFile(openCuePackage.Container, openCuePackage.PackageName));
                commandLine += GetParameterSet(isWindows, "installerPath", openCuePackage.PackageName);
            }

            commandLine += ";";

            startTask.CommandLine   = commandLine;
            startTask.ResourceFiles = resourceFiles;
        }
Exemple #14
0
        public static string GetDeadlinePoolsString(this PoolConfigurationModel poolConfiguration)
        {
            if (poolConfiguration == null)
            {
                return(null);
            }

            var pools = poolConfiguration.UseDeadlineGroups ? "" : poolConfiguration.PoolName;

            if (poolConfiguration.AdditionalPools != null && poolConfiguration.AdditionalPools.Any())
            {
                pools += string.IsNullOrEmpty(pools) ? "" : ",";
                pools += string.Join(',', poolConfiguration.AdditionalPools);
            }

            return(string.IsNullOrEmpty(pools) ? null : pools);
        }
Exemple #15
0
        public static string GetDeadlineGroupsString(this PoolConfigurationModel poolConfiguration)
        {
            if (poolConfiguration == null)
            {
                return(null);
            }

            var groups = poolConfiguration.UseDeadlineGroups ? poolConfiguration.PoolName : "";

            if (poolConfiguration.AdditionalGroups != null && poolConfiguration.AdditionalGroups.Any())
            {
                groups += string.IsNullOrEmpty(groups) ? "" : ",";
                groups += string.Join(',', poolConfiguration.AdditionalGroups);
            }

            return(string.IsNullOrEmpty(groups) ? null : groups);
        }
Exemple #16
0
        private async Task AppendQubeParamsToStartTask(
            PoolConfigurationModel poolConfiguration,
            RenderingEnvironment environment,
            StartTask startTask,
            QubeConfig qubeConfig,
            InstallationPackage qubePackage,
            bool isWindows)
        {
            var commandLine   = startTask.CommandLine;
            var resourceFiles = new List <ResourceFile>(startTask.ResourceFiles);

            var workerGroups = $"azure,{poolConfiguration.PoolName}";

            if (poolConfiguration.AdditionalGroups != null && poolConfiguration.AdditionalGroups.Any())
            {
                workerGroups += $",{string.Join(',', poolConfiguration.AdditionalGroups)}";
            }

            commandLine += $"-qubeSupervisorIp {qubeConfig.SupervisorIp} " +
                           $"-workerHostGroups '{workerGroups}'";

            if (qubePackage != null && !string.IsNullOrEmpty(qubePackage.Container))
            {
                resourceFiles.AddRange(await GetResourceFilesFromContainer(qubePackage.Container));

                // Add qb.conf if one isn't already specified by the package
                if (!resourceFiles.Any(rf => rf.FilePath.Contains("qb.conf")))
                {
                    var qbConfResourceFile = new ResourceFile(httpUrl: _configuration["Qube:QbConf"], filePath: "qb.conf");
                    resourceFiles.Add(qbConfResourceFile);
                }
            }
            else
            {
                // No package, lets just configure
                commandLine += " -skipInstall ";
            }

            commandLine += ";";

            startTask.CommandLine   = commandLine;
            startTask.ResourceFiles = resourceFiles;
        }
Exemple #17
0
        private void AppendBYOSParamsToStartTask(
            PoolConfigurationModel poolConfiguration,
            RenderingEnvironment environment,
            StartTask startTask,
            BYOSConfig byosConfig,
            bool isWindows)
        {
            var commandLine   = startTask.CommandLine;
            var resourceFiles = new List <ResourceFile>(startTask.ResourceFiles);

            if (environment.KeyVaultServicePrincipal != null)
            {
                commandLine += GetParameterSet(isWindows, "tenantId", environment.KeyVaultServicePrincipal.TenantId.ToString());
                commandLine += GetParameterSet(isWindows, "applicationId", environment.KeyVaultServicePrincipal.ApplicationId.ToString());
                commandLine += GetParameterSet(isWindows, "keyVaultCertificateThumbprint", environment.KeyVaultServicePrincipal.Thumbprint);
                commandLine += GetParameterSet(isWindows, "keyVaultName", environment.KeyVault.Name);
            }

            if (!string.IsNullOrWhiteSpace(byosConfig.SchedulerHostnameOrIp))
            {
                commandLine += GetParameterSet(isWindows, "host", byosConfig.SchedulerHostnameOrIp);
            }

            var groups = $"azure,{poolConfiguration.PoolName}";

            if (poolConfiguration.AdditionalGroups != null && poolConfiguration.AdditionalGroups.Any())
            {
                groups += $",{string.Join(',', poolConfiguration.AdditionalGroups)}";
            }

            if (!string.IsNullOrWhiteSpace(groups))
            {
                commandLine += GetParameterSet(isWindows, "groups", groups);
            }

            commandLine += ";";

            startTask.CommandLine   = commandLine;
            startTask.ResourceFiles = resourceFiles;
        }
Exemple #18
0
        public static void AddDeadlinePoolsAndGroups(this IList <MetadataItem> metadata, PoolConfigurationModel poolConfiguration)
        {
            if (metadata == null)
            {
                return;
            }

            var pools = poolConfiguration.GetDeadlinePoolsString();

            if (!string.IsNullOrEmpty(pools))
            {
                metadata.AddOrUpdateMetadata(MetadataKeys.DeadlinePools, pools);
            }

            var groups = poolConfiguration.GetDeadlineGroupsString();

            if (!string.IsNullOrEmpty(groups))
            {
                metadata.AddOrUpdateMetadata(MetadataKeys.DeadlineGroups, groups);
            }
        }
Exemple #19
0
        private void AppendDeadlineParamsToStartTask(
            PoolConfigurationModel poolConfiguration,
            RenderingEnvironment environment,
            StartTask startTask,
            DeadlineConfig deadlineConfig,
            InstallationPackage deadlinePackage,
            bool isWindows)
        {
            var commandLine   = startTask.CommandLine;
            var resourceFiles = new List <ResourceFile>(startTask.ResourceFiles);

            if (deadlinePackage != null && !string.IsNullOrEmpty(deadlinePackage.Container))
            {
                resourceFiles.Add(GetContainerResourceFile(deadlinePackage.Container, deadlinePackage.PackageName));
                commandLine += GetParameterSet(isWindows, "installerPath", deadlinePackage.PackageName);
            }

            if (isWindows & environment.Domain != null && environment.Domain.JoinDomain)
            {
                commandLine += GetParameterSet(isWindows, "domainJoin");
                commandLine += GetParameterSet(isWindows, "domainName", environment.Domain.DomainName);
                commandLine += GetParameterSet(isWindows, "domainJoinUserName", environment.Domain.DomainJoinUsername);

                if (!string.IsNullOrWhiteSpace(environment.Domain.DomainWorkerOuPath))
                {
                    commandLine += GetParameterSet(isWindows, "domainOuPath", environment.Domain.DomainWorkerOuPath);
                }
            }

            if (environment.KeyVaultServicePrincipal != null)
            {
                commandLine += GetParameterSet(isWindows, "tenantId", environment.KeyVaultServicePrincipal.TenantId.ToString());
                commandLine += GetParameterSet(isWindows, "applicationId", environment.KeyVaultServicePrincipal.ApplicationId.ToString());
                commandLine += GetParameterSet(isWindows, "keyVaultCertificateThumbprint", environment.KeyVaultServicePrincipal.Thumbprint);
                commandLine += GetParameterSet(isWindows, "keyVaultName", environment.KeyVault.Name);
            }

            var repoPath = isWindows ? deadlineConfig.WindowsRepositoryPath : deadlineConfig.LinuxRepositoryPath;

            if (!string.IsNullOrWhiteSpace(repoPath))
            {
                commandLine += GetParameterSet(isWindows, "deadlineRepositoryPath", deadlineConfig.WindowsRepositoryPath);
            }

            if (!string.IsNullOrEmpty(deadlineConfig.RepositoryUser))
            {
                commandLine += GetParameterSet(isWindows, "deadlineRepositoryUserName", deadlineConfig.RepositoryUser);
            }

            if (!string.IsNullOrEmpty(deadlineConfig.ServiceUser))
            {
                commandLine += GetParameterSet(isWindows, "deadlineServiceUserName", deadlineConfig.ServiceUser);
            }
            else
            {
                // If the Deadline slave is running under the start task context (not a service)
                // then we don't want to wait for success as it will block after launching the
                // Deadline launcher to prevent it being killed.
                startTask.WaitForSuccess = false;
            }

            if (deadlineConfig.LicenseMode != null)
            {
                commandLine += GetParameterSet(isWindows, "deadlineLicenseMode", deadlineConfig.LicenseMode.ToString());
            }

            if (!string.IsNullOrEmpty(deadlineConfig.DeadlineRegion))
            {
                commandLine += GetParameterSet(isWindows, "deadlineRegion", deadlineConfig.DeadlineRegion);
            }

            if (!string.IsNullOrEmpty(deadlineConfig.LicenseServer))
            {
                commandLine += GetParameterSet(isWindows, "deadlineLicenseServer", deadlineConfig.LicenseServer);
            }

            var pools = poolConfiguration.GetDeadlinePoolsString();

            if (!string.IsNullOrEmpty(pools))
            {
                commandLine += GetParameterSet(isWindows, "deadlinePools", pools);
            }

            var groups = poolConfiguration.GetDeadlineGroupsString();

            if (!string.IsNullOrEmpty(groups))
            {
                commandLine += GetParameterSet(isWindows, "deadlineGroups", groups);
            }

            var limitGroups = poolConfiguration.GetDeadlineExcludeFromLimitGroupsString(deadlineConfig);

            if (!string.IsNullOrWhiteSpace(limitGroups))
            {
                commandLine += GetParameterSet(isWindows, "excludeFromLimitGroups", limitGroups);
            }

            commandLine += "; ";

            if (!isWindows)
            {
                commandLine += "wait";
            }

            startTask.CommandLine   = commandLine;
            startTask.ResourceFiles = resourceFiles;
        }
        public async Task <ActionResult <PoolConfigurationModel> > New(string envId, PoolConfigurationModel model)
        {
            ValidateImageRefOrCustomAndSku(model);

            var environment = await _environmentCoordinator.GetEnvironment(envId);

            if (environment == null)
            {
                return(RedirectToAction("Index", "Environments"));
            }

            var packageErrors = false;
            InstallationPackage renderManagerPackage = null;
            var renderManagerPackageSelected         = model.SelectedRenderManagerPackageId != NoPackageSelected;

            if (renderManagerPackageSelected)
            {
                renderManagerPackage = await _packageCoordinator.GetPackage(model.SelectedRenderManagerPackageId);

                if (renderManagerPackage == null)
                {
                    packageErrors = true;
                    ModelState.AddModelError(nameof(PoolConfigurationModel.SelectedRenderManagerPackageId), Validation.Errors.Custom.PackageNotFound);
                }
            }

            InstallationPackage gpuPackage = null;
            var gpuPackageSelected         = model.SelectedGpuPackageId != NoPackageSelected;

            if (gpuPackageSelected)
            {
                gpuPackage = await _packageCoordinator.GetPackage(model.SelectedGpuPackageId);

                if (gpuPackage == null)
                {
                    packageErrors = true;
                    ModelState.AddModelError(nameof(PoolConfigurationModel.SelectedGpuPackageId), Validation.Errors.Custom.PackageNotFound);
                }
            }

            List <InstallationPackage> generalPackages = new List <InstallationPackage>();

            if (model.SelectedGeneralPackageIds != null)
            {
                foreach (var selectedGeneralPackageId in GetSelectedGeneralPackages(model.SelectedGeneralPackageIds))
                {
                    var package = await _packageCoordinator.GetPackage(selectedGeneralPackageId);

                    if (package == null)
                    {
                        packageErrors = true;
                        ModelState.AddModelError(nameof(PoolConfigurationModel.SelectedGeneralPackageIds), Validation.Errors.Custom.PackageNotFound);
                    }
                    else
                    {
                        generalPackages.Add(package);
                    }
                }
            }

            if (!ModelState.IsValid || packageErrors)
            {
                ModelState.AddModelError("", Validation.Errors.Custom.FormSummary);
                await PopulateSelectableProperties(environment, model);

                return(View(model));
            }

            try
            {
                var mappedPool = await MapFromConfiguration(model, renderManagerPackage, gpuPackage, generalPackages);

                await _poolCoordinator.CreatePool(environment, mappedPool);
            }
            catch (CloudException cEx)
            {
                // TODO: Log somewhere
                Console.WriteLine(cEx);
                ModelState.AddModelError("", $"Pool creation failed with error: {cEx.Message}{cEx.Response?.Content}");
            }
            catch (Exception ex)
            {
                // TODO: Log somewhere
                Console.WriteLine(ex);
                ModelState.AddModelError("", $"Failed to configure pool with error: {ex}");
            }

            // if any of the above failed
            if (!ModelState.IsValid)
            {
                await PopulateSelectableProperties(environment, model);

                return(View(model));
            }

            return(RedirectToAction("Overview", new { envId, poolId = model.PoolName }));
        }
Exemple #21
0
        public async Task <StartTask> GetStartTask(
            PoolConfigurationModel poolConfiguration,
            RenderingEnvironment environment,
            InstallationPackage renderManagerPackage,
            InstallationPackage gpuPackage,
            IEnumerable <InstallationPackage> generalPackages,
            bool isWindows)
        {
            var resourceFiles = new List <ResourceFile>();

            var startTask = new StartTask(
                "",
                resourceFiles,
                GetEnvironmentSettings(environment, isWindows),
                new UserIdentity(
                    autoUser: new AutoUserSpecification(AutoUserScope.Pool, ElevationLevel.Admin)),
                3,     // retries
                true); // waitForSuccess

            AppendGpu(startTask, gpuPackage);

            AppendDomainSetup(startTask, environment);

            AppendGeneralPackages(startTask, generalPackages);

            // Appends the start task script, i.e. deadline-starttask.ps1 or tractor-starttask.ps1
            AppendRenderManagerStartTask(environment, startTask, isWindows);

            // Appends the render manager specific parameters and package (if specified)
            switch (environment.RenderManager)
            {
            case RenderManagerType.Deadline:
                AppendDeadlineParamsToStartTask(
                    poolConfiguration,
                    environment,
                    startTask,
                    environment.RenderManagerConfig.Deadline,
                    renderManagerPackage,
                    isWindows);
                break;

            case RenderManagerType.OpenCue:
                AppendOpenCueParamsToStartTask(
                    poolConfiguration,
                    environment,
                    startTask,
                    environment.RenderManagerConfig.OpenCue,
                    renderManagerPackage,
                    isWindows);
                break;

            case RenderManagerType.Qube610:
            case RenderManagerType.Qube70:
                await AppendQubeParamsToStartTask(
                    poolConfiguration,
                    environment,
                    startTask,
                    environment.RenderManagerConfig.Qube,
                    renderManagerPackage,
                    isWindows);

                break;

            case RenderManagerType.Tractor2:
                AppendTractorParamsToStartTask(
                    poolConfiguration,
                    environment,
                    startTask,
                    environment.RenderManagerConfig.Tractor,
                    renderManagerPackage,
                    isWindows);
                break;

            case RenderManagerType.BYOS:
                AppendBYOSParamsToStartTask(
                    poolConfiguration,
                    environment,
                    startTask,
                    environment.RenderManagerConfig.BYOS,
                    isWindows);
                break;
            }

            // Wrap all the start task command
            if (isWindows)
            {
                startTask.CommandLine = $"powershell.exe -ExecutionPolicy RemoteSigned -NoProfile \"$ErrorActionPreference='Stop'; {startTask.CommandLine}\"";
            }
            else
            {
                startTask.CommandLine = $"/bin/bash -c 'set -e; set -o pipefail; {startTask.CommandLine}'";
            }

            return(startTask);
        }