diff --git a/src/Runner.Common/AsyncManualResetEvent.cs b/src/Runner.Common/AsyncManualResetEvent.cs deleted file mode 100644 index 42f5b7844..000000000 --- a/src/Runner.Common/AsyncManualResetEvent.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System.Threading; -using System.Threading.Tasks; - -namespace GitHub.Runner.Common -{ - //Stephen Toub: http://blogs.msdn.com/b/pfxteam/archive/2012/02/11/10266920.aspx - - public class AsyncManualResetEvent - { - private volatile TaskCompletionSource m_tcs = new TaskCompletionSource(); - - public Task WaitAsync() { return m_tcs.Task; } - - public void Set() - { - var tcs = m_tcs; - Task.Factory.StartNew(s => ((TaskCompletionSource)s).TrySetResult(true), - tcs, CancellationToken.None, TaskCreationOptions.PreferFairness, TaskScheduler.Default); - tcs.Task.Wait(); - } - - public void Reset() - { - while (true) - { - var tcs = m_tcs; - if (!tcs.Task.IsCompleted || - Interlocked.CompareExchange(ref m_tcs, new TaskCompletionSource(), tcs) == tcs) - return; - } - } - } -} diff --git a/src/Runner.Common/ConfigurationStore.cs b/src/Runner.Common/ConfigurationStore.cs index ccf9298fa..ab83132a5 100644 --- a/src/Runner.Common/ConfigurationStore.cs +++ b/src/Runner.Common/ConfigurationStore.cs @@ -71,15 +71,6 @@ namespace GitHub.Runner.Common } } - [DataContract] - public sealed class RunnerRuntimeOptions - { -#if OS_WINDOWS - [DataMember(EmitDefaultValue = false)] - public bool GitUseSecureChannel { get; set; } -#endif - } - [ServiceLocator(Default = typeof(ConfigurationStore))] public interface IConfigurationStore : IRunnerService { @@ -92,9 +83,6 @@ namespace GitHub.Runner.Common void SaveSettings(RunnerSettings settings); void DeleteCredential(); void DeleteSettings(); - RunnerRuntimeOptions GetRunnerRuntimeOptions(); - void SaveRunnerRuntimeOptions(RunnerRuntimeOptions options); - void DeleteRunnerRuntimeOptions(); } public sealed class ConfigurationStore : RunnerService, IConfigurationStore @@ -103,11 +91,9 @@ namespace GitHub.Runner.Common private string _configFilePath; private string _credFilePath; private string _serviceConfigFilePath; - private string _runtimeOptionsFilePath; private CredentialData _creds; private RunnerSettings _settings; - private RunnerRuntimeOptions _runtimeOptions; public override void Initialize(IHostContext hostContext) { @@ -130,16 +116,12 @@ namespace GitHub.Runner.Common _serviceConfigFilePath = hostContext.GetConfigFile(WellKnownConfigFile.Service); Trace.Info("ServiceConfigFilePath: {0}", _serviceConfigFilePath); - - _runtimeOptionsFilePath = hostContext.GetConfigFile(WellKnownConfigFile.Options); - Trace.Info("RuntimeOptionsFilePath: {0}", _runtimeOptionsFilePath); } public string RootFolder { get; private set; } public bool HasCredentials() { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); Trace.Info("HasCredentials()"); bool credsStored = (new FileInfo(_credFilePath)).Exists; Trace.Info("stored {0}", credsStored); @@ -149,14 +131,13 @@ namespace GitHub.Runner.Common public bool IsConfigured() { Trace.Info("IsConfigured()"); - bool configured = HostContext.RunMode == RunMode.Local || (new FileInfo(_configFilePath)).Exists; + bool configured = new FileInfo(_configFilePath).Exists; Trace.Info("IsConfigured: {0}", configured); return configured; } public bool IsServiceConfigured() { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); Trace.Info("IsServiceConfigured()"); bool serviceConfigured = (new FileInfo(_serviceConfigFilePath)).Exists; Trace.Info($"IsServiceConfigured: {serviceConfigured}"); @@ -165,7 +146,6 @@ namespace GitHub.Runner.Common public CredentialData GetCredentials() { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); if (_creds == null) { _creds = IOUtil.LoadObject(_credFilePath); @@ -195,7 +175,6 @@ namespace GitHub.Runner.Common public void SaveCredential(CredentialData credential) { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); Trace.Info("Saving {0} credential @ {1}", credential.Scheme, _credFilePath); if (File.Exists(_credFilePath)) { @@ -211,7 +190,6 @@ namespace GitHub.Runner.Common public void SaveSettings(RunnerSettings settings) { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); Trace.Info("Saving runner settings."); if (File.Exists(_configFilePath)) { @@ -227,44 +205,12 @@ namespace GitHub.Runner.Common public void DeleteCredential() { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); IOUtil.Delete(_credFilePath, default(CancellationToken)); } public void DeleteSettings() { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); IOUtil.Delete(_configFilePath, default(CancellationToken)); } - - public RunnerRuntimeOptions GetRunnerRuntimeOptions() - { - if (_runtimeOptions == null && File.Exists(_runtimeOptionsFilePath)) - { - _runtimeOptions = IOUtil.LoadObject(_runtimeOptionsFilePath); - } - - return _runtimeOptions; - } - - public void SaveRunnerRuntimeOptions(RunnerRuntimeOptions options) - { - Trace.Info("Saving runtime options."); - if (File.Exists(_runtimeOptionsFilePath)) - { - // Delete existing runtime options file first, since the file is hidden and not able to overwrite. - Trace.Info("Delete exist runtime options file."); - IOUtil.DeleteFile(_runtimeOptionsFilePath); - } - - IOUtil.SaveObject(options, _runtimeOptionsFilePath); - Trace.Info("Options Saved."); - File.SetAttributes(_runtimeOptionsFilePath, File.GetAttributes(_runtimeOptionsFilePath) | FileAttributes.Hidden); - } - - public void DeleteRunnerRuntimeOptions() - { - IOUtil.Delete(_runtimeOptionsFilePath, default(CancellationToken)); - } } } diff --git a/src/Runner.Common/Constants.cs b/src/Runner.Common/Constants.cs index f4211ce91..e0781c21f 100644 --- a/src/Runner.Common/Constants.cs +++ b/src/Runner.Common/Constants.cs @@ -2,12 +2,6 @@ namespace GitHub.Runner.Common { - public enum RunMode - { - Normal, // Keep "Normal" first (default value). - Local, - } - public enum WellKnownDirectory { Bin, @@ -94,10 +88,6 @@ namespace GitHub.Runner.Common public static readonly string MonitorSocketAddress = "monitorsocketaddress"; public static readonly string Name = "name"; public static readonly string Pool = "pool"; - public static readonly string SslCACert = "sslcacert"; - public static readonly string SslClientCert = "sslclientcert"; - public static readonly string SslClientCertKey = "sslclientcertkey"; - public static readonly string SslClientCertArchive = "sslclientcertarchive"; public static readonly string StartupType = "startuptype"; public static readonly string Url = "url"; public static readonly string UserName = "username"; @@ -105,14 +95,10 @@ namespace GitHub.Runner.Common public static readonly string Work = "work"; // Secret args. Must be added to the "Secrets" getter as well. - public static readonly string Password = "password"; - public static readonly string SslClientCertPassword = "sslclientcertpassword"; public static readonly string Token = "token"; public static readonly string WindowsLogonPassword = "windowslogonpassword"; public static string[] Secrets => new[] { - Password, - SslClientCertPassword, Token, WindowsLogonPassword, }; @@ -131,13 +117,10 @@ namespace GitHub.Runner.Common public static class Flags { public static readonly string Commit = "commit"; - public static readonly string GitUseSChannel = "gituseschannel"; public static readonly string Help = "help"; public static readonly string Replace = "replace"; - public static readonly string LaunchBrowser = "launchbrowser"; public static readonly string Once = "once"; public static readonly string RunAsService = "runasservice"; - public static readonly string SslSkipCertValidation = "sslskipcertvalidation"; public static readonly string Unattended = "unattended"; public static readonly string Version = "version"; } @@ -164,9 +147,7 @@ namespace GitHub.Runner.Common public static class Configuration { - public static readonly string AAD = "AAD"; public static readonly string OAuthAccessToken = "OAuthAccessToken"; - public static readonly string PAT = "PAT"; public static readonly string OAuth = "OAuth"; } diff --git a/src/Runner.Common/HostContext.cs b/src/Runner.Common/HostContext.cs index f49932adc..f20a9c4e4 100644 --- a/src/Runner.Common/HostContext.cs +++ b/src/Runner.Common/HostContext.cs @@ -20,7 +20,6 @@ namespace GitHub.Runner.Common { public interface IHostContext : IDisposable { - RunMode RunMode { get; set; } StartupType StartupType { get; set; } CancellationToken RunnerShutdownToken { get; } ShutdownReason RunnerShutdownReason { get; } @@ -58,7 +57,6 @@ namespace GitHub.Runner.Common private readonly ProductInfoHeaderValue _userAgent = new ProductInfoHeaderValue($"GitHubActionsRunner-{BuildConstants.RunnerPackage.PackageName}", BuildConstants.RunnerPackage.Version); private CancellationTokenSource _runnerShutdownTokenSource = new CancellationTokenSource(); private object _perfLock = new object(); - private RunMode _runMode = RunMode.Normal; private Tracing _trace; private Tracing _vssTrace; private Tracing _httpTrace; @@ -194,20 +192,6 @@ namespace GitHub.Runner.Common } } - public RunMode RunMode - { - get - { - return _runMode; - } - - set - { - _trace.Info($"Set run mode: {value}"); - _runMode = value; - } - } - public string GetDirectory(WellKnownDirectory directory) { string path; diff --git a/src/Runner.Common/JobServer.cs b/src/Runner.Common/JobServer.cs index d7576199e..860555419 100644 --- a/src/Runner.Common/JobServer.cs +++ b/src/Runner.Common/JobServer.cs @@ -32,11 +32,6 @@ namespace GitHub.Runner.Common public async Task ConnectAsync(VssConnection jobConnection) { - if (HostContext.RunMode == RunMode.Local) - { - return; - } - _connection = jobConnection; int attemptCount = 5; while (!_connection.HasAuthenticated && attemptCount-- > 0) @@ -73,88 +68,48 @@ namespace GitHub.Runner.Common public Task AppendLogContentAsync(Guid scopeIdentifier, string hubName, Guid planId, int logId, Stream uploadStream, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(); return _taskClient.AppendLogContentAsync(scopeIdentifier, hubName, planId, logId, uploadStream, cancellationToken: cancellationToken); } public Task AppendTimelineRecordFeedAsync(Guid scopeIdentifier, string hubName, Guid planId, Guid timelineId, Guid timelineRecordId, Guid stepId, IList lines, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.CompletedTask; - } - CheckConnection(); return _taskClient.AppendTimelineRecordFeedAsync(scopeIdentifier, hubName, planId, timelineId, timelineRecordId, stepId, lines, cancellationToken: cancellationToken); } public Task CreateAttachmentAsync(Guid scopeIdentifier, string hubName, Guid planId, Guid timelineId, Guid timelineRecordId, string type, string name, Stream uploadStream, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(); return _taskClient.CreateAttachmentAsync(scopeIdentifier, hubName, planId, timelineId, timelineRecordId, type, name, uploadStream, cancellationToken: cancellationToken); } public Task CreateLogAsync(Guid scopeIdentifier, string hubName, Guid planId, TaskLog log, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(); return _taskClient.CreateLogAsync(scopeIdentifier, hubName, planId, log, cancellationToken: cancellationToken); } public Task CreateTimelineAsync(Guid scopeIdentifier, string hubName, Guid planId, Guid timelineId, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(); return _taskClient.CreateTimelineAsync(scopeIdentifier, hubName, planId, new Timeline(timelineId), cancellationToken: cancellationToken); } public Task> UpdateTimelineRecordsAsync(Guid scopeIdentifier, string hubName, Guid planId, Guid timelineId, IEnumerable records, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult>(null); - } - CheckConnection(); return _taskClient.UpdateTimelineRecordsAsync(scopeIdentifier, hubName, planId, timelineId, records, cancellationToken: cancellationToken); } public Task RaisePlanEventAsync(Guid scopeIdentifier, string hubName, Guid planId, T eventData, CancellationToken cancellationToken) where T : JobEvent { - if (HostContext.RunMode == RunMode.Local) - { - return Task.CompletedTask; - } - CheckConnection(); return _taskClient.RaisePlanEventAsync(scopeIdentifier, hubName, planId, eventData, cancellationToken: cancellationToken); } public Task GetTimelineAsync(Guid scopeIdentifier, string hubName, Guid planId, Guid timelineId, CancellationToken cancellationToken) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(); return _taskClient.GetTimelineAsync(scopeIdentifier, hubName, planId, timelineId, includeRecords: true, cancellationToken: cancellationToken); } diff --git a/src/Runner.Common/JobServerQueue.cs b/src/Runner.Common/JobServerQueue.cs index 5ffd7eac2..787daeffd 100644 --- a/src/Runner.Common/JobServerQueue.cs +++ b/src/Runner.Common/JobServerQueue.cs @@ -63,7 +63,6 @@ namespace GitHub.Runner.Common private Task[] _allDequeueTasks; private readonly TaskCompletionSource _jobCompletionSource = new TaskCompletionSource(); private bool _queueInProcess = false; - private ITerminal _term; public event EventHandler JobServerQueueThrottling; @@ -85,11 +84,6 @@ namespace GitHub.Runner.Common public void Start(Pipelines.AgentJobRequestMessage jobRequest) { Trace.Entering(); - if (HostContext.RunMode == RunMode.Local) - { - _term = HostContext.GetService(); - return; - } if (_queueInProcess) { @@ -129,11 +123,6 @@ namespace GitHub.Runner.Common // TimelineUpdate queue error will become critical when timeline records contain output variabls. public async Task ShutdownAsync() { - if (HostContext.RunMode == RunMode.Local) - { - return; - } - if (!_queueInProcess) { Trace.Info("No-op, all queue process tasks have been stopped."); @@ -169,32 +158,11 @@ namespace GitHub.Runner.Common public void QueueWebConsoleLine(Guid stepRecordId, string line) { Trace.Verbose("Enqueue web console line queue: {0}", line); - if (HostContext.RunMode == RunMode.Local) - { - if ((line ?? string.Empty).StartsWith("##[section]")) - { - Console.WriteLine("******************************************************************************"); - Console.WriteLine(line.Substring("##[section]".Length)); - Console.WriteLine("******************************************************************************"); - } - else - { - Console.WriteLine(line); - } - - return; - } - _webConsoleLineQueue.Enqueue(new ConsoleLineInfo(stepRecordId, line)); } public void QueueFileUpload(Guid timelineId, Guid timelineRecordId, string type, string name, string path, bool deleteSource) { - if (HostContext.RunMode == RunMode.Local) - { - return; - } - ArgUtil.NotEmpty(timelineId, nameof(timelineId)); ArgUtil.NotEmpty(timelineRecordId, nameof(timelineRecordId)); @@ -215,11 +183,6 @@ namespace GitHub.Runner.Common public void QueueTimelineRecordUpdate(Guid timelineId, TimelineRecord timelineRecord) { - if (HostContext.RunMode == RunMode.Local) - { - return; - } - ArgUtil.NotEmpty(timelineId, nameof(timelineId)); ArgUtil.NotNull(timelineRecord, nameof(timelineRecord)); ArgUtil.NotEmpty(timelineRecord.Id, nameof(timelineRecord.Id)); diff --git a/src/Runner.Common/RunnerCertificateManager.cs b/src/Runner.Common/RunnerCertificateManager.cs deleted file mode 100644 index 40389a55b..000000000 --- a/src/Runner.Common/RunnerCertificateManager.cs +++ /dev/null @@ -1,231 +0,0 @@ -using System; -using GitHub.Runner.Common.Util; -using System.IO; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using System.Security.Cryptography.X509Certificates; -using System.Net; -using System.Net.Security; -using System.Net.Http; -using GitHub.Services.WebApi; -using GitHub.Runner.Sdk; - -namespace GitHub.Runner.Common -{ - [ServiceLocator(Default = typeof(RunnerCertificateManager))] - public interface IRunnerCertificateManager : IRunnerService - { - bool SkipServerCertificateValidation { get; } - string CACertificateFile { get; } - string ClientCertificateFile { get; } - string ClientCertificatePrivateKeyFile { get; } - string ClientCertificateArchiveFile { get; } - string ClientCertificatePassword { get; } - IVssClientCertificateManager VssClientCertificateManager { get; } - } - - public class RunnerCertificateManager : RunnerService, IRunnerCertificateManager - { - private RunnerClientCertificateManager _runnerClientCertificateManager = new RunnerClientCertificateManager(); - - public bool SkipServerCertificateValidation { private set; get; } - public string CACertificateFile { private set; get; } - public string ClientCertificateFile { private set; get; } - public string ClientCertificatePrivateKeyFile { private set; get; } - public string ClientCertificateArchiveFile { private set; get; } - public string ClientCertificatePassword { private set; get; } - public IVssClientCertificateManager VssClientCertificateManager => _runnerClientCertificateManager; - - public override void Initialize(IHostContext hostContext) - { - base.Initialize(hostContext); - LoadCertificateSettings(); - } - - // This should only be called from config - public void SetupCertificate(bool skipCertValidation, string caCert, string clientCert, string clientCertPrivateKey, string clientCertArchive, string clientCertPassword) - { - Trace.Info("Setup runner certificate setting base on configuration inputs."); - - if (skipCertValidation) - { - Trace.Info("Ignore SSL server certificate validation error"); - SkipServerCertificateValidation = true; - VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback = HttpClientHandler.DangerousAcceptAnyServerCertificateValidator; - } - - if (!string.IsNullOrEmpty(caCert)) - { - ArgUtil.File(caCert, nameof(caCert)); - Trace.Info($"Self-Signed CA '{caCert}'"); - } - - if (!string.IsNullOrEmpty(clientCert)) - { - ArgUtil.File(clientCert, nameof(clientCert)); - ArgUtil.File(clientCertPrivateKey, nameof(clientCertPrivateKey)); - ArgUtil.File(clientCertArchive, nameof(clientCertArchive)); - - Trace.Info($"Client cert '{clientCert}'"); - Trace.Info($"Client cert private key '{clientCertPrivateKey}'"); - Trace.Info($"Client cert archive '{clientCertArchive}'"); - } - - CACertificateFile = caCert; - ClientCertificateFile = clientCert; - ClientCertificatePrivateKeyFile = clientCertPrivateKey; - ClientCertificateArchiveFile = clientCertArchive; - ClientCertificatePassword = clientCertPassword; - - _runnerClientCertificateManager.AddClientCertificate(ClientCertificateArchiveFile, ClientCertificatePassword); - } - - // This should only be called from config - public void SaveCertificateSetting() - { - string certSettingFile = HostContext.GetConfigFile(WellKnownConfigFile.Certificates); - IOUtil.DeleteFile(certSettingFile); - - var setting = new RunnerCertificateSetting(); - if (SkipServerCertificateValidation) - { - Trace.Info($"Store Skip ServerCertificateValidation setting to '{certSettingFile}'"); - setting.SkipServerCertValidation = true; - } - - if (!string.IsNullOrEmpty(CACertificateFile)) - { - Trace.Info($"Store CA cert setting to '{certSettingFile}'"); - setting.CACert = CACertificateFile; - } - - if (!string.IsNullOrEmpty(ClientCertificateFile) && - !string.IsNullOrEmpty(ClientCertificatePrivateKeyFile) && - !string.IsNullOrEmpty(ClientCertificateArchiveFile)) - { - Trace.Info($"Store client cert settings to '{certSettingFile}'"); - - setting.ClientCert = ClientCertificateFile; - setting.ClientCertPrivatekey = ClientCertificatePrivateKeyFile; - setting.ClientCertArchive = ClientCertificateArchiveFile; - - if (!string.IsNullOrEmpty(ClientCertificatePassword)) - { - string lookupKey = Guid.NewGuid().ToString("D").ToUpperInvariant(); - Trace.Info($"Store client cert private key password with lookup key {lookupKey}"); - - var credStore = HostContext.GetService(); - credStore.Write($"GITHUB_ACTIONS_RUNNER_CLIENT_CERT_PASSWORD_{lookupKey}", "GitHub", ClientCertificatePassword); - - setting.ClientCertPasswordLookupKey = lookupKey; - } - } - - if (SkipServerCertificateValidation || - !string.IsNullOrEmpty(CACertificateFile) || - !string.IsNullOrEmpty(ClientCertificateFile)) - { - IOUtil.SaveObject(setting, certSettingFile); - File.SetAttributes(certSettingFile, File.GetAttributes(certSettingFile) | FileAttributes.Hidden); - } - } - - // This should only be called from unconfig - public void DeleteCertificateSetting() - { - string certSettingFile = HostContext.GetConfigFile(WellKnownConfigFile.Certificates); - if (File.Exists(certSettingFile)) - { - Trace.Info($"Load runner certificate setting from '{certSettingFile}'"); - var certSetting = IOUtil.LoadObject(certSettingFile); - - if (certSetting != null && !string.IsNullOrEmpty(certSetting.ClientCertPasswordLookupKey)) - { - Trace.Info("Delete client cert private key password from credential store."); - var credStore = HostContext.GetService(); - credStore.Delete($"GITHUB_ACTIONS_RUNNER_CLIENT_CERT_PASSWORD_{certSetting.ClientCertPasswordLookupKey}"); - } - - Trace.Info($"Delete cert setting file: {certSettingFile}"); - IOUtil.DeleteFile(certSettingFile); - } - } - - public void LoadCertificateSettings() - { - string certSettingFile = HostContext.GetConfigFile(WellKnownConfigFile.Certificates); - if (File.Exists(certSettingFile)) - { - Trace.Info($"Load runner certificate setting from '{certSettingFile}'"); - var certSetting = IOUtil.LoadObject(certSettingFile); - ArgUtil.NotNull(certSetting, nameof(RunnerCertificateSetting)); - - if (certSetting.SkipServerCertValidation) - { - Trace.Info("Ignore SSL server certificate validation error"); - SkipServerCertificateValidation = true; - VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback = HttpClientHandler.DangerousAcceptAnyServerCertificateValidator; - } - - if (!string.IsNullOrEmpty(certSetting.CACert)) - { - // make sure all settings file exist - ArgUtil.File(certSetting.CACert, nameof(certSetting.CACert)); - Trace.Info($"CA '{certSetting.CACert}'"); - CACertificateFile = certSetting.CACert; - } - - if (!string.IsNullOrEmpty(certSetting.ClientCert)) - { - // make sure all settings file exist - ArgUtil.File(certSetting.ClientCert, nameof(certSetting.ClientCert)); - ArgUtil.File(certSetting.ClientCertPrivatekey, nameof(certSetting.ClientCertPrivatekey)); - ArgUtil.File(certSetting.ClientCertArchive, nameof(certSetting.ClientCertArchive)); - - Trace.Info($"Client cert '{certSetting.ClientCert}'"); - Trace.Info($"Client cert private key '{certSetting.ClientCertPrivatekey}'"); - Trace.Info($"Client cert archive '{certSetting.ClientCertArchive}'"); - - ClientCertificateFile = certSetting.ClientCert; - ClientCertificatePrivateKeyFile = certSetting.ClientCertPrivatekey; - ClientCertificateArchiveFile = certSetting.ClientCertArchive; - - if (!string.IsNullOrEmpty(certSetting.ClientCertPasswordLookupKey)) - { - var cerdStore = HostContext.GetService(); - ClientCertificatePassword = cerdStore.Read($"GITHUB_ACTIONS_RUNNER_CLIENT_CERT_PASSWORD_{certSetting.ClientCertPasswordLookupKey}").Password; - HostContext.SecretMasker.AddValue(ClientCertificatePassword); - } - - _runnerClientCertificateManager.AddClientCertificate(ClientCertificateArchiveFile, ClientCertificatePassword); - } - } - else - { - Trace.Info("No certificate setting found."); - } - } - } - - [DataContract] - internal class RunnerCertificateSetting - { - [DataMember] - public bool SkipServerCertValidation { get; set; } - - [DataMember] - public string CACert { get; set; } - - [DataMember] - public string ClientCert { get; set; } - - [DataMember] - public string ClientCertPrivatekey { get; set; } - - [DataMember] - public string ClientCertArchive { get; set; } - - [DataMember] - public string ClientCertPasswordLookupKey { get; set; } - } -} diff --git a/src/Runner.Common/RunnerCredentialStore.cs b/src/Runner.Common/RunnerCredentialStore.cs deleted file mode 100644 index 1a1520abf..000000000 --- a/src/Runner.Common/RunnerCredentialStore.cs +++ /dev/null @@ -1,948 +0,0 @@ -using System; -using System.Collections.Concurrent; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Net; -using System.Runtime.InteropServices; -using System.Text; -using System.Text.RegularExpressions; -using System.Threading; -using GitHub.Runner.Common.Util; -using Newtonsoft.Json; -using System.IO; -using System.Runtime.Serialization; -using System.Security.Cryptography; -using GitHub.Runner.Sdk; - -namespace GitHub.Runner.Common -{ - // The purpose of this class is to store user's credential during runner configuration and retrive the credential back at runtime. -#if OS_WINDOWS - [ServiceLocator(Default = typeof(WindowsRunnerCredentialStore))] -#elif OS_OSX - [ServiceLocator(Default = typeof(MacOSRunnerCredentialStore))] -#else - [ServiceLocator(Default = typeof(LinuxRunnerCredentialStore))] -#endif - public interface IRunnerCredentialStore : IRunnerService - { - NetworkCredential Write(string target, string username, string password); - - // throw exception when target not found from cred store - NetworkCredential Read(string target); - - // throw exception when target not found from cred store - void Delete(string target); - } - -#if OS_WINDOWS - // Windows credential store is per user. - // This is a limitation for user configure the runner run as windows service, when user's current login account is different with the service run as account. - // Ex: I login the box as domain\admin, configure the runner as windows service and run as domian\buildserver - // domain\buildserver won't read the stored credential from domain\admin's windows credential store. - // To workaround this limitation. - // Anytime we try to save a credential: - // 1. store it into current user's windows credential store - // 2. use DP-API do a machine level encrypt and store the encrypted content on disk. - // At the first time we try to read the credential: - // 1. read from current user's windows credential store, delete the DP-API encrypted backup content on disk if the windows credential store read succeed. - // 2. if credential not found in current user's windows credential store, read from the DP-API encrypted backup content on disk, - // write the credential back the current user's windows credential store and delete the backup on disk. - public sealed class WindowsRunnerCredentialStore : RunnerService, IRunnerCredentialStore - { - private string _credStoreFile; - private Dictionary _credStore; - - public override void Initialize(IHostContext hostContext) - { - base.Initialize(hostContext); - - _credStoreFile = hostContext.GetConfigFile(WellKnownConfigFile.CredentialStore); - if (File.Exists(_credStoreFile)) - { - _credStore = IOUtil.LoadObject>(_credStoreFile); - } - else - { - _credStore = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - } - - public NetworkCredential Write(string target, string username, string password) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - ArgUtil.NotNullOrEmpty(username, nameof(username)); - ArgUtil.NotNullOrEmpty(password, nameof(password)); - - // save to .credential_store file first, then Windows credential store - string usernameBase64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(username)); - string passwordBase64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(password)); - - // Base64Username:Base64Password -> DP-API machine level encrypt -> Base64Encoding - string encryptedUsernamePassword = Convert.ToBase64String(ProtectedData.Protect(Encoding.UTF8.GetBytes($"{usernameBase64}:{passwordBase64}"), null, DataProtectionScope.LocalMachine)); - Trace.Info($"Credentials for '{target}' written to credential store file."); - _credStore[target] = encryptedUsernamePassword; - - // save to .credential_store file - SyncCredentialStoreFile(); - - // save to Windows Credential Store - return WriteInternal(target, username, password); - } - - public NetworkCredential Read(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - IntPtr credPtr = IntPtr.Zero; - try - { - if (CredRead(target, CredentialType.Generic, 0, out credPtr)) - { - Credential credStruct = (Credential)Marshal.PtrToStructure(credPtr, typeof(Credential)); - int passwordLength = (int)credStruct.CredentialBlobSize; - string password = passwordLength > 0 ? Marshal.PtrToStringUni(credStruct.CredentialBlob, passwordLength / sizeof(char)) : String.Empty; - string username = Marshal.PtrToStringUni(credStruct.UserName); - Trace.Info($"Credentials for '{target}' read from windows credential store."); - - // delete from .credential_store file since we are able to read it from windows credential store - if (_credStore.Remove(target)) - { - Trace.Info($"Delete credentials for '{target}' from credential store file."); - SyncCredentialStoreFile(); - } - - return new NetworkCredential(username, password); - } - else - { - // Can't read from Windows Credential Store, fail back to .credential_store file - if (_credStore.ContainsKey(target) && !string.IsNullOrEmpty(_credStore[target])) - { - Trace.Info($"Credentials for '{target}' read from credential store file."); - - // Base64Decode -> DP-API machine level decrypt -> Base64Username:Base64Password -> Base64Decode - string decryptedUsernamePassword = Encoding.UTF8.GetString(ProtectedData.Unprotect(Convert.FromBase64String(_credStore[target]), null, DataProtectionScope.LocalMachine)); - - string[] credential = decryptedUsernamePassword.Split(':'); - if (credential.Length == 2 && !string.IsNullOrEmpty(credential[0]) && !string.IsNullOrEmpty(credential[1])) - { - string username = Encoding.UTF8.GetString(Convert.FromBase64String(credential[0])); - string password = Encoding.UTF8.GetString(Convert.FromBase64String(credential[1])); - - // store back to windows credential store for current user - NetworkCredential creds = WriteInternal(target, username, password); - - // delete from .credential_store file since we are able to write the credential to windows credential store for current user. - if (_credStore.Remove(target)) - { - Trace.Info($"Delete credentials for '{target}' from credential store file."); - SyncCredentialStoreFile(); - } - - return creds; - } - else - { - throw new ArgumentOutOfRangeException(nameof(decryptedUsernamePassword)); - } - } - - throw new Win32Exception(Marshal.GetLastWin32Error(), $"CredRead throw an error for '{target}'"); - } - } - finally - { - if (credPtr != IntPtr.Zero) - { - CredFree(credPtr); - } - } - } - - public void Delete(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - - // remove from .credential_store file - if (_credStore.Remove(target)) - { - Trace.Info($"Delete credentials for '{target}' from credential store file."); - SyncCredentialStoreFile(); - } - - // remove from windows credential store - if (!CredDelete(target, CredentialType.Generic, 0)) - { - throw new Win32Exception(Marshal.GetLastWin32Error(), $"Failed to delete credentials for {target}"); - } - else - { - Trace.Info($"Credentials for '{target}' deleted from windows credential store."); - } - } - - private NetworkCredential WriteInternal(string target, string username, string password) - { - // save to Windows Credential Store - Credential credential = new Credential() - { - Type = CredentialType.Generic, - Persist = (UInt32)CredentialPersist.LocalMachine, - TargetName = Marshal.StringToCoTaskMemUni(target), - UserName = Marshal.StringToCoTaskMemUni(username), - CredentialBlob = Marshal.StringToCoTaskMemUni(password), - CredentialBlobSize = (UInt32)Encoding.Unicode.GetByteCount(password), - AttributeCount = 0, - Comment = IntPtr.Zero, - Attributes = IntPtr.Zero, - TargetAlias = IntPtr.Zero - }; - - try - { - if (CredWrite(ref credential, 0)) - { - Trace.Info($"Credentials for '{target}' written to windows credential store."); - return new NetworkCredential(username, password); - } - else - { - int error = Marshal.GetLastWin32Error(); - throw new Win32Exception(error, "Failed to write credentials"); - } - } - finally - { - if (credential.CredentialBlob != IntPtr.Zero) - { - Marshal.FreeCoTaskMem(credential.CredentialBlob); - } - if (credential.TargetName != IntPtr.Zero) - { - Marshal.FreeCoTaskMem(credential.TargetName); - } - if (credential.UserName != IntPtr.Zero) - { - Marshal.FreeCoTaskMem(credential.UserName); - } - } - } - - private void SyncCredentialStoreFile() - { - Trace.Info("Sync in-memory credential store with credential store file."); - - // delete the cred store file first anyway, since it's a readonly file. - IOUtil.DeleteFile(_credStoreFile); - - // delete cred store file when all creds gone - if (_credStore.Count == 0) - { - return; - } - else - { - IOUtil.SaveObject(_credStore, _credStoreFile); - File.SetAttributes(_credStoreFile, File.GetAttributes(_credStoreFile) | FileAttributes.Hidden); - } - } - - [DllImport("Advapi32.dll", EntryPoint = "CredDeleteW", CharSet = CharSet.Unicode, SetLastError = true)] - internal static extern bool CredDelete(string target, CredentialType type, int reservedFlag); - - [DllImport("Advapi32.dll", EntryPoint = "CredReadW", CharSet = CharSet.Unicode, SetLastError = true)] - internal static extern bool CredRead(string target, CredentialType type, int reservedFlag, out IntPtr CredentialPtr); - - [DllImport("Advapi32.dll", EntryPoint = "CredWriteW", CharSet = CharSet.Unicode, SetLastError = true)] - internal static extern bool CredWrite([In] ref Credential userCredential, [In] UInt32 flags); - - [DllImport("Advapi32.dll", EntryPoint = "CredFree", SetLastError = true)] - internal static extern bool CredFree([In] IntPtr cred); - - internal enum CredentialPersist : UInt32 - { - Session = 0x01, - LocalMachine = 0x02 - } - - internal enum CredentialType : uint - { - Generic = 0x01, - DomainPassword = 0x02, - DomainCertificate = 0x03 - } - - [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] - internal struct Credential - { - public UInt32 Flags; - public CredentialType Type; - public IntPtr TargetName; - public IntPtr Comment; - public System.Runtime.InteropServices.ComTypes.FILETIME LastWritten; - public UInt32 CredentialBlobSize; - public IntPtr CredentialBlob; - public UInt32 Persist; - public UInt32 AttributeCount; - public IntPtr Attributes; - public IntPtr TargetAlias; - public IntPtr UserName; - } - } -#elif OS_OSX - public sealed class MacOSRunnerCredentialStore : RunnerService, IRunnerCredentialStore - { - private const string _osxRunnerCredStoreKeyChainName = "_GITHUB_ACTIONS_RUNNER_CREDSTORE_INTERNAL_"; - - // Keychain requires a password, but this is not intended to add security - private const string _osxRunnerCredStoreKeyChainPassword = "C46F23C36AF94B72B1EAEE32C68670A0"; - - private string _securityUtil; - - private string _runnerCredStoreKeyChain; - - public override void Initialize(IHostContext hostContext) - { - base.Initialize(hostContext); - - _securityUtil = WhichUtil.Which("security", true, Trace); - - _runnerCredStoreKeyChain = hostContext.GetConfigFile(WellKnownConfigFile.CredentialStore); - - // Create osx key chain if it doesn't exists. - if (!File.Exists(_runnerCredStoreKeyChain)) - { - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - // make sure the 'security' has access to the key so we won't get prompt at runtime. - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"create-keychain -p {_osxRunnerCredStoreKeyChainPassword} \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info($"Successfully create-keychain for {_runnerCredStoreKeyChain}"); - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security create-keychain' failed with exit code {exitCode}."); - } - } - } - else - { - // Try unlock and lock the keychain, make sure it's still in good stage - UnlockKeyChain(); - LockKeyChain(); - } - } - - public NetworkCredential Write(string target, string username, string password) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - ArgUtil.NotNullOrEmpty(username, nameof(username)); - ArgUtil.NotNullOrEmpty(password, nameof(password)); - - try - { - UnlockKeyChain(); - - // base64encode username + ':' + base64encode password - // OSX keychain requires you provide -s target and -a username to retrieve password - // So, we will trade both username and password as 'secret' store into keychain - string usernameBase64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(username)); - string passwordBase64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(password)); - string secretForKeyChain = $"{usernameBase64}:{passwordBase64}"; - - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - // make sure the 'security' has access to the key so we won't get prompt at runtime. - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"add-generic-password -s {target} -a GITHUBACTIONSRUNNER -w {secretForKeyChain} -T \"{_securityUtil}\" \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info($"Successfully add-generic-password for {target} (GITHUBACTIONSRUNNER)"); - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security add-generic-password' failed with exit code {exitCode}."); - } - } - - return new NetworkCredential(username, password); - } - finally - { - LockKeyChain(); - } - } - - public NetworkCredential Read(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - - try - { - UnlockKeyChain(); - - string username; - string password; - - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"find-generic-password -s {target} -a GITHUBACTIONSRUNNER -w -g \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - string keyChainSecret = securityOut.First(); - string[] secrets = keyChainSecret.Split(':'); - if (secrets.Length == 2 && !string.IsNullOrEmpty(secrets[0]) && !string.IsNullOrEmpty(secrets[1])) - { - Trace.Info($"Successfully find-generic-password for {target} (GITHUBACTIONSRUNNER)"); - username = Encoding.UTF8.GetString(Convert.FromBase64String(secrets[0])); - password = Encoding.UTF8.GetString(Convert.FromBase64String(secrets[1])); - return new NetworkCredential(username, password); - } - else - { - throw new ArgumentOutOfRangeException(nameof(keyChainSecret)); - } - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security find-generic-password' failed with exit code {exitCode}."); - } - } - } - finally - { - LockKeyChain(); - } - } - - public void Delete(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - - try - { - UnlockKeyChain(); - - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"delete-generic-password -s {target} -a GITHUBACTIONSRUNNER \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info($"Successfully delete-generic-password for {target} (GITHUBACTIONSRUNNER)"); - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security delete-generic-password' failed with exit code {exitCode}."); - } - } - } - finally - { - LockKeyChain(); - } - } - - private void UnlockKeyChain() - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(_securityUtil, nameof(_securityUtil)); - ArgUtil.NotNullOrEmpty(_runnerCredStoreKeyChain, nameof(_runnerCredStoreKeyChain)); - - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - // make sure the 'security' has access to the key so we won't get prompt at runtime. - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"unlock-keychain -p {_osxRunnerCredStoreKeyChainPassword} \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info($"Successfully unlock-keychain for {_runnerCredStoreKeyChain}"); - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security unlock-keychain' failed with exit code {exitCode}."); - } - } - } - - private void LockKeyChain() - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(_securityUtil, nameof(_securityUtil)); - ArgUtil.NotNullOrEmpty(_runnerCredStoreKeyChain, nameof(_runnerCredStoreKeyChain)); - - List securityOut = new List(); - List securityError = new List(); - object outputLock = new object(); - using (var p = HostContext.CreateService()) - { - p.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) - { - if (!string.IsNullOrEmpty(stdout.Data)) - { - lock (outputLock) - { - securityOut.Add(stdout.Data); - } - } - }; - - p.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (outputLock) - { - securityError.Add(stderr.Data); - } - } - }; - - // make sure the 'security' has access to the key so we won't get prompt at runtime. - int exitCode = p.ExecuteAsync(workingDirectory: HostContext.GetDirectory(WellKnownDirectory.Root), - fileName: _securityUtil, - arguments: $"lock-keychain \"{_runnerCredStoreKeyChain}\"", - environment: null, - cancellationToken: CancellationToken.None).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info($"Successfully lock-keychain for {_runnerCredStoreKeyChain}"); - } - else - { - if (securityOut.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityOut)); - } - if (securityError.Count > 0) - { - Trace.Error(string.Join(Environment.NewLine, securityError)); - } - - throw new InvalidOperationException($"'security lock-keychain' failed with exit code {exitCode}."); - } - } - } - } -#else - public sealed class LinuxRunnerCredentialStore : RunnerService, IRunnerCredentialStore - { - // 'ghrunner' 128 bits iv - private readonly byte[] iv = new byte[] { 0x67, 0x68, 0x72, 0x75, 0x6e, 0x6e, 0x65, 0x72, 0x67, 0x68, 0x72, 0x75, 0x6e, 0x6e, 0x65, 0x72 }; - - // 256 bits key - private byte[] _symmetricKey; - private string _credStoreFile; - private Dictionary _credStore; - - public override void Initialize(IHostContext hostContext) - { - base.Initialize(hostContext); - - _credStoreFile = hostContext.GetConfigFile(WellKnownConfigFile.CredentialStore); - if (File.Exists(_credStoreFile)) - { - _credStore = IOUtil.LoadObject>(_credStoreFile); - } - else - { - _credStore = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - string machineId; - if (File.Exists("/etc/machine-id")) - { - // try use machine-id as encryption key - // this helps avoid accidental information disclosure, but isn't intended for true security - machineId = File.ReadAllLines("/etc/machine-id").FirstOrDefault(); - Trace.Info($"machine-id length {machineId?.Length ?? 0}."); - - // machine-id doesn't exist or machine-id is not 256 bits - if (string.IsNullOrEmpty(machineId) || machineId.Length != 32) - { - Trace.Warning("Can not get valid machine id from '/etc/machine-id'."); - machineId = "43e7fe5da07740cf914b90f1dac51c2a"; - } - } - else - { - // /etc/machine-id not exist - Trace.Warning("/etc/machine-id doesn't exist."); - machineId = "43e7fe5da07740cf914b90f1dac51c2a"; - } - - List keyBuilder = new List(); - foreach (var c in machineId) - { - keyBuilder.Add(Convert.ToByte(c)); - } - - _symmetricKey = keyBuilder.ToArray(); - } - - public NetworkCredential Write(string target, string username, string password) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - ArgUtil.NotNullOrEmpty(username, nameof(username)); - ArgUtil.NotNullOrEmpty(password, nameof(password)); - - Trace.Info($"Store credential for '{target}' to cred store."); - Credential cred = new Credential(username, Encrypt(password)); - _credStore[target] = cred; - SyncCredentialStoreFile(); - return new NetworkCredential(username, password); - } - - public NetworkCredential Read(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - Trace.Info($"Read credential for '{target}' from cred store."); - if (_credStore.ContainsKey(target)) - { - Credential cred = _credStore[target]; - if (!string.IsNullOrEmpty(cred.UserName) && !string.IsNullOrEmpty(cred.Password)) - { - Trace.Info($"Return credential for '{target}' from cred store."); - return new NetworkCredential(cred.UserName, Decrypt(cred.Password)); - } - } - - throw new KeyNotFoundException(target); - } - - public void Delete(string target) - { - Trace.Entering(); - ArgUtil.NotNullOrEmpty(target, nameof(target)); - - if (_credStore.ContainsKey(target)) - { - Trace.Info($"Delete credential for '{target}' from cred store."); - _credStore.Remove(target); - SyncCredentialStoreFile(); - } - else - { - throw new KeyNotFoundException(target); - } - } - - private void SyncCredentialStoreFile() - { - Trace.Entering(); - Trace.Info("Sync in-memory credential store with credential store file."); - - // delete cred store file when all creds gone - if (_credStore.Count == 0) - { - IOUtil.DeleteFile(_credStoreFile); - return; - } - - if (!File.Exists(_credStoreFile)) - { - CreateCredentialStoreFile(); - } - - IOUtil.SaveObject(_credStore, _credStoreFile); - } - - private string Encrypt(string secret) - { - using (Aes aes = Aes.Create()) - { - aes.Key = _symmetricKey; - aes.IV = iv; - - // Create a decrytor to perform the stream transform. - ICryptoTransform encryptor = aes.CreateEncryptor(); - - // Create the streams used for encryption. - using (MemoryStream msEncrypt = new MemoryStream()) - { - using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write)) - { - using (StreamWriter swEncrypt = new StreamWriter(csEncrypt)) - { - swEncrypt.Write(secret); - } - - return Convert.ToBase64String(msEncrypt.ToArray()); - } - } - } - } - - private string Decrypt(string encryptedText) - { - using (Aes aes = Aes.Create()) - { - aes.Key = _symmetricKey; - aes.IV = iv; - - // Create a decrytor to perform the stream transform. - ICryptoTransform decryptor = aes.CreateDecryptor(); - - // Create the streams used for decryption. - using (MemoryStream msDecrypt = new MemoryStream(Convert.FromBase64String(encryptedText))) - { - using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read)) - { - using (StreamReader srDecrypt = new StreamReader(csDecrypt)) - { - // Read the decrypted bytes from the decrypting stream and place them in a string. - return srDecrypt.ReadToEnd(); - } - } - } - } - } - - private void CreateCredentialStoreFile() - { - File.WriteAllText(_credStoreFile, ""); - File.SetAttributes(_credStoreFile, File.GetAttributes(_credStoreFile) | FileAttributes.Hidden); - - // Try to lock down the .credentials_store file to the owner/group - var chmodPath = WhichUtil.Which("chmod", trace: Trace); - if (!String.IsNullOrEmpty(chmodPath)) - { - var arguments = $"600 {new FileInfo(_credStoreFile).FullName}"; - using (var invoker = HostContext.CreateService()) - { - var exitCode = invoker.ExecuteAsync(HostContext.GetDirectory(WellKnownDirectory.Root), chmodPath, arguments, null, default(CancellationToken)).GetAwaiter().GetResult(); - if (exitCode == 0) - { - Trace.Info("Successfully set permissions for credentials store file {0}", _credStoreFile); - } - else - { - Trace.Warning("Unable to successfully set permissions for credentials store file {0}. Received exit code {1} from {2}", _credStoreFile, exitCode, chmodPath); - } - } - } - else - { - Trace.Warning("Unable to locate chmod to set permissions for credentials store file {0}.", _credStoreFile); - } - } - } - - [DataContract] - internal class Credential - { - public Credential() - { } - - public Credential(string userName, string password) - { - UserName = userName; - Password = password; - } - - [DataMember(IsRequired = true)] - public string UserName { get; set; } - - [DataMember(IsRequired = true)] - public string Password { get; set; } - } -#endif -} diff --git a/src/Runner.Common/RunnerServer.cs b/src/Runner.Common/RunnerServer.cs index 23200d46b..f06635aad 100644 --- a/src/Runner.Common/RunnerServer.cs +++ b/src/Runner.Common/RunnerServer.cs @@ -66,11 +66,6 @@ namespace GitHub.Runner.Common public async Task ConnectAsync(Uri serverUrl, VssCredentials credentials) { - if (HostContext.RunMode == RunMode.Local) - { - return; - } - var createGenericConnection = EstablishVssConnection(serverUrl, credentials, TimeSpan.FromSeconds(100)); var createMessageConnection = EstablishVssConnection(serverUrl, credentials, TimeSpan.FromSeconds(60)); var createRequestConnection = EstablishVssConnection(serverUrl, credentials, TimeSpan.FromSeconds(60)); @@ -303,29 +298,18 @@ namespace GitHub.Runner.Common public Task RenewAgentRequestAsync(int poolId, long requestId, Guid lockToken, CancellationToken cancellationToken = default(CancellationToken)) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(JsonUtility.FromString("{ lockedUntil: \"" + DateTime.Now.Add(TimeSpan.FromMinutes(5)).ToString("u") + "\" }")); - } - CheckConnection(RunnerConnectionType.JobRequest); return _requestTaskAgentClient.RenewAgentRequestAsync(poolId, requestId, lockToken, cancellationToken: cancellationToken); } public Task FinishAgentRequestAsync(int poolId, long requestId, Guid lockToken, DateTime finishTime, TaskResult result, CancellationToken cancellationToken = default(CancellationToken)) { - if (HostContext.RunMode == RunMode.Local) - { - return Task.FromResult(null); - } - CheckConnection(RunnerConnectionType.JobRequest); return _requestTaskAgentClient.FinishAgentRequestAsync(poolId, requestId, lockToken, finishTime, result, cancellationToken: cancellationToken); } public Task GetAgentRequestAsync(int poolId, long requestId, CancellationToken cancellationToken = default(CancellationToken)) { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); CheckConnection(RunnerConnectionType.JobRequest); return _requestTaskAgentClient.GetAgentRequestAsync(poolId, requestId, cancellationToken: cancellationToken); } @@ -335,7 +319,6 @@ namespace GitHub.Runner.Common //----------------------------------------------------------------- public Task> GetPackagesAsync(string packageType, string platform, int top, CancellationToken cancellationToken) { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); CheckConnection(RunnerConnectionType.Generic); return _genericTaskAgentClient.GetPackagesAsync(packageType, platform, top, cancellationToken: cancellationToken); } diff --git a/src/Runner.Listener/CommandSettings.cs b/src/Runner.Listener/CommandSettings.cs index 1d0c999a4..8797d3bdc 100644 --- a/src/Runner.Listener/CommandSettings.cs +++ b/src/Runner.Listener/CommandSettings.cs @@ -28,14 +28,10 @@ namespace GitHub.Runner.Listener private readonly string[] validFlags = { Constants.Runner.CommandLine.Flags.Commit, -#if OS_WINDOWS - Constants.Runner.CommandLine.Flags.GitUseSChannel, -#endif Constants.Runner.CommandLine.Flags.Help, Constants.Runner.CommandLine.Flags.Replace, Constants.Runner.CommandLine.Flags.RunAsService, Constants.Runner.CommandLine.Flags.Once, - Constants.Runner.CommandLine.Flags.SslSkipCertValidation, Constants.Runner.CommandLine.Flags.Unattended, Constants.Runner.CommandLine.Flags.Version }; @@ -45,13 +41,7 @@ namespace GitHub.Runner.Listener Constants.Runner.CommandLine.Args.Auth, Constants.Runner.CommandLine.Args.MonitorSocketAddress, Constants.Runner.CommandLine.Args.Name, - Constants.Runner.CommandLine.Args.Password, Constants.Runner.CommandLine.Args.Pool, - Constants.Runner.CommandLine.Args.SslCACert, - Constants.Runner.CommandLine.Args.SslClientCert, - Constants.Runner.CommandLine.Args.SslClientCertKey, - Constants.Runner.CommandLine.Args.SslClientCertArchive, - Constants.Runner.CommandLine.Args.SslClientCertPassword, Constants.Runner.CommandLine.Args.StartupType, Constants.Runner.CommandLine.Args.Token, Constants.Runner.CommandLine.Args.Url, @@ -73,9 +63,6 @@ namespace GitHub.Runner.Listener public bool Unattended => TestFlag(Constants.Runner.CommandLine.Flags.Unattended); public bool Version => TestFlag(Constants.Runner.CommandLine.Flags.Version); -#if OS_WINDOWS - public bool GitUseSChannel => TestFlag(Constants.Runner.CommandLine.Flags.GitUseSChannel); -#endif public bool RunOnce => TestFlag(Constants.Runner.CommandLine.Flags.Once); // Constructor. @@ -160,13 +147,6 @@ namespace GitHub.Runner.Listener defaultValue: false); } - public bool GetAutoLaunchBrowser() - { - return TestFlagOrPrompt( - name: Constants.Runner.CommandLine.Flags.LaunchBrowser, - description: "Would you like to launch your browser for AAD Device Code Flow? (Y/N)", - defaultValue: true); - } // // Args. // @@ -179,24 +159,6 @@ namespace GitHub.Runner.Listener validator: Validators.AuthSchemeValidator); } - public string GetPassword() - { - return GetArgOrPrompt( - name: Constants.Runner.CommandLine.Args.Password, - description: "What is your GitHub password?", - defaultValue: string.Empty, - validator: Validators.NonEmptyValidator); - } - - public string GetPool() - { - return GetArgOrPrompt( - name: Constants.Runner.CommandLine.Args.Pool, - description: "Enter the name of your runner pool:", - defaultValue: "default", - validator: Validators.NonEmptyValidator); - } - public string GetRunnerName() { return GetArgOrPrompt( @@ -210,7 +172,7 @@ namespace GitHub.Runner.Listener { return GetArgOrPrompt( name: Constants.Runner.CommandLine.Args.Token, - description: "Enter your personal access token:", + description: "What is your pool admin oauth access token?", defaultValue: string.Empty, validator: Validators.NonEmptyValidator); } @@ -219,7 +181,7 @@ namespace GitHub.Runner.Listener { return GetArgOrPrompt( name: Constants.Runner.CommandLine.Args.Token, - description: "Enter runner register token:", + description: "What is your runner register token?", defaultValue: string.Empty, validator: Validators.NonEmptyValidator); } @@ -249,15 +211,6 @@ namespace GitHub.Runner.Listener validator: Validators.ServerUrlValidator); } - public string GetUserName() - { - return GetArgOrPrompt( - name: Constants.Runner.CommandLine.Args.UserName, - description: "What is your GitHub username?", - defaultValue: string.Empty, - validator: Validators.NonEmptyValidator); - } - public string GetWindowsLogonAccount(string defaultValue, string descriptionMsg) { return GetArgOrPrompt( @@ -296,36 +249,6 @@ namespace GitHub.Runner.Listener return GetArg(Constants.Runner.CommandLine.Args.StartupType); } - public bool GetSkipCertificateValidation() - { - return TestFlag(Constants.Runner.CommandLine.Flags.SslSkipCertValidation); - } - - public string GetCACertificate() - { - return GetArg(Constants.Runner.CommandLine.Args.SslCACert); - } - - public string GetClientCertificate() - { - return GetArg(Constants.Runner.CommandLine.Args.SslClientCert); - } - - public string GetClientCertificatePrivateKey() - { - return GetArg(Constants.Runner.CommandLine.Args.SslClientCertKey); - } - - public string GetClientCertificateArchrive() - { - return GetArg(Constants.Runner.CommandLine.Args.SslClientCertArchive); - } - - public string GetClientCertificatePassword() - { - return GetArg(Constants.Runner.CommandLine.Args.SslClientCertPassword); - } - // // Private helpers. // diff --git a/src/Runner.Listener/Configuration/ConfigurationManager.cs b/src/Runner.Listener/Configuration/ConfigurationManager.cs index b24912c05..15440b911 100644 --- a/src/Runner.Listener/Configuration/ConfigurationManager.cs +++ b/src/Runner.Listener/Configuration/ConfigurationManager.cs @@ -79,61 +79,12 @@ namespace GitHub.Runner.Listener.Configuration _term.WriteLine("| |", ConsoleColor.White); _term.WriteLine("--------------------------------------------------------------------------------", ConsoleColor.White); - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); Trace.Info(nameof(ConfigureAsync)); if (IsConfigured()) { throw new InvalidOperationException("Cannot configure the runner because it is already configured. To reconfigure the runner, run 'config.cmd remove' or './config.sh remove' first."); } - // Populate cert setting from commandline args - var runnerCertManager = HostContext.GetService(); - bool saveCertSetting = false; - bool skipCertValidation = command.GetSkipCertificateValidation(); - string caCert = command.GetCACertificate(); - string clientCert = command.GetClientCertificate(); - string clientCertKey = command.GetClientCertificatePrivateKey(); - string clientCertArchive = command.GetClientCertificateArchrive(); - string clientCertPassword = command.GetClientCertificatePassword(); - - // We require all Certificate files are under agent root. - // So we can set ACL correctly when configure as service - if (!string.IsNullOrEmpty(caCert)) - { - caCert = Path.Combine(HostContext.GetDirectory(WellKnownDirectory.Root), caCert); - ArgUtil.File(caCert, nameof(caCert)); - } - - if (!string.IsNullOrEmpty(clientCert) && - !string.IsNullOrEmpty(clientCertKey) && - !string.IsNullOrEmpty(clientCertArchive)) - { - // Ensure all client cert pieces are there. - clientCert = Path.Combine(HostContext.GetDirectory(WellKnownDirectory.Root), clientCert); - clientCertKey = Path.Combine(HostContext.GetDirectory(WellKnownDirectory.Root), clientCertKey); - clientCertArchive = Path.Combine(HostContext.GetDirectory(WellKnownDirectory.Root), clientCertArchive); - - ArgUtil.File(clientCert, nameof(clientCert)); - ArgUtil.File(clientCertKey, nameof(clientCertKey)); - ArgUtil.File(clientCertArchive, nameof(clientCertArchive)); - } - else if (!string.IsNullOrEmpty(clientCert) || - !string.IsNullOrEmpty(clientCertKey) || - !string.IsNullOrEmpty(clientCertArchive)) - { - // Print out which args are missing. - ArgUtil.NotNullOrEmpty(Constants.Runner.CommandLine.Args.SslClientCert, Constants.Runner.CommandLine.Args.SslClientCert); - ArgUtil.NotNullOrEmpty(Constants.Runner.CommandLine.Args.SslClientCertKey, Constants.Runner.CommandLine.Args.SslClientCertKey); - ArgUtil.NotNullOrEmpty(Constants.Runner.CommandLine.Args.SslClientCertArchive, Constants.Runner.CommandLine.Args.SslClientCertArchive); - } - - if (skipCertValidation || !string.IsNullOrEmpty(caCert) || !string.IsNullOrEmpty(clientCert)) - { - Trace.Info("Reset runner cert setting base on commandline args."); - (runnerCertManager as RunnerCertificateManager).SetupCertificate(skipCertValidation, caCert, clientCert, clientCertKey, clientCertArchive, clientCertPassword); - saveCertSetting = true; - } - RunnerSettings runnerSettings = new RunnerSettings(); bool isHostedServer = false; @@ -353,31 +304,10 @@ namespace GitHub.Runner.Listener.Configuration _store.SaveSettings(runnerSettings); - if (saveCertSetting) - { - Trace.Info("Save agent cert setting to disk."); - (runnerCertManager as RunnerCertificateManager).SaveCertificateSetting(); - } - _term.WriteLine(); _term.WriteSuccessMessage("Settings Saved."); _term.WriteLine(); - bool saveRuntimeOptions = false; - var runtimeOptions = new RunnerRuntimeOptions(); -#if OS_WINDOWS - if (command.GitUseSChannel) - { - saveRuntimeOptions = true; - runtimeOptions.GitUseSecureChannel = true; - } -#endif - if (saveRuntimeOptions) - { - Trace.Info("Save agent runtime options to disk."); - _store.SaveRunnerRuntimeOptions(runtimeOptions); - } - #if OS_WINDOWS // config windows service bool runAsService = command.GetRunAsService(); @@ -397,7 +327,6 @@ namespace GitHub.Runner.Listener.Configuration public async Task UnconfigureAsync(CommandSettings command) { - ArgUtil.Equal(RunMode.Normal, HostContext.RunMode, nameof(HostContext.RunMode)); string currentAction = string.Empty; _term.WriteSection("Runner removal"); @@ -491,13 +420,6 @@ namespace GitHub.Runner.Listener.Configuration currentAction = "Removing .runner"; if (isConfigured) { - - // delete agent cert setting - (HostContext.GetService() as RunnerCertificateManager).DeleteCertificateSetting(); - - // delete agent runtime option - _store.DeleteRunnerRuntimeOptions(); - _store.DeleteSettings(); _term.WriteSuccessMessage("Removed .runner"); } @@ -520,7 +442,7 @@ namespace GitHub.Runner.Listener.Configuration Trace.Info(nameof(GetCredentialProvider)); var credentialManager = HostContext.GetService(); - string authType = command.GetAuth(defaultValue: Constants.Configuration.AAD); + string authType = command.GetAuth(defaultValue: Constants.Configuration.OAuthAccessToken); // Create the credential. Trace.Info("Creating credential for auth: {0}", authType); diff --git a/src/Runner.Listener/Configuration/CredentialManager.cs b/src/Runner.Listener/Configuration/CredentialManager.cs index 34e540fe6..9c804b736 100644 --- a/src/Runner.Listener/Configuration/CredentialManager.cs +++ b/src/Runner.Listener/Configuration/CredentialManager.cs @@ -20,8 +20,6 @@ namespace GitHub.Runner.Listener.Configuration { public static readonly Dictionary CredentialTypes = new Dictionary(StringComparer.OrdinalIgnoreCase) { - { Constants.Configuration.AAD, typeof(AadDeviceCodeAccessToken)}, - { Constants.Configuration.PAT, typeof(PersonalAccessToken)}, { Constants.Configuration.OAuth, typeof(OAuthCredential)}, { Constants.Configuration.OAuthAccessToken, typeof(OAuthAccessTokenCredential)}, }; @@ -80,7 +78,7 @@ namespace GitHub.Runner.Listener.Configuration if (string.Equals(TokenSchema, "OAuthAccessToken", StringComparison.OrdinalIgnoreCase)) { - return new VssCredentials(null, new VssOAuthAccessTokenCredential(Token), CredentialPromptType.DoNotPrompt); + return new VssCredentials(new VssOAuthAccessTokenCredential(Token), CredentialPromptType.DoNotPrompt); } else { diff --git a/src/Runner.Listener/Configuration/CredentialProvider.cs b/src/Runner.Listener/Configuration/CredentialProvider.cs index 5223c0803..304c11770 100644 --- a/src/Runner.Listener/Configuration/CredentialProvider.cs +++ b/src/Runner.Listener/Configuration/CredentialProvider.cs @@ -1,13 +1,5 @@ using System; -using System.Diagnostics; -using System.Linq; -using System.Net.Http; -using System.Net.Http.Headers; -using Microsoft.IdentityModel.Clients.ActiveDirectory; -using GitHub.Runner.Common.Util; -using GitHub.Services.Client; using GitHub.Services.Common; -using GitHub.Services.WebApi; using GitHub.Runner.Common; using GitHub.Runner.Sdk; using GitHub.Services.OAuth; @@ -37,125 +29,6 @@ namespace GitHub.Runner.Listener.Configuration public abstract void EnsureCredential(IHostContext context, CommandSettings command, string serverUrl); } - public sealed class AadDeviceCodeAccessToken : CredentialProvider - { - private string _azureDevOpsClientId = "97877f11-0fc6-4aee-b1ff-febb0519dd00"; - - public override Boolean RequireInteractive => true; - - public AadDeviceCodeAccessToken() : base(Constants.Configuration.AAD) { } - - public override VssCredentials GetVssCredentials(IHostContext context) - { - ArgUtil.NotNull(context, nameof(context)); - Tracing trace = context.GetTrace(nameof(AadDeviceCodeAccessToken)); - trace.Info(nameof(GetVssCredentials)); - ArgUtil.NotNull(CredentialData, nameof(CredentialData)); - - CredentialData.Data.TryGetValue(Constants.Runner.CommandLine.Args.Url, out string serverUrl); - ArgUtil.NotNullOrEmpty(serverUrl, nameof(serverUrl)); - - var tenantAuthorityUrl = GetTenantAuthorityUrl(context, serverUrl); - if (tenantAuthorityUrl == null) - { - throw new NotSupportedException($"'{serverUrl}' is not backed by Azure Active Directory."); - } - - LoggerCallbackHandler.LogCallback = ((LogLevel level, string message, bool containsPii) => - { - switch (level) - { - case LogLevel.Information: - trace.Info(message); - break; - case LogLevel.Error: - trace.Error(message); - break; - case LogLevel.Warning: - trace.Warning(message); - break; - default: - trace.Verbose(message); - break; - } - }); - - LoggerCallbackHandler.UseDefaultLogging = false; - AuthenticationContext ctx = new AuthenticationContext(tenantAuthorityUrl.AbsoluteUri); - var queryParameters = $"redirect_uri={Uri.EscapeDataString(new Uri(serverUrl).GetLeftPart(UriPartial.Authority))}"; - DeviceCodeResult codeResult = ctx.AcquireDeviceCodeAsync("https://management.core.windows.net/", _azureDevOpsClientId, queryParameters).GetAwaiter().GetResult(); - - var term = context.GetService(); - term.WriteLine($"Please finish AAD device code flow in browser ({codeResult.VerificationUrl}), user code: {codeResult.UserCode}"); - if (string.Equals(CredentialData.Data[Constants.Runner.CommandLine.Flags.LaunchBrowser], bool.TrueString, StringComparison.OrdinalIgnoreCase)) - { - try - { -#if OS_WINDOWS - Process.Start(new ProcessStartInfo() { FileName = codeResult.VerificationUrl, UseShellExecute = true }); -#elif OS_LINUX - Process.Start(new ProcessStartInfo() { FileName = "xdg-open", Arguments = codeResult.VerificationUrl }); -#else - Process.Start(new ProcessStartInfo() { FileName = "open", Arguments = codeResult.VerificationUrl }); -#endif - } - catch (Exception ex) - { - // not able to open browser, ex: xdg-open/open is not installed. - trace.Error(ex); - term.WriteLine($"Fail to open browser. {codeResult.Message}"); - } - } - - AuthenticationResult authResult = ctx.AcquireTokenByDeviceCodeAsync(codeResult).GetAwaiter().GetResult(); - ArgUtil.NotNull(authResult, nameof(authResult)); - trace.Info($"receive AAD auth result with {authResult.AccessTokenType} token"); - - var aadCred = new VssAadCredential(new VssAadToken(authResult)); - VssCredentials creds = new VssCredentials(null, aadCred, CredentialPromptType.DoNotPrompt); - trace.Info("cred created"); - - return creds; - } - - public override void EnsureCredential(IHostContext context, CommandSettings command, string serverUrl) - { - ArgUtil.NotNull(context, nameof(context)); - Tracing trace = context.GetTrace(nameof(AadDeviceCodeAccessToken)); - trace.Info(nameof(EnsureCredential)); - ArgUtil.NotNull(command, nameof(command)); - CredentialData.Data[Constants.Runner.CommandLine.Args.Url] = serverUrl; - CredentialData.Data[Constants.Runner.CommandLine.Flags.LaunchBrowser] = command.GetAutoLaunchBrowser().ToString(); - } - - private Uri GetTenantAuthorityUrl(IHostContext context, string serverUrl) - { - using (var client = new HttpClient(context.CreateHttpClientHandler())) - { - client.DefaultRequestHeaders.Accept.Clear(); - client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); - client.DefaultRequestHeaders.Add("X-TFS-FedAuthRedirect", "Suppress"); - client.DefaultRequestHeaders.UserAgent.Clear(); - client.DefaultRequestHeaders.UserAgent.AddRange(VssClientHttpRequestSettings.Default.UserAgent); - var requestMessage = new HttpRequestMessage(HttpMethod.Head, $"{serverUrl.Trim('/')}/_apis/connectiondata"); - var response = client.SendAsync(requestMessage).GetAwaiter().GetResult(); - - // Get the tenant from the Login URL, MSA backed accounts will not return `Bearer` www-authenticate header. - var bearerResult = response.Headers.WwwAuthenticate.Where(p => p.Scheme.Equals("Bearer", StringComparison.OrdinalIgnoreCase)).FirstOrDefault(); - if (bearerResult != null && bearerResult.Parameter.StartsWith("authorization_uri=", StringComparison.OrdinalIgnoreCase)) - { - var authorizationUri = bearerResult.Parameter.Substring("authorization_uri=".Length); - if (Uri.TryCreate(authorizationUri, UriKind.Absolute, out Uri aadTenantUrl)) - { - return aadTenantUrl; - } - } - - return null; - } - } - } - public sealed class OAuthAccessTokenCredential : CredentialProvider { public OAuthAccessTokenCredential() : base(Constants.Configuration.OAuthAccessToken) { } @@ -175,7 +48,7 @@ namespace GitHub.Runner.Listener.Configuration ArgUtil.NotNullOrEmpty(token, nameof(token)); trace.Info("token retrieved: {0} chars", token.Length); - VssCredentials creds = new VssCredentials(null, new VssOAuthAccessTokenCredential(token), CredentialPromptType.DoNotPrompt); + VssCredentials creds = new VssCredentials(new VssOAuthAccessTokenCredential(token), CredentialPromptType.DoNotPrompt); trace.Info("cred created"); return creds; @@ -190,42 +63,4 @@ namespace GitHub.Runner.Listener.Configuration CredentialData.Data[Constants.Runner.CommandLine.Args.Token] = command.GetToken(); } } - - public sealed class PersonalAccessToken : CredentialProvider - { - public PersonalAccessToken() : base(Constants.Configuration.PAT) { } - - public override VssCredentials GetVssCredentials(IHostContext context) - { - ArgUtil.NotNull(context, nameof(context)); - Tracing trace = context.GetTrace(nameof(PersonalAccessToken)); - trace.Info(nameof(GetVssCredentials)); - ArgUtil.NotNull(CredentialData, nameof(CredentialData)); - string token; - if (!CredentialData.Data.TryGetValue(Constants.Runner.CommandLine.Args.Token, out token)) - { - token = null; - } - - ArgUtil.NotNullOrEmpty(token, nameof(token)); - - trace.Info("token retrieved: {0} chars", token.Length); - - // PAT uses a basic credential - VssBasicCredential basicCred = new VssBasicCredential("ActionsRunner", token); - VssCredentials creds = new VssCredentials(null, basicCred, CredentialPromptType.DoNotPrompt); - trace.Info("cred created"); - - return creds; - } - - public override void EnsureCredential(IHostContext context, CommandSettings command, string serverUrl) - { - ArgUtil.NotNull(context, nameof(context)); - Tracing trace = context.GetTrace(nameof(PersonalAccessToken)); - trace.Info(nameof(EnsureCredential)); - ArgUtil.NotNull(command, nameof(command)); - CredentialData.Data[Constants.Runner.CommandLine.Args.Token] = command.GetToken(); - } - } } diff --git a/src/Runner.Listener/Configuration/OAuthCredential.cs b/src/Runner.Listener/Configuration/OAuthCredential.cs index fb303836c..72d4899c9 100644 --- a/src/Runner.Listener/Configuration/OAuthCredential.cs +++ b/src/Runner.Listener/Configuration/OAuthCredential.cs @@ -43,7 +43,7 @@ namespace GitHub.Runner.Listener.Configuration // Construct a credentials cache with a single OAuth credential for communication. The windows credential // is explicitly set to null to ensure we never do that negotiation. - return new VssCredentials(null, agentCredential, CredentialPromptType.DoNotPrompt); + return new VssCredentials(agentCredential, CredentialPromptType.DoNotPrompt); } } } diff --git a/src/Runner.Listener/Configuration/Validators.cs b/src/Runner.Listener/Configuration/Validators.cs index aa17717c1..c0cd1ef0e 100644 --- a/src/Runner.Listener/Configuration/Validators.cs +++ b/src/Runner.Listener/Configuration/Validators.cs @@ -38,25 +38,6 @@ namespace GitHub.Runner.Listener.Configuration return CredentialManager.CredentialTypes.ContainsKey(value); } - public static bool FilePathValidator(string value) - { - var directoryInfo = new DirectoryInfo(value); - - if (!directoryInfo.Exists) - { - try - { - Directory.CreateDirectory(value); - } - catch (Exception) - { - return false; - } - } - - return true; - } - public static bool BoolValidator(string value) { return string.Equals(value, "true", StringComparison.OrdinalIgnoreCase) || diff --git a/src/Runner.Listener/JobDispatcher.cs b/src/Runner.Listener/JobDispatcher.cs index 4fa3af7fd..867fffb3b 100644 --- a/src/Runner.Listener/JobDispatcher.cs +++ b/src/Runner.Listener/JobDispatcher.cs @@ -22,7 +22,6 @@ namespace GitHub.Runner.Listener void Run(Pipelines.AgentJobRequestMessage message, bool runOnce = false); bool Cancel(JobCancelMessage message); Task WaitAsync(CancellationToken token); - TaskResult GetLocalRunJobResult(AgentJobRequestMessage message); Task ShutdownAsync(); } @@ -165,11 +164,6 @@ namespace GitHub.Runner.Listener } } - public TaskResult GetLocalRunJobResult(AgentJobRequestMessage message) - { - return _localRunJobResult.Value[message.RequestId]; - } - public async Task ShutdownAsync() { Trace.Info($"Shutting down JobDispatcher. Make sure all WorkerDispatcher has finished."); @@ -373,37 +367,29 @@ namespace GitHub.Runner.Listener ArgUtil.NotNullOrEmpty(pipeHandleOut, nameof(pipeHandleOut)); ArgUtil.NotNullOrEmpty(pipeHandleIn, nameof(pipeHandleIn)); - if (HostContext.RunMode == RunMode.Normal) + // Save STDOUT from worker, worker will use STDOUT report unhandle exception. + processInvoker.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) { - // Save STDOUT from worker, worker will use STDOUT report unhandle exception. - processInvoker.OutputDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stdout) + if (!string.IsNullOrEmpty(stdout.Data)) { - if (!string.IsNullOrEmpty(stdout.Data)) + lock (_outputLock) { - lock (_outputLock) - { - workerOutput.Add(stdout.Data); - } + workerOutput.Add(stdout.Data); } - }; + } + }; - // Save STDERR from worker, worker will use STDERR on crash. - processInvoker.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) - { - if (!string.IsNullOrEmpty(stderr.Data)) - { - lock (_outputLock) - { - workerOutput.Add(stderr.Data); - } - } - }; - } - else if (HostContext.RunMode == RunMode.Local) + // Save STDERR from worker, worker will use STDERR on crash. + processInvoker.ErrorDataReceived += delegate (object sender, ProcessDataReceivedEventArgs stderr) { - processInvoker.OutputDataReceived += (object sender, ProcessDataReceivedEventArgs e) => Console.WriteLine(e.Data); - processInvoker.ErrorDataReceived += (object sender, ProcessDataReceivedEventArgs e) => Console.WriteLine(e.Data); - } + if (!string.IsNullOrEmpty(stderr.Data)) + { + lock (_outputLock) + { + workerOutput.Add(stderr.Data); + } + } + }; // Start the child process. HostContext.WritePerfCounter("StartingWorkerProcess"); @@ -730,11 +716,6 @@ namespace GitHub.Runner.Listener private async Task CompleteJobRequestAsync(int poolId, Pipelines.AgentJobRequestMessage message, Guid lockToken, TaskResult result, string detailInfo = null) { Trace.Entering(); - if (HostContext.RunMode == RunMode.Local) - { - _localRunJobResult.Value[message.RequestId] = result; - return; - } if (PlanUtil.GetFeatures(message.Plan).HasFlag(PlanFeatures.JobCompletedPlanEvent)) { diff --git a/src/Runner.Listener/Runner.Listener.csproj b/src/Runner.Listener/Runner.Listener.csproj index 4d73e2a24..3b21c2ffa 100644 --- a/src/Runner.Listener/Runner.Listener.csproj +++ b/src/Runner.Listener/Runner.Listener.csproj @@ -24,7 +24,6 @@ - diff --git a/src/Runner.Listener/Runner.cs b/src/Runner.Listener/Runner.cs index d9cc2c783..690955668 100644 --- a/src/Runner.Listener/Runner.cs +++ b/src/Runner.Listener/Runner.cs @@ -37,8 +37,7 @@ namespace GitHub.Runner.Listener { try { - var runnerCertManager = HostContext.GetService(); - VssUtil.InitializeVssClientSettings(HostContext.UserAgent, HostContext.WebProxy, runnerCertManager.VssClientCertificateManager); + VssUtil.InitializeVssClientSettings(HostContext.UserAgent, HostContext.WebProxy); _inConfigStage = true; _completedCommand.Reset(); diff --git a/src/Runner.Plugins/Repository/v1.0/GitSourceProvider.cs b/src/Runner.Plugins/Repository/v1.0/GitSourceProvider.cs index 57f30a629..39fc9dc84 100644 --- a/src/Runner.Plugins/Repository/v1.0/GitSourceProvider.cs +++ b/src/Runner.Plugins/Repository/v1.0/GitSourceProvider.cs @@ -79,11 +79,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 { // Validate args. ArgUtil.NotNull(executionContext, nameof(executionContext)); - bool useSelfSignedCACert = false; - bool useClientCert = false; - string clientCertPrivateKeyAskPassFile = null; - bool acceptUntrustedCerts = false; - executionContext.Output($"Syncing repository: {repoFullName}"); Uri repositoryUrl = new Uri($"https://github.com/{repoFullName}"); if (!repositoryUrl.IsAbsoluteUri) @@ -112,9 +107,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 } } - var runnerCert = executionContext.GetCertConfiguration(); - acceptUntrustedCerts = runnerCert?.SkipServerCertificateValidation ?? false; - executionContext.Debug($"repository url={repositoryUrl}"); executionContext.Debug($"targetPath={targetPath}"); executionContext.Debug($"sourceBranch={sourceBranch}"); @@ -124,12 +116,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 executionContext.Debug($"checkoutNestedSubmodules={checkoutNestedSubmodules}"); executionContext.Debug($"fetchDepth={fetchDepth}"); executionContext.Debug($"gitLfsSupport={gitLfsSupport}"); - executionContext.Debug($"acceptUntrustedCerts={acceptUntrustedCerts}"); - -#if OS_WINDOWS - bool schannelSslBackend = StringUtil.ConvertToBoolean(executionContext.GetRunnerContext("gituseschannel")); - executionContext.Debug($"schannelSslBackend={schannelSslBackend}"); -#endif // Initialize git command manager with additional environment variables. Dictionary gitEnv = new Dictionary(StringComparer.OrdinalIgnoreCase); @@ -164,54 +150,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 // prepare askpass for client cert private key, if the repository's endpoint url match the runner config url var systemConnection = executionContext.Endpoints.Single(x => string.Equals(x.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase)); - if (runnerCert != null && Uri.Compare(repositoryUrl, systemConnection.Url, UriComponents.SchemeAndServer, UriFormat.Unescaped, StringComparison.OrdinalIgnoreCase) == 0) - { - if (!string.IsNullOrEmpty(runnerCert.CACertificateFile)) - { - useSelfSignedCACert = true; - } - - if (!string.IsNullOrEmpty(runnerCert.ClientCertificateFile) && - !string.IsNullOrEmpty(runnerCert.ClientCertificatePrivateKeyFile)) - { - useClientCert = true; - - // prepare askpass for client cert password - if (!string.IsNullOrEmpty(runnerCert.ClientCertificatePassword)) - { - clientCertPrivateKeyAskPassFile = Path.Combine(executionContext.GetRunnerContext("temp"), $"{Guid.NewGuid()}.sh"); - List askPass = new List(); - askPass.Add("#!/bin/sh"); - askPass.Add($"echo \"{runnerCert.ClientCertificatePassword}\""); - File.WriteAllLines(clientCertPrivateKeyAskPassFile, askPass); - -#if !OS_WINDOWS - string toolPath = WhichUtil.Which("chmod", true); - string argLine = $"775 {clientCertPrivateKeyAskPassFile}"; - executionContext.Command($"chmod {argLine}"); - - var processInvoker = new ProcessInvoker(executionContext); - processInvoker.OutputDataReceived += (object sender, ProcessDataReceivedEventArgs args) => - { - if (!string.IsNullOrEmpty(args.Data)) - { - executionContext.Output(args.Data); - } - }; - processInvoker.ErrorDataReceived += (object sender, ProcessDataReceivedEventArgs args) => - { - if (!string.IsNullOrEmpty(args.Data)) - { - executionContext.Output(args.Data); - } - }; - - string workingDirectory = executionContext.GetRunnerContext("workspace"); - await processInvoker.ExecuteAsync(workingDirectory, toolPath, argLine, null, true, CancellationToken.None); -#endif - } - } - } // Check the current contents of the root folder to see if there is already a repo // If there is a repo, see if it matches the one we are expecting to be there based on the remote fetch url @@ -361,46 +299,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 additionalFetchArgs.Add($"-c http.extraheader=\"AUTHORIZATION: {GenerateBasicAuthHeader(executionContext, accessToken)}\""); } - // Prepare ignore ssl cert error config for fetch. - if (acceptUntrustedCerts) - { - additionalFetchArgs.Add($"-c http.sslVerify=false"); - additionalLfsFetchArgs.Add($"-c http.sslVerify=false"); - } - - // Prepare self-signed CA cert config for fetch from server. - if (useSelfSignedCACert) - { - executionContext.Debug($"Use self-signed certificate '{runnerCert.CACertificateFile}' for git fetch."); - additionalFetchArgs.Add($"-c http.sslcainfo=\"{runnerCert.CACertificateFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcainfo=\"{runnerCert.CACertificateFile}\""); - } - - // Prepare client cert config for fetch from server. - if (useClientCert) - { - executionContext.Debug($"Use client certificate '{runnerCert.ClientCertificateFile}' for git fetch."); - - if (!string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - additionalFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - } - else - { - additionalFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - } - } - -#if OS_WINDOWS - if (schannelSslBackend) - { - executionContext.Debug("Use SChannel SslBackend for git fetch."); - additionalFetchArgs.Add("-c http.sslbackend=\"schannel\""); - additionalLfsFetchArgs.Add("-c http.sslbackend=\"schannel\""); - } -#endif // Prepare gitlfs url for fetch and checkout if (gitLfsSupport) { @@ -502,55 +400,12 @@ namespace GitHub.Runner.Plugins.Repository.v1_0 additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.extraheader=\"AUTHORIZATION: {GenerateBasicAuthHeader(executionContext, accessToken)}\""); } - // Prepare ignore ssl cert error config for fetch. - if (acceptUntrustedCerts) - { - additionalSubmoduleUpdateArgs.Add($"-c http.sslVerify=false"); - } - - // Prepare self-signed CA cert config for submodule update. - if (useSelfSignedCACert) - { - executionContext.Debug($"Use self-signed CA certificate '{runnerCert.CACertificateFile}' for git submodule update."); - string authorityUrl = repositoryUrl.AbsoluteUri.Replace(repositoryUrl.PathAndQuery, string.Empty); - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcainfo=\"{runnerCert.CACertificateFile}\""); - } - - // Prepare client cert config for submodule update. - if (useClientCert) - { - executionContext.Debug($"Use client certificate '{runnerCert.ClientCertificateFile}' for git submodule update."); - string authorityUrl = repositoryUrl.AbsoluteUri.Replace(repositoryUrl.PathAndQuery, string.Empty); - - if (!string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.{authorityUrl}.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.{authorityUrl}.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - } - else - { - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.{authorityUrl}.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - } - } -#if OS_WINDOWS - if (schannelSslBackend) - { - executionContext.Debug("Use SChannel SslBackend for git submodule update."); - additionalSubmoduleUpdateArgs.Add("-c http.sslbackend=\"schannel\""); - } -#endif - int exitCode_submoduleUpdate = await gitCommandManager.GitSubmoduleUpdate(executionContext, targetPath, fetchDepth, string.Join(" ", additionalSubmoduleUpdateArgs), checkoutNestedSubmodules, cancellationToken); if (exitCode_submoduleUpdate != 0) { throw new InvalidOperationException($"Git submodule update failed with exit code: {exitCode_submoduleUpdate}"); } } - - if (useClientCert && !string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - executionContext.Debug("Remove git.sslkey askpass file."); - IOUtil.DeleteFile(clientCertPrivateKeyAskPassFile); - } } private async Task IsRepositoryOriginUrlMatch(RunnerActionPluginExecutionContext context, GitCliManager gitCommandManager, string repositoryPath, Uri expectedRepositoryOriginUrl) diff --git a/src/Runner.Plugins/Repository/v1.1/GitSourceProvider.cs b/src/Runner.Plugins/Repository/v1.1/GitSourceProvider.cs index 4858b0679..f7f4bfaaf 100644 --- a/src/Runner.Plugins/Repository/v1.1/GitSourceProvider.cs +++ b/src/Runner.Plugins/Repository/v1.1/GitSourceProvider.cs @@ -65,11 +65,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 // Validate args. ArgUtil.NotNull(executionContext, nameof(executionContext)); Dictionary configModifications = new Dictionary(); - bool useSelfSignedCACert = false; - bool useClientCert = false; - string clientCertPrivateKeyAskPassFile = null; - bool acceptUntrustedCerts = false; - executionContext.Output($"Syncing repository: {repoFullName}"); Uri repositoryUrl = new Uri($"https://github.com/{repoFullName}"); if (!repositoryUrl.IsAbsoluteUri) @@ -98,9 +93,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 } } - var runnerCert = executionContext.GetCertConfiguration(); - acceptUntrustedCerts = runnerCert?.SkipServerCertificateValidation ?? false; - executionContext.Debug($"repository url={repositoryUrl}"); executionContext.Debug($"targetPath={targetPath}"); executionContext.Debug($"sourceBranch={sourceBranch}"); @@ -110,12 +102,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 executionContext.Debug($"checkoutNestedSubmodules={checkoutNestedSubmodules}"); executionContext.Debug($"fetchDepth={fetchDepth}"); executionContext.Debug($"gitLfsSupport={gitLfsSupport}"); - executionContext.Debug($"acceptUntrustedCerts={acceptUntrustedCerts}"); - -#if OS_WINDOWS - bool schannelSslBackend = StringUtil.ConvertToBoolean(executionContext.GetRunnerContext("gituseschannel")); - executionContext.Debug($"schannelSslBackend={schannelSslBackend}"); -#endif // Initialize git command manager with additional environment variables. Dictionary gitEnv = new Dictionary(StringComparer.OrdinalIgnoreCase); @@ -153,54 +139,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 // prepare askpass for client cert private key, if the repository's endpoint url match the runner config url var systemConnection = executionContext.Endpoints.Single(x => string.Equals(x.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase)); - if (runnerCert != null && Uri.Compare(repositoryUrl, systemConnection.Url, UriComponents.SchemeAndServer, UriFormat.Unescaped, StringComparison.OrdinalIgnoreCase) == 0) - { - if (!string.IsNullOrEmpty(runnerCert.CACertificateFile)) - { - useSelfSignedCACert = true; - } - - if (!string.IsNullOrEmpty(runnerCert.ClientCertificateFile) && - !string.IsNullOrEmpty(runnerCert.ClientCertificatePrivateKeyFile)) - { - useClientCert = true; - - // prepare askpass for client cert password - if (!string.IsNullOrEmpty(runnerCert.ClientCertificatePassword)) - { - clientCertPrivateKeyAskPassFile = Path.Combine(executionContext.GetRunnerContext("temp"), $"{Guid.NewGuid()}.sh"); - List askPass = new List(); - askPass.Add("#!/bin/sh"); - askPass.Add($"echo \"{runnerCert.ClientCertificatePassword}\""); - File.WriteAllLines(clientCertPrivateKeyAskPassFile, askPass); - -#if !OS_WINDOWS - string toolPath = WhichUtil.Which("chmod", true); - string argLine = $"775 {clientCertPrivateKeyAskPassFile}"; - executionContext.Command($"chmod {argLine}"); - - var processInvoker = new ProcessInvoker(executionContext); - processInvoker.OutputDataReceived += (object sender, ProcessDataReceivedEventArgs args) => - { - if (!string.IsNullOrEmpty(args.Data)) - { - executionContext.Output(args.Data); - } - }; - processInvoker.ErrorDataReceived += (object sender, ProcessDataReceivedEventArgs args) => - { - if (!string.IsNullOrEmpty(args.Data)) - { - executionContext.Output(args.Data); - } - }; - - string workingDirectory = executionContext.GetRunnerContext("workspace"); - await processInvoker.ExecuteAsync(workingDirectory, toolPath, argLine, null, true, CancellationToken.None); -#endif - } - } - } // Check the current contents of the root folder to see if there is already a repo // If there is a repo, see if it matches the one we are expecting to be there based on the remote fetch url @@ -355,46 +293,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 throw new InvalidOperationException($"Git config failed with exit code: {exitCode_config}"); } - // Prepare ignore ssl cert error config for fetch. - if (acceptUntrustedCerts) - { - additionalFetchArgs.Add($"-c http.sslVerify=false"); - additionalLfsFetchArgs.Add($"-c http.sslVerify=false"); - } - - // Prepare self-signed CA cert config for fetch from server. - if (useSelfSignedCACert) - { - executionContext.Debug($"Use self-signed certificate '{runnerCert.CACertificateFile}' for git fetch."); - additionalFetchArgs.Add($"-c http.sslcainfo=\"{runnerCert.CACertificateFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcainfo=\"{runnerCert.CACertificateFile}\""); - } - - // Prepare client cert config for fetch from server. - if (useClientCert) - { - executionContext.Debug($"Use client certificate '{runnerCert.ClientCertificateFile}' for git fetch."); - - if (!string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - additionalFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - } - else - { - additionalFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - additionalLfsFetchArgs.Add($"-c http.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - } - } - -#if OS_WINDOWS - if (schannelSslBackend) - { - executionContext.Debug("Use SChannel SslBackend for git fetch."); - additionalFetchArgs.Add("-c http.sslbackend=\"schannel\""); - additionalLfsFetchArgs.Add("-c http.sslbackend=\"schannel\""); - } -#endif // Prepare gitlfs url for fetch and checkout if (gitLfsSupport) { @@ -484,43 +382,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 List additionalSubmoduleUpdateArgs = new List(); - // Prepare ignore ssl cert error config for fetch. - if (acceptUntrustedCerts) - { - additionalSubmoduleUpdateArgs.Add($"-c http.sslVerify=false"); - } - - // Prepare self-signed CA cert config for submodule update. - if (useSelfSignedCACert) - { - executionContext.Debug($"Use self-signed CA certificate '{runnerCert.CACertificateFile}' for git submodule update."); - string authorityUrl = repositoryUrl.AbsoluteUri.Replace(repositoryUrl.PathAndQuery, string.Empty); - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcainfo=\"{runnerCert.CACertificateFile}\""); - } - - // Prepare client cert config for submodule update. - if (useClientCert) - { - executionContext.Debug($"Use client certificate '{runnerCert.ClientCertificateFile}' for git submodule update."); - string authorityUrl = repositoryUrl.AbsoluteUri.Replace(repositoryUrl.PathAndQuery, string.Empty); - - if (!string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.{authorityUrl}.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\" -c http.{authorityUrl}.sslCertPasswordProtected=true -c core.askpass=\"{clientCertPrivateKeyAskPassFile}\""); - } - else - { - additionalSubmoduleUpdateArgs.Add($"-c http.{authorityUrl}.sslcert=\"{runnerCert.ClientCertificateFile}\" -c http.{authorityUrl}.sslkey=\"{runnerCert.ClientCertificatePrivateKeyFile}\""); - } - } -#if OS_WINDOWS - if (schannelSslBackend) - { - executionContext.Debug("Use SChannel SslBackend for git submodule update."); - additionalSubmoduleUpdateArgs.Add("-c http.sslbackend=\"schannel\""); - } -#endif - int exitCode_submoduleUpdate = await gitCommandManager.GitSubmoduleUpdate(executionContext, targetPath, fetchDepth, string.Join(" ", additionalSubmoduleUpdateArgs), checkoutNestedSubmodules, cancellationToken); if (exitCode_submoduleUpdate != 0) { @@ -528,12 +389,6 @@ namespace GitHub.Runner.Plugins.Repository.v1_1 } } - if (useClientCert && !string.IsNullOrEmpty(clientCertPrivateKeyAskPassFile)) - { - executionContext.Debug("Remove git.sslkey askpass file."); - IOUtil.DeleteFile(clientCertPrivateKeyAskPassFile); - } - // Set intra-task variable for post job cleanup executionContext.SetIntraActionState("repositoryPath", targetPath); executionContext.SetIntraActionState("modifiedgitconfig", JsonUtility.ToString(configModifications.Keys)); diff --git a/src/Runner.Sdk/ActionPlugin.cs b/src/Runner.Sdk/ActionPlugin.cs index d29f644ac..2a9d87a0a 100644 --- a/src/Runner.Sdk/ActionPlugin.cs +++ b/src/Runner.Sdk/ActionPlugin.cs @@ -83,21 +83,6 @@ namespace GitHub.Runner.Sdk } VssClientHttpRequestSettings.Default.UserAgent = headerValues; - - var certSetting = GetCertConfiguration(); - if (certSetting != null) - { - if (!string.IsNullOrEmpty(certSetting.ClientCertificateArchiveFile)) - { - VssClientHttpRequestSettings.Default.ClientCertificateManager = new RunnerClientCertificateManager(certSetting.ClientCertificateArchiveFile, certSetting.ClientCertificatePassword); - } - - if (certSetting.SkipServerCertificateValidation) - { - VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback = HttpClientHandler.DangerousAcceptAnyServerCertificateValidator; - } - } - VssHttpMessageHandler.DefaultWebProxy = this.WebProxy; ServiceEndpoint systemConnection = this.Endpoints.FirstOrDefault(e => string.Equals(e.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase)); ArgUtil.NotNull(systemConnection, nameof(systemConnection)); @@ -227,40 +212,6 @@ namespace GitHub.Runner.Sdk } } - public RunnerCertificateSettings GetCertConfiguration() - { - bool skipCertValidation = StringUtil.ConvertToBoolean(GetRunnerContext("SkipCertValidation")); - string caFile = GetRunnerContext("CAInfo"); - string clientCertFile = GetRunnerContext("ClientCert"); - - if (!string.IsNullOrEmpty(caFile) || !string.IsNullOrEmpty(clientCertFile) || skipCertValidation) - { - var certConfig = new RunnerCertificateSettings(); - certConfig.SkipServerCertificateValidation = skipCertValidation; - certConfig.CACertificateFile = caFile; - - if (!string.IsNullOrEmpty(clientCertFile)) - { - certConfig.ClientCertificateFile = clientCertFile; - string clientCertKey = GetRunnerContext("ClientCertKey"); - string clientCertArchive = GetRunnerContext("ClientCertArchive"); - string clientCertPassword = GetRunnerContext("ClientCertPassword"); - - certConfig.ClientCertificatePrivateKeyFile = clientCertKey; - certConfig.ClientCertificateArchiveFile = clientCertArchive; - certConfig.ClientCertificatePassword = clientCertPassword; - - certConfig.VssClientCertificateManager = new RunnerClientCertificateManager(clientCertArchive, clientCertPassword); - } - - return certConfig; - } - else - { - return null; - } - } - private string Escape(string input) { foreach (var mapping in _commandEscapeMappings) diff --git a/src/Runner.Sdk/RunnerClientCertificateManager.cs b/src/Runner.Sdk/RunnerClientCertificateManager.cs deleted file mode 100644 index a64b86e50..000000000 --- a/src/Runner.Sdk/RunnerClientCertificateManager.cs +++ /dev/null @@ -1,40 +0,0 @@ - -using System.Security.Cryptography.X509Certificates; -using GitHub.Services.Common; - -namespace GitHub.Runner.Sdk -{ - public class RunnerCertificateSettings - { - public bool SkipServerCertificateValidation { get; set; } - public string CACertificateFile { get; set; } - public string ClientCertificateFile { get; set; } - public string ClientCertificatePrivateKeyFile { get; set; } - public string ClientCertificateArchiveFile { get; set; } - public string ClientCertificatePassword { get; set; } - public IVssClientCertificateManager VssClientCertificateManager { get; set; } - } - - public class RunnerClientCertificateManager : IVssClientCertificateManager - { - private readonly X509Certificate2Collection _clientCertificates = new X509Certificate2Collection(); - public X509Certificate2Collection ClientCertificates => _clientCertificates; - - public RunnerClientCertificateManager() - { - } - - public RunnerClientCertificateManager(string clientCertificateArchiveFile, string clientCertificatePassword) - { - AddClientCertificate(clientCertificateArchiveFile, clientCertificatePassword); - } - - public void AddClientCertificate(string clientCertificateArchiveFile, string clientCertificatePassword) - { - if (!string.IsNullOrEmpty(clientCertificateArchiveFile)) - { - _clientCertificates.Add(new X509Certificate2(clientCertificateArchiveFile, clientCertificatePassword)); - } - } - } -} diff --git a/src/Runner.Sdk/Util/VssUtil.cs b/src/Runner.Sdk/Util/VssUtil.cs index 4c7605af6..b5b6ce7b3 100644 --- a/src/Runner.Sdk/Util/VssUtil.cs +++ b/src/Runner.Sdk/Util/VssUtil.cs @@ -14,7 +14,7 @@ namespace GitHub.Runner.Sdk { public static class VssUtil { - public static void InitializeVssClientSettings(ProductInfoHeaderValue additionalUserAgent, IWebProxy proxy, IVssClientCertificateManager clientCert) + public static void InitializeVssClientSettings(ProductInfoHeaderValue additionalUserAgent, IWebProxy proxy) { var headerValues = new List(); headerValues.Add(additionalUserAgent); @@ -26,7 +26,6 @@ namespace GitHub.Runner.Sdk } VssClientHttpRequestSettings.Default.UserAgent = headerValues; - VssClientHttpRequestSettings.Default.ClientCertificateManager = clientCert; VssHttpMessageHandler.DefaultWebProxy = proxy; } @@ -83,7 +82,7 @@ namespace GitHub.Runner.Sdk if (serviceEndpoint.Authorization.Scheme == EndpointAuthorizationSchemes.OAuth && serviceEndpoint.Authorization.Parameters.TryGetValue(EndpointAuthorizationParameters.AccessToken, out accessToken)) { - credentials = new VssCredentials(null, new VssOAuthAccessTokenCredential(accessToken), CredentialPromptType.DoNotPrompt); + credentials = new VssCredentials(new VssOAuthAccessTokenCredential(accessToken), CredentialPromptType.DoNotPrompt); } return credentials; diff --git a/src/Runner.Worker/ExecutionContext.cs b/src/Runner.Worker/ExecutionContext.cs index 23e6ad8fa..e03d173af 100644 --- a/src/Runner.Worker/ExecutionContext.cs +++ b/src/Runner.Worker/ExecutionContext.cs @@ -41,7 +41,6 @@ namespace GitHub.Runner.Worker TaskResult? CommandResult { get; set; } CancellationToken CancellationToken { get; } List Endpoints { get; } - List SecureFiles { get; } PlanFeatures Features { get; } Variables Variables { get; } @@ -136,7 +135,6 @@ namespace GitHub.Runner.Worker public Task ForceCompleted => _forceCompleted.Task; public CancellationToken CancellationToken => _cancellationTokenSource.Token; public List Endpoints { get; private set; } - public List SecureFiles { get; private set; } public Variables Variables { get; private set; } public Dictionary IntraActionState { get; private set; } public HashSet OutputVariables => _outputvariables; @@ -257,7 +255,6 @@ namespace GitHub.Runner.Worker child.Features = Features; child.Variables = Variables; child.Endpoints = Endpoints; - child.SecureFiles = SecureFiles; if (intraActionState == null) { child.IntraActionState = new Dictionary(StringComparer.OrdinalIgnoreCase); @@ -549,9 +546,6 @@ namespace GitHub.Runner.Worker // Endpoints Endpoints = message.Resources.Endpoints; - // SecureFiles - SecureFiles = message.Resources.SecureFiles; - // Variables Variables = new Variables(HostContext, message.Variables); @@ -616,44 +610,6 @@ namespace GitHub.Runner.Worker // PostJobSteps for job ExecutionContext PostJobSteps = new Stack(); - // // Certificate variables - // var agentCert = HostContext.GetService(); - // if (agentCert.SkipServerCertificateValidation) - // { - // SetRunnerContext("sslskipcertvalidation", bool.TrueString); - // } - - // if (!string.IsNullOrEmpty(agentCert.CACertificateFile)) - // { - // SetRunnerContext("sslcainfo", agentCert.CACertificateFile); - // } - - // if (!string.IsNullOrEmpty(agentCert.ClientCertificateFile) && - // !string.IsNullOrEmpty(agentCert.ClientCertificatePrivateKeyFile) && - // !string.IsNullOrEmpty(agentCert.ClientCertificateArchiveFile)) - // { - // SetRunnerContext("clientcertfile", agentCert.ClientCertificateFile); - // SetRunnerContext("clientcertprivatekey", agentCert.ClientCertificatePrivateKeyFile); - // SetRunnerContext("clientcertarchive", agentCert.ClientCertificateArchiveFile); - - // if (!string.IsNullOrEmpty(agentCert.ClientCertificatePassword)) - // { - // HostContext.SecretMasker.AddValue(agentCert.ClientCertificatePassword); - // SetRunnerContext("clientcertpassword", agentCert.ClientCertificatePassword); - // } - // } - - // // Runtime option variables - // var runtimeOptions = HostContext.GetService().GetRunnerRuntimeOptions(); - // if (runtimeOptions != null) - // { - // #if OS_WINDOWS - // if (runtimeOptions.GitUseSecureChannel) - // { - // SetRunnerContext("gituseschannel", runtimeOptions.GitUseSecureChannel.ToString()); - // } - // #endif - // } // Job timeline record. InitializeTimelineRecord( diff --git a/src/Runner.Worker/Worker.cs b/src/Runner.Worker/Worker.cs index de22c444e..8db8424d2 100644 --- a/src/Runner.Worker/Worker.cs +++ b/src/Runner.Worker/Worker.cs @@ -40,8 +40,7 @@ namespace GitHub.Runner.Worker // Validate args. ArgUtil.NotNullOrEmpty(pipeIn, nameof(pipeIn)); ArgUtil.NotNullOrEmpty(pipeOut, nameof(pipeOut)); - var runnerCertManager = HostContext.GetService(); - VssUtil.InitializeVssClientSettings(HostContext.UserAgent, HostContext.WebProxy, runnerCertManager.VssClientCertificateManager); + VssUtil.InitializeVssClientSettings(HostContext.UserAgent, HostContext.WebProxy); var jobRunner = HostContext.CreateService(); using (var channel = HostContext.CreateService()) @@ -178,15 +177,6 @@ namespace GitHub.Runner.Worker } } } - - // Add masks for secure file download tickets - foreach (SecureFile file in message.Resources.SecureFiles ?? new List()) - { - if (!string.IsNullOrEmpty(file.Ticket)) - { - HostContext.SecretMasker.AddValue(file.Ticket); - } - } } private void SetCulture(Pipelines.AgentJobRequestMessage message) diff --git a/src/Sdk/AadAuthentication/CookieUtility.cs b/src/Sdk/AadAuthentication/CookieUtility.cs deleted file mode 100644 index ea9975646..000000000 --- a/src/Sdk/AadAuthentication/CookieUtility.cs +++ /dev/null @@ -1,264 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Linq; -using System.Net; -using System.Net.Http; -using System.Runtime.InteropServices; -using System.Text; -using GitHub.Services.Common; - -namespace GitHub.Services.Client -{ - internal static class CookieUtility - { - public static readonly String AcsMetadataRetrievalExceptionText = "Unable to retrieve ACS Metadata from '{0}'"; - public static readonly String FedAuthCookieName = "FedAuth"; - public static readonly String WindowsLiveSignOutUrl = "https://login.live.com/uilogout.srf"; - public static readonly Uri WindowsLiveCookieDomain = new Uri("https://login.live.com/"); - - public static CookieCollection GetFederatedCookies(Uri cookieDomainAndPath) - { - CookieCollection result = null; - - Cookie cookie = GetCookieEx(cookieDomainAndPath, FedAuthCookieName).FirstOrDefault(); - - if (cookie != null) - { - result = new CookieCollection(); - result.Add(cookie); - - for (Int32 x = 1; x < 50; x++) - { - String cookieName = FedAuthCookieName + x; - cookie = GetCookieEx(cookieDomainAndPath, cookieName).FirstOrDefault(); - - if (cookie != null) - { - result.Add(cookie); - } - else - { - break; - } - } - } - - return result; - } - - public static CookieCollection GetFederatedCookies(String[] token) - { - CookieCollection result = null; - - if (token != null && token.Length > 0 && token[0] != null) - { - result = new CookieCollection(); - result.Add(new Cookie(FedAuthCookieName, token[0])); - - for (Int32 x = 1; x < token.Length; x++) - { - String cookieName = FedAuthCookieName + x; - - if (token[x] != null) - { - Cookie cookie = new Cookie(cookieName, token[x]); - cookie.HttpOnly = true; - result.Add(cookie); - } - else - { - break; - } - } - } - - return result; - } - - public static CookieCollection GetFederatedCookies(IHttpResponse webResponse) - { - CookieCollection result = null; - IEnumerable cookies = null; - - if (webResponse.Headers.TryGetValues("Set-Cookie", out cookies)) - { - foreach (String cookie in cookies) - { - if (cookie != null && cookie.StartsWith(CookieUtility.FedAuthCookieName, StringComparison.OrdinalIgnoreCase)) - { - // Only take the security token field of the cookie, and discard the rest - String fedAuthToken = cookie.Split(';').FirstOrDefault(); - Int32 index = fedAuthToken.IndexOf('='); - - if (index > 0 && index < fedAuthToken.Length - 1) - { - String name = fedAuthToken.Substring(0, index); - String value = fedAuthToken.Substring(index + 1); - - result = result ?? new CookieCollection(); - result.Add(new Cookie(name, value)); - } - } - } - } - - return result; - } - - public static CookieCollection GetAllCookies(Uri cookieDomainAndPath) - { - CookieCollection result = null; - List cookies = GetCookieEx(cookieDomainAndPath, null); - foreach (Cookie cookie in cookies) - { - if (result == null) - { - result = new CookieCollection(); - } - - result.Add(cookie); - } - - return result; - } - - public static void DeleteFederatedCookies(Uri cookieDomainAndPath) - { - CookieCollection cookies = GetFederatedCookies(cookieDomainAndPath); - - if (cookies != null) - { - foreach (Cookie cookie in cookies) - { - DeleteCookieEx(cookieDomainAndPath, cookie.Name); - } - } - } - - public static void DeleteWindowsLiveCookies() - { - DeleteAllCookies(WindowsLiveCookieDomain); - } - - public static void DeleteAllCookies(Uri cookieDomainAndPath) - { - CookieCollection cookies = GetAllCookies(cookieDomainAndPath); - - if (cookies != null) - { - foreach (Cookie cookie in cookies) - { - DeleteCookieEx(cookieDomainAndPath, cookie.Name); - } - } - } - - public const UInt32 INTERNET_COOKIE_HTTPONLY = 0x00002000; - - [DllImport("wininet.dll", SetLastError = true, CharSet = CharSet.Unicode)] - static extern bool InternetGetCookieEx( - String url, String cookieName, StringBuilder cookieData, ref Int32 size, UInt32 flags, IntPtr reserved); - - [DllImport("wininet.dll", SetLastError = true, CharSet = CharSet.Unicode)] - static extern bool InternetSetCookieEx( - String url, String cookieName, String cookieData, UInt32 flags, IntPtr reserved); - - public static Boolean DeleteCookieEx(Uri cookiePath, String cookieName) - { - UInt32 flags = INTERNET_COOKIE_HTTPONLY; - - String path = cookiePath.ToString(); - if (!path.EndsWith("/", StringComparison.Ordinal)) - { - path = path + "/"; - } - - DateTime expiration = DateTime.UtcNow.AddYears(-1); - String cookieData = String.Format(CultureInfo.InvariantCulture, "{0}=0;expires={1};path=/;domain={2};httponly", cookieName, expiration.ToString("R"), cookiePath.Host); - - return InternetSetCookieEx(path, null, cookieData, flags, IntPtr.Zero); - } - - public static Boolean SetCookiesEx( - Uri cookiePath, - CookieCollection cookies) - { - String path = cookiePath.ToString(); - if (!path.EndsWith("/", StringComparison.Ordinal)) - { - path = path + "/"; - } - - Boolean successful = true; - foreach (Cookie cookie in cookies) - { - // This means it doesn't expire - if (cookie.Expires.Year == 1) - { - continue; - } - - String cookieData = String.Format(CultureInfo.InvariantCulture, - "{0}; path={1}; domain={2}; expires={3}; httponly", - cookie.Value, - cookie.Path, - cookie.Domain, - cookie.Expires.ToString("ddd, dd-MMM-yyyy HH:mm:ss 'GMT'")); - - successful &= InternetSetCookieEx(path, cookie.Name, cookieData, INTERNET_COOKIE_HTTPONLY, IntPtr.Zero); - } - return successful; - } - - public static List GetCookieEx(Uri cookiePath, String cookieName) - { - UInt32 flags = INTERNET_COOKIE_HTTPONLY; - - List cookies = new List(); - Int32 size = 256; - StringBuilder cookieData = new StringBuilder(size); - String path = cookiePath.ToString(); - if (!path.EndsWith("/", StringComparison.Ordinal)) - { - path = path + "/"; - } - - if (!InternetGetCookieEx(path, cookieName, cookieData, ref size, flags, IntPtr.Zero)) - { - if (size < 0) - { - return cookies; - } - - cookieData = new StringBuilder(size); - - if (!InternetGetCookieEx(path, cookieName, cookieData, ref size, flags, IntPtr.Zero)) - { - return cookies; - } - } - - if (cookieData.Length > 0) - { - String[] cookieSections = cookieData.ToString().Split(new char[] { ';' }); - - foreach (String cookieSection in cookieSections) - { - String[] cookieParts = cookieSection.Split(new char[] { '=' }, 2); - - if (cookieParts.Length == 2) - { - Cookie cookie = new Cookie(); - cookie.Name = cookieParts[0].TrimStart(); - cookie.Value = cookieParts[1]; - cookie.HttpOnly = true; - cookies.Add(cookie); - } - } - } - - return cookies; - } - } -} diff --git a/src/Sdk/AadAuthentication/VssAadCredential.cs b/src/Sdk/AadAuthentication/VssAadCredential.cs deleted file mode 100644 index 92f365d5f..000000000 --- a/src/Sdk/AadAuthentication/VssAadCredential.cs +++ /dev/null @@ -1,95 +0,0 @@ -using System; -using System.Net.Http; -using System.Security; -using GitHub.Services.Common; - -namespace GitHub.Services.Client -{ - /// - /// Currently it is impossible to get whether prompting is allowed from the credential itself without reproducing the logic - /// used by VssClientCredentials. Since this is a stop gap solution to get Windows integrated authentication to work against - /// AAD via ADFS for now this class will only support that one, non-interactive flow. We need to assess how much we want to - /// invest in this legacy stack rather than recommending people move to the VssConnect API for future authentication needs. - /// - [Serializable] - public sealed class VssAadCredential : FederatedCredential - { - private string username; - private SecureString password; - - public VssAadCredential() - : base(null) - { - } - - public VssAadCredential(VssAadToken initialToken) - : base(initialToken) - { - } - - public VssAadCredential(string username) - : base(null) - { - this.username = username; - } - - public VssAadCredential(string username, string password) - : base(null) - { - this.username = username; - - if (password != null) - { - this.password = new SecureString(); - - foreach (char character in password) - { - this.password.AppendChar(character); - } - } - } - - public VssAadCredential(string username, SecureString password) - : base(null) - { - this.username = username; - this.password = password; - } - - public override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Aad; - } - } - - internal string Username - { - get - { - return username; - } - } - - internal SecureString Password => password; - - public override bool IsAuthenticationChallenge(IHttpResponse webResponse) - { - bool isNonAuthenticationChallenge = false; - return VssFederatedCredential.IsVssFederatedAuthenticationChallenge(webResponse, out isNonAuthenticationChallenge) ?? false; - } - - protected override IssuedTokenProvider OnCreateTokenProvider( - Uri serverUrl, - IHttpResponse response) - { - if (response == null && base.InitialToken == null) - { - return null; - } - - return new VssAadTokenProvider(this); - } - } -} diff --git a/src/Sdk/AadAuthentication/VssAadSettings.cs b/src/Sdk/AadAuthentication/VssAadSettings.cs deleted file mode 100644 index 651d642c2..000000000 --- a/src/Sdk/AadAuthentication/VssAadSettings.cs +++ /dev/null @@ -1,89 +0,0 @@ -using System; -using System.Diagnostics; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.Services.Client -{ - internal static class VssAadSettings - { - public const string DefaultAadInstance = "https://login.microsoftonline.com/"; - - public const string CommonTenant = "common"; - - // VSTS service principal. - public const string Resource = "499b84ac-1321-427f-aa17-267ca6975798"; - - // Visual Studio IDE client ID originally provisioned by Azure Tools. - public const string Client = "872cd9fa-d31f-45e0-9eab-6e460a02d1f1"; - - // AAD Production Application tenant. - private const string ApplicationTenantId = "f8cdef31-a31e-4b4a-93e4-5f571e91255a"; - -#if !NETSTANDARD - public static Uri NativeClientRedirectUri - { - get - { - Uri nativeClientRedirect = null; - - try - { - string nativeRedirect = VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.AadNativeClientRedirect); - if (!string.IsNullOrEmpty(nativeRedirect)) - { - Uri.TryCreate(nativeRedirect, UriKind.RelativeOrAbsolute, out nativeClientRedirect); - } - } - catch (Exception e) - { - Debug.WriteLine(string.Format("NativeClientRedirectUri: {0}", e)); - } - - return nativeClientRedirect ?? new Uri("urn:ietf:wg:oauth:2.0:oob"); - } - } - - public static string ClientId - { - get - { - string nativeRedirect = VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.AadNativeClientIdentifier); - return nativeRedirect ?? VssAadSettings.Client; - } - } -#endif - - public static string AadInstance - { - get - { -#if !NETSTANDARD - string aadInstance = VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.AadInstance); -#else - string aadInstance = null; -#endif - - if (string.IsNullOrWhiteSpace(aadInstance)) - { - aadInstance = DefaultAadInstance; - } - else if (!aadInstance.EndsWith("/")) - { - aadInstance = aadInstance + "/"; - } - - return aadInstance; - } - } - -#if !NETSTANDARD - /// - /// Application tenant either from a registry override or a constant - /// - public static string ApplicationTenant => - VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.AadApplicationTenant) - ?? VssAadSettings.ApplicationTenantId; -#endif - } -} diff --git a/src/Sdk/AadAuthentication/VssAadToken.cs b/src/Sdk/AadAuthentication/VssAadToken.cs deleted file mode 100644 index debfad147..000000000 --- a/src/Sdk/AadAuthentication/VssAadToken.cs +++ /dev/null @@ -1,124 +0,0 @@ -using System; -using Microsoft.IdentityModel.Clients.ActiveDirectory; -using GitHub.Services.Common; - -namespace GitHub.Services.Client -{ - [Serializable] - public class VssAadToken : IssuedToken - { - private string accessToken; - private string accessTokenType; - - private AuthenticationContext authenticationContext; - private UserCredential userCredential; - private VssAadTokenOptions options; - - public VssAadToken(AuthenticationResult authentication) - { - // Prevent any attempt to store this token. - this.FromStorage = true; - - if (!string.IsNullOrWhiteSpace(authentication.AccessToken)) - { - this.Authenticated(); - } - - this.accessToken = authentication.AccessToken; - this.accessTokenType = authentication.AccessTokenType; - } - - public VssAadToken( - string accessTokenType, - string accessToken) - { - // Prevent any attempt to store this token. - this.FromStorage = true; - - if (!string.IsNullOrWhiteSpace(accessToken) && !string.IsNullOrWhiteSpace(accessTokenType)) - { - this.Authenticated(); - } - - this.accessToken = accessToken; - this.accessTokenType = accessTokenType; - } - - public VssAadToken( - AuthenticationContext authenticationContext, - UserCredential userCredential = null, - VssAadTokenOptions options = VssAadTokenOptions.None) - { - // Prevent any attempt to store this token. - this.FromStorage = true; - - this.authenticationContext = authenticationContext; - this.userCredential = userCredential; - this.options = options; - } - - protected internal override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Aad; - } - } - - public AuthenticationResult AcquireToken() - { - if (this.authenticationContext == null) - { - return null; - } - - AuthenticationResult authenticationResult = null; - - for (int index = 0; index < 3; index++) - { - try - { - if (this.userCredential == null && !options.HasFlag(VssAadTokenOptions.AllowDialog)) - { - authenticationResult = authenticationContext.AcquireTokenSilentAsync(VssAadSettings.Resource, VssAadSettings.Client).ConfigureAwait(false).GetAwaiter().GetResult(); - } - else - { - authenticationResult = authenticationContext.AcquireTokenAsync(VssAadSettings.Resource, VssAadSettings.Client, this.userCredential).ConfigureAwait(false).GetAwaiter().GetResult(); - } - - if (authenticationResult != null) - { - break; - } - } - catch (Exception x) - { - System.Diagnostics.Debug.WriteLine("Failed to get ADFS token: " + x.ToString()); - } - } - - return authenticationResult; - } - - internal override void ApplyTo(IHttpRequest request) - { - AuthenticationResult authenticationResult = AcquireToken(); - if (authenticationResult != null) - { - request.Headers.SetValue(Common.Internal.HttpHeaders.Authorization, $"{authenticationResult.AccessTokenType} {authenticationResult.AccessToken}"); - } - else if (!string.IsNullOrEmpty(this.accessTokenType) && !string.IsNullOrEmpty(this.accessToken)) - { - request.Headers.SetValue(Common.Internal.HttpHeaders.Authorization, $"{this.accessTokenType} {this.accessToken}"); - } - } - } - - [Flags] - public enum VssAadTokenOptions - { - None = 0, - AllowDialog = 1 - } -} diff --git a/src/Sdk/AadAuthentication/VssAadTokenProvider.cs b/src/Sdk/AadAuthentication/VssAadTokenProvider.cs deleted file mode 100644 index a10dbf1b5..000000000 --- a/src/Sdk/AadAuthentication/VssAadTokenProvider.cs +++ /dev/null @@ -1,77 +0,0 @@ -using System.Threading; -using System.Threading.Tasks; -using Microsoft.IdentityModel.Clients.ActiveDirectory; -using GitHub.Services.Common; - -namespace GitHub.Services.Client -{ - internal sealed class VssAadTokenProvider : IssuedTokenProvider - { - public VssAadTokenProvider(VssAadCredential credential) - : base(credential, null, null) - { - } - - public override bool GetTokenIsInteractive - { - get - { - return false; - } - } - - private VssAadToken GetVssAadToken() - { - AuthenticationContext authenticationContext = new AuthenticationContext(string.Concat(VssAadSettings.AadInstance, VssAadSettings.CommonTenant)); - UserCredential userCredential = null; - - VssAadCredential credential = this.Credential as VssAadCredential; - - if (credential?.Username != null) - { -#if NETSTANDARD - // UserPasswordCredential does not currently exist for ADAL 3.13.5 for any non-desktop build. - userCredential = new UserCredential(credential.Username); -#else - if (credential.Password != null) - { - userCredential = new UserPasswordCredential(credential.Username, credential.Password); - - } - else - { - userCredential = new UserCredential(credential.Username); - } -#endif - } - else - { - userCredential = new UserCredential(); - } - - return new VssAadToken(authenticationContext, userCredential); - } - - /// - /// Temporary implementation since we don't have a good configuration story here at the moment. - /// - protected override Task OnGetTokenAsync(IssuedToken failedToken, CancellationToken cancellationToken) - { - // If we have already tried to authenticate with an AAD token retrieved from Windows integrated authentication and it is not working, clear out state. - if (failedToken != null && failedToken.CredentialType == VssCredentialsType.Aad && failedToken.IsAuthenticated) - { - this.CurrentToken = null; - return Task.FromResult(null); - } - - try - { - return Task.FromResult(GetVssAadToken()); - } - catch - { } - - return Task.FromResult(null); - } - } -} diff --git a/src/Sdk/AadAuthentication/VssFederatedCredential.cs b/src/Sdk/AadAuthentication/VssFederatedCredential.cs deleted file mode 100644 index dcc5bda97..000000000 --- a/src/Sdk/AadAuthentication/VssFederatedCredential.cs +++ /dev/null @@ -1,172 +0,0 @@ -using System; -using System.Linq; -using System.Net; -using GitHub.Services.Common; -using GitHub.Services.Common.Internal; - -namespace GitHub.Services.Client -{ - /// - /// Provides federated authentication with a hosted VssConnection instance using cookies. - /// - [Serializable] - public sealed class VssFederatedCredential : FederatedCredential - { - /// - /// Initializes a new VssFederatedCredential instance. - /// - public VssFederatedCredential() - : this(true) - { - } - - /// - /// Initializes a new VssFederatedCredential instance. - /// - public VssFederatedCredential(Boolean useCache) - : this(useCache, null) - { - } - - /// - /// Initializes a new VssFederatedCredential instance. - /// - /// The initial token if available - public VssFederatedCredential(VssFederatedToken initialToken) - : this(false, initialToken) - { - } - - public VssFederatedCredential( - Boolean useCache, - VssFederatedToken initialToken) - : base(initialToken) - { -#if !NETSTANDARD - if (useCache) - { - Storage = new VssClientCredentialStorage(); - } -#endif - } - - /// - /// - /// - public override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Federated; - } - } - - public override Boolean IsAuthenticationChallenge(IHttpResponse webResponse) - { - bool isNonAuthenticationChallenge = false; - return IsVssFederatedAuthenticationChallenge(webResponse, out isNonAuthenticationChallenge) ?? isNonAuthenticationChallenge; - } - - protected override IssuedTokenProvider OnCreateTokenProvider( - Uri serverUrl, - IHttpResponse response) - { - // The response is only null when attempting to determine the most appropriate token provider to - // use for the connection. The only way we should do anything here is if we have an initial token - // since that means we can present something without making a server call. - if (response == null && base.InitialToken == null) - { - return null; - } - - Uri signInUrl = null; - String realm = String.Empty; - String issuer = String.Empty; - - if (response != null) - { - var location = response.Headers.GetValues(HttpHeaders.Location).FirstOrDefault(); - if (location == null) - { - location = response.Headers.GetValues(HttpHeaders.TfsFedAuthRedirect).FirstOrDefault(); - } - - if (!String.IsNullOrEmpty(location)) - { - signInUrl = new Uri(location); - } - - // Inform the server that we support the javascript notify "smart client" pattern for ACS auth - AddParameter(ref signInUrl, "protocol", "javascriptnotify"); - - // Do not automatically sign in with existing FedAuth cookie - AddParameter(ref signInUrl, "force", "1"); - - GetRealmAndIssuer(response, out realm, out issuer); - } - - return new VssFederatedTokenProvider(this, serverUrl, signInUrl, issuer, realm); - } - - internal static void GetRealmAndIssuer( - IHttpResponse response, - out String realm, - out String issuer) - { - realm = response.Headers.GetValues(HttpHeaders.TfsFedAuthRealm).FirstOrDefault(); - issuer = response.Headers.GetValues(HttpHeaders.TfsFedAuthIssuer).FirstOrDefault(); - - if (!String.IsNullOrWhiteSpace(issuer)) - { - issuer = new Uri(issuer).GetLeftPart(UriPartial.Authority); - } - } - - internal static Boolean? IsVssFederatedAuthenticationChallenge( - IHttpResponse webResponse, - out Boolean isNonAuthenticationChallenge) - { - isNonAuthenticationChallenge = false; - - if (webResponse == null) - { - return false; - } - - // Check to make sure that the redirect was issued from the Tfs service. We include the TfsServiceError - // header to avoid the possibility that a redirect from a non-tfs service is issued and we incorrectly - // launch the credentials UI. - if (webResponse.StatusCode == HttpStatusCode.Found || - webResponse.StatusCode == HttpStatusCode.Redirect) - { - return webResponse.Headers.GetValues(HttpHeaders.Location).Any() && webResponse.Headers.GetValues(HttpHeaders.TfsFedAuthRealm).Any(); - } - else if (webResponse.StatusCode == HttpStatusCode.Unauthorized) - { - return webResponse.Headers.GetValues(HttpHeaders.WwwAuthenticate).Any(x => x.StartsWith("TFS-Federated", StringComparison.OrdinalIgnoreCase)); - } - else if (webResponse.StatusCode == HttpStatusCode.Forbidden) - { - // This is not strictly an "authentication challenge" but it is a state the user can do something about so they can get access to the resource - // they are attempting to access. Specifically, the user will hit this when they need to update or create a profile required by business policy. - isNonAuthenticationChallenge = webResponse.Headers.GetValues(HttpHeaders.TfsFedAuthRedirect).Any(); - if (isNonAuthenticationChallenge) - { - return null; - } - } - - return false; - } - - private static void AddParameter(ref Uri uri, String name, String value) - { - if (uri.Query.IndexOf(String.Concat(name, "="), StringComparison.OrdinalIgnoreCase) < 0) - { - UriBuilder builder = new UriBuilder(uri); - builder.Query = String.Concat(builder.Query.TrimStart('?'), "&", name, "=", value); - uri = builder.Uri; - } - } - } -} diff --git a/src/Sdk/AadAuthentication/VssFederatedToken.cs b/src/Sdk/AadAuthentication/VssFederatedToken.cs deleted file mode 100644 index 3e3cbed9d..000000000 --- a/src/Sdk/AadAuthentication/VssFederatedToken.cs +++ /dev/null @@ -1,84 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Net; -using GitHub.Services.Common; - -namespace GitHub.Services.Client -{ - /// - /// Provides a cookie-based authentication token. - /// - [Serializable] - public sealed class VssFederatedToken : IssuedToken - { - /// - /// Initializes a new VssFederatedToken instance using the specified cookies. - /// - /// - public VssFederatedToken(CookieCollection cookies) - { - ArgumentUtility.CheckForNull(cookies, "cookies"); - m_cookies = cookies; - } - - /// - /// Returns the CookieCollection contained within this token. For internal use only. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public CookieCollection CookieCollection - { - get - { - return m_cookies; - } - } - - protected internal override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Federated; - } - } - - internal override void ApplyTo(IHttpRequest request) - { - // From http://www.ietf.org/rfc/rfc2109.txt: - // Note: For backward compatibility, the separator in the Cookie header - // is semi-colon (;) everywhere. - // - // HttpRequestHeaders uses comma as the default separator, so instead of returning - // a list of cookies, the method returns one semicolon separated string. - IEnumerable values = request.Headers.GetValues(s_cookieHeader); - request.Headers.SetValue(s_cookieHeader, GetHeaderValue(values)); - } - - private String GetHeaderValue(IEnumerable cookieHeaders) - { - List currentCookies = new List(); - if (cookieHeaders != null) - { - foreach (String value in cookieHeaders) - { - currentCookies.AddRange(value.Split(';').Select(x => x.Trim())); - } - } - - currentCookies.RemoveAll(x => String.IsNullOrEmpty(x)); - - foreach (Cookie cookie in m_cookies) - { - // Remove all existing cookies that match the name of the cookie we are going to add. - currentCookies.RemoveAll(x => String.Equals(x.Substring(0, x.IndexOf('=')), cookie.Name, StringComparison.OrdinalIgnoreCase)); - currentCookies.Add(String.Concat(cookie.Name, "=", cookie.Value)); - } - - return String.Join("; ", currentCookies); - } - - private CookieCollection m_cookies; - private static readonly String s_cookieHeader = HttpRequestHeader.Cookie.ToString(); - } -} diff --git a/src/Sdk/AadAuthentication/VssFederatedTokenProvider.cs b/src/Sdk/AadAuthentication/VssFederatedTokenProvider.cs deleted file mode 100644 index e43f3de4c..000000000 --- a/src/Sdk/AadAuthentication/VssFederatedTokenProvider.cs +++ /dev/null @@ -1,157 +0,0 @@ -using System; -using System.Net; -using System.Net.Http; -using GitHub.Services.Common; -using System.Globalization; - -namespace GitHub.Services.Client -{ - /// - /// Provides authentication for internet identities using single-sign-on cookies. - /// - internal sealed class VssFederatedTokenProvider : IssuedTokenProvider, ISupportSignOut - { - public VssFederatedTokenProvider( - VssFederatedCredential credential, - Uri serverUrl, - Uri signInUrl, - String issuer, - String realm) - : base(credential, serverUrl, signInUrl) - { - Issuer = issuer; - Realm = realm; - } - - protected override String AuthenticationScheme - { - get - { - return "TFS-Federated"; - } - } - - protected override String AuthenticationParameter - { - get - { - if (String.IsNullOrEmpty(this.Issuer) && String.IsNullOrEmpty(this.Realm)) - { - return String.Empty; - } - else - { - return String.Format(CultureInfo.InvariantCulture, "issuer=\"{0}\", realm=\"{1}\"", this.Issuer, this.Realm); - } - } - } - - /// - /// Gets the federated credential from which this provider was created. - /// - public new VssFederatedCredential Credential - { - get - { - return (VssFederatedCredential)base.Credential; - } - } - - /// - /// Gets a value indicating whether or not a call to get token will require interactivity. - /// - public override Boolean GetTokenIsInteractive - { - get - { - return this.CurrentToken == null; - } - } - - /// - /// Gets the issuer for the token provider. - /// - public String Issuer - { - get; - private set; - } - - /// - /// Gets the realm for the token provider. - /// - public String Realm - { - get; - private set; - } - - protected internal override Boolean IsAuthenticationChallenge(IHttpResponse webResponse) - { - if (!base.IsAuthenticationChallenge(webResponse)) - { - return false; - } - - // This means we were proactively constructed without any connection information. In this case - // we return false to ensure that a new provider is reconstructed with all appropriate configuration - // to retrieve a new token. - if (this.SignInUrl == null) - { - return false; - } - - String realm, issuer; - VssFederatedCredential.GetRealmAndIssuer(webResponse, out realm, out issuer); - - return this.Realm.Equals(realm, StringComparison.OrdinalIgnoreCase) && - this.Issuer.Equals(issuer, StringComparison.OrdinalIgnoreCase); - } - - protected override IssuedToken OnValidatingToken( - IssuedToken token, - IHttpResponse webResponse) - { - // If the response has Set-Cookie headers, attempt to retrieve the FedAuth cookie from the response - // and replace the current token with the new FedAuth cookie. Note that the server only reissues the - // FedAuth cookie if it is issued for more than an hour. - CookieCollection fedAuthCookies = CookieUtility.GetFederatedCookies(webResponse); - - if (fedAuthCookies != null) - { - // The reissued token should have the same user information as the previous one. - VssFederatedToken federatedToken = new VssFederatedToken(fedAuthCookies) - { - Properties = token.Properties, - UserId = token.UserId, - UserName = token.UserName - }; - - token = federatedToken; - } - - return token; - } - - public void SignOut(Uri signOutUrl, Uri replyToUrl, String identityProvider) - { - // The preferred implementation is to follow the signOutUrl with a browser and kill the browser whenever it - // arrives at the replyToUrl (or if it bombs out somewhere along the way). - // This will work for all Web-based identity providers (Live, Google, Yahoo, Facebook) supported by ACS provided that - // the TFS server has registered sign-out urls (in the TF Registry) for each of these. - // This is the long-term approach that should be pursued and probably the approach recommended to other - // clients which don't have direct access to the cookie store (TEE?) - - // In the short term we are simply going to delete the TFS cookies and the Windows Live cookies that are exposed to this - // session. This has the drawback of not properly signing out of Live (you'd still be signed in to e.g. Hotmail, Xbox, MSN, etc.) - // but will allow the user to re-enter their live credentials and sign-in again to TFS. - // The other drawback is that the clients will have to be updated again when we pursue the implementation outlined above. - - CookieUtility.DeleteFederatedCookies(replyToUrl); - if (!String.IsNullOrEmpty(identityProvider) && identityProvider.Equals("Windows Live ID", StringComparison.OrdinalIgnoreCase)) - { - CookieUtility.DeleteWindowsLiveCookies(); - } - } - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssBasicCredential.cs b/src/Sdk/Common/Common/Authentication/VssBasicCredential.cs deleted file mode 100644 index eb984d19f..000000000 --- a/src/Sdk/Common/Common/Authentication/VssBasicCredential.cs +++ /dev/null @@ -1,92 +0,0 @@ -using System; -using System.Linq; -using System.Net; -using GitHub.Services.Common.Internal; - -namespace GitHub.Services.Common -{ - /// - /// Provides a credential for basic authentication against a Visual Studio Service. - /// - public sealed class VssBasicCredential : FederatedCredential - { - /// - /// Initializes a new VssBasicCredential instance with no token specified. - /// - public VssBasicCredential() - : this((VssBasicToken)null) - { - } - - /// - /// Initializes a new VssBasicCredential instance with the specified user name and password. - /// - /// The user name - /// The password - public VssBasicCredential( - string userName, - string password) - : this(new VssBasicToken(new NetworkCredential(userName, password))) - { - } - - /// - /// Initializes a new VssBasicCredential instance with the specified token. - /// - /// An optional token which, if present, should be used before obtaining a new token - public VssBasicCredential(ICredentials initialToken) - : this(new VssBasicToken(initialToken)) - { - } - - /// - /// Initializes a new VssBasicCredential instance with the specified token. - /// - /// An optional token which, if present, should be used before obtaining a new token - public VssBasicCredential(VssBasicToken initialToken) - : base(initialToken) - { - } - - public override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Basic; - } - } - - public override bool IsAuthenticationChallenge(IHttpResponse webResponse) - { - if (webResponse == null) - { - return false; - } - - if (webResponse.StatusCode != HttpStatusCode.Found && - webResponse.StatusCode != HttpStatusCode.Redirect && - webResponse.StatusCode != HttpStatusCode.Unauthorized) - { - return false; - } - - return webResponse.Headers.GetValues(HttpHeaders.WwwAuthenticate).Any(x => x.StartsWith("Basic", StringComparison.OrdinalIgnoreCase)); - } - - protected override IssuedTokenProvider OnCreateTokenProvider( - Uri serverUrl, - IHttpResponse response) - { - if (serverUrl.Scheme != "https") - { - String unsafeBasicAuthEnv = Environment.GetEnvironmentVariable("VSS_ALLOW_UNSAFE_BASICAUTH") ?? "false"; - if (!Boolean.TryParse(unsafeBasicAuthEnv, out Boolean unsafeBasicAuth) || !unsafeBasicAuth) - { - throw new InvalidOperationException(CommonResources.BasicAuthenticationRequiresSsl()); - } - } - - return new BasicAuthTokenProvider(this, serverUrl); - } - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssBasicToken.cs b/src/Sdk/Common/Common/Authentication/VssBasicToken.cs deleted file mode 100644 index ce4142bf2..000000000 --- a/src/Sdk/Common/Common/Authentication/VssBasicToken.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.Globalization; -using System.Net; - -namespace GitHub.Services.Common -{ - /// - /// Provides a token for basic authentication of internet identities. - /// - public sealed class VssBasicToken : IssuedToken - { - /// - /// Initializes a new BasicAuthToken instance with the specified token value. - /// - /// The credentials which should be used for authentication - public VssBasicToken(ICredentials credentials) - { - m_credentials = credentials; - } - - internal ICredentials Credentials - { - get - { - return m_credentials; - } - } - - protected internal override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Basic; - } - } - - internal override void ApplyTo(IHttpRequest request) - { - var basicCredential = m_credentials.GetCredential(request.RequestUri, "Basic"); - if (basicCredential != null) - { - request.Headers.SetValue(Internal.HttpHeaders.Authorization, "Basic " + FormatBasicAuthHeader(basicCredential)); - } - } - - private static String FormatBasicAuthHeader(NetworkCredential credential) - { - String authHeader = String.Empty; - if (!String.IsNullOrEmpty(credential.Domain)) - { - authHeader = String.Format(CultureInfo.InvariantCulture, "{0}\\{1}:{2}", credential.Domain, credential.UserName, credential.Password); - } - else - { - authHeader = String.Format(CultureInfo.InvariantCulture, "{0}:{1}", credential.UserName, credential.Password); - } - - return Convert.ToBase64String(VssHttpRequestSettings.Encoding.GetBytes(authHeader)); - } - - private readonly ICredentials m_credentials; - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssBasicTokenProvider.cs b/src/Sdk/Common/Common/Authentication/VssBasicTokenProvider.cs deleted file mode 100644 index 051699965..000000000 --- a/src/Sdk/Common/Common/Authentication/VssBasicTokenProvider.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System; -using System.Net; - -namespace GitHub.Services.Common -{ - internal sealed class BasicAuthTokenProvider : IssuedTokenProvider - { - public BasicAuthTokenProvider( - VssBasicCredential credential, - Uri serverUrl) - : base(credential, serverUrl, serverUrl) - { - } - - protected override String AuthenticationScheme - { - get - { - return "Basic"; - } - } - - public new VssBasicCredential Credential - { - get - { - return (VssBasicCredential)base.Credential; - } - } - - public override Boolean GetTokenIsInteractive - { - get - { - return base.CurrentToken == null; - } - } - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssCredentials.cs b/src/Sdk/Common/Common/Authentication/VssCredentials.cs index 92ffd5e5a..c29c5fa31 100644 --- a/src/Sdk/Common/Common/Authentication/VssCredentials.cs +++ b/src/Sdk/Common/Common/Authentication/VssCredentials.cs @@ -51,47 +51,7 @@ namespace GitHub.Services.Common /// Initializes a new VssCredentials instance with default credentials. /// public VssCredentials() - : this(true) - { - } - - /// - /// Initializes a new VssCredentials instance with default credentials if specified. - /// - /// True to use default windows credentials; otherwise, false - public VssCredentials(bool useDefaultCredentials) - : this(new WindowsCredential(useDefaultCredentials)) - { - } - - /// - /// Initializes a new VssCredentials instance with the specified windows credential. - /// - /// The windows credential to use for authentication - public VssCredentials(WindowsCredential windowsCredential) - : this(windowsCredential, null) - { - } - - /// - /// Initializes a new VssCredentials instance with the specified windows credential. - /// - /// The windows credential to use for authentication - /// CredentialPromptType.PromptIfNeeded if interactive prompts are allowed, otherwise CredentialProptType.DoNotPrompt - public VssCredentials( - WindowsCredential windowsCredential, - CredentialPromptType promptType) - : this(windowsCredential, null, promptType) - { - } - - /// - /// Initializes a new VssCredentials instance with the specified issued token credential and - /// default windows credential. - /// - /// The federated credential to use for authentication - public VssCredentials(FederatedCredential federatedCredential) - : this(new WindowsCredential(), federatedCredential) + : this(null) { } @@ -99,12 +59,9 @@ namespace GitHub.Services.Common /// Initializes a new VssCredentials instance with the specified windows and issued token /// credential. /// - /// The windows credential to use for authentication /// The federated credential to use for authentication - public VssCredentials( - WindowsCredential windowsCredential, - FederatedCredential federatedCredential) - : this(windowsCredential, federatedCredential, EnvironmentUserInteractive + public VssCredentials(FederatedCredential federatedCredential) + : this(federatedCredential, EnvironmentUserInteractive ? CredentialPromptType.PromptIfNeeded : CredentialPromptType.DoNotPrompt) { } @@ -113,14 +70,12 @@ namespace GitHub.Services.Common /// Initializes a new VssCredentials instance with the specified windows and issued token /// credential. /// - /// The windows credential to use for authentication /// The federated credential to use for authentication /// CredentialPromptType.PromptIfNeeded if interactive prompts are allowed, otherwise CredentialProptType.DoNotPrompt public VssCredentials( - WindowsCredential windowsCredential, FederatedCredential federatedCredential, CredentialPromptType promptType) - : this(windowsCredential, federatedCredential, promptType, null) + : this(federatedCredential, promptType, null) { } @@ -128,16 +83,14 @@ namespace GitHub.Services.Common /// Initializes a new VssCredentials instance with the specified windows and issued token /// credential. /// - /// The windows credential to use for authentication /// The federated credential to use for authentication /// CredentialPromptType.PromptIfNeeded if interactive prompts are allowed; otherwise, CredentialProptType.DoNotPrompt /// An optional TaskScheduler to ensure credentials prompting occurs on the UI thread public VssCredentials( - WindowsCredential windowsCredential, FederatedCredential federatedCredential, CredentialPromptType promptType, TaskScheduler scheduler) - : this(windowsCredential, federatedCredential, promptType, scheduler, null) + : this(federatedCredential, promptType, scheduler, null) { } @@ -145,13 +98,11 @@ namespace GitHub.Services.Common /// Initializes a new VssCredentials instance with the specified windows and issued token /// credential. /// - /// The windows credential to use for authentication /// The federated credential to use for authentication /// CredentialPromptType.PromptIfNeeded if interactive prompts are allowed; otherwise, CredentialProptType.DoNotPrompt /// An optional TaskScheduler to ensure credentials prompting occurs on the UI thread /// An optional IVssCredentialPrompt to perform prompting for credentials public VssCredentials( - WindowsCredential windowsCredential, FederatedCredential federatedCredential, CredentialPromptType promptType, TaskScheduler scheduler, @@ -172,13 +123,6 @@ namespace GitHub.Services.Common scheduler = TaskScheduler.Default; } - if (windowsCredential != null) - { - m_windowsCredential = windowsCredential; - m_windowsCredential.Scheduler = scheduler; - m_windowsCredential.Prompt = credentialPrompt; - } - if (federatedCredential != null) { m_federatedCredential = federatedCredential; @@ -199,16 +143,6 @@ namespace GitHub.Services.Common return new VssCredentials(credential); } - /// - /// Implicitly converts a WindowsCredential instance into a VssCredentials instance. - /// - /// The windows credential instance - /// A new VssCredentials instance which wraps the specified credential - public static implicit operator VssCredentials(WindowsCredential credential) - { - return new VssCredentials(credential); - } - /// /// Gets or sets a value indicating whether or not interactive prompts are allowed. /// @@ -240,17 +174,6 @@ namespace GitHub.Services.Common } } - /// - /// Gets the windows credential to use for NTLM authentication with the server. - /// - public WindowsCredential Windows - { - get - { - return m_windowsCredential; - } - } - /// /// A pluggable credential store. /// Simply assign a storage implementation to this property @@ -267,11 +190,6 @@ namespace GitHub.Services.Common { m_credentialStorage = value; - if (m_windowsCredential != null) - { - m_windowsCredential.Storage = value; - } - if (m_federatedCredential != null) { m_federatedCredential.Storage = value; @@ -327,20 +245,6 @@ namespace GitHub.Services.Common VssHttpEventSource.Log.IssuedTokenProviderCreated(traceActivity, tokenProvider); } } - else if (m_windowsCredential != null && m_windowsCredential.IsAuthenticationChallenge(webResponse)) - { - if (tokenProvider != null) - { - VssHttpEventSource.Log.IssuedTokenProviderRemoved(traceActivity, tokenProvider); - } - - tokenProvider = m_windowsCredential.CreateTokenProvider(serverUrl, webResponse, failedToken); - - if (tokenProvider != null) - { - VssHttpEventSource.Log.IssuedTokenProviderCreated(traceActivity, tokenProvider); - } - } m_currentProvider = tokenProvider; } @@ -356,7 +260,7 @@ namespace GitHub.Services.Common /// Stores the active token provider, if one exists /// True if a token provider was found, false otherwise public bool TryGetTokenProvider( - Uri serverUrl, + Uri serverUrl, out IssuedTokenProvider provider) { ArgumentUtility.CheckForNull(serverUrl, "serverUrl"); @@ -371,11 +275,6 @@ namespace GitHub.Services.Common m_currentProvider = m_federatedCredential.CreateTokenProvider(serverUrl, null, null); } - if (m_currentProvider == null && m_windowsCredential != null) - { - m_currentProvider = m_windowsCredential.CreateTokenProvider(serverUrl, null, null); - } - if (m_currentProvider != null) { VssHttpEventSource.Log.IssuedTokenProviderCreated(VssTraceActivity.Current, m_currentProvider); @@ -401,11 +300,6 @@ namespace GitHub.Services.Common } bool isChallenge = false; - if (m_windowsCredential != null) - { - isChallenge = m_windowsCredential.IsAuthenticationChallenge(webResponse); - } - if (!isChallenge && m_federatedCredential != null) { isChallenge = m_federatedCredential.IsAuthenticationChallenge(webResponse); @@ -415,8 +309,8 @@ namespace GitHub.Services.Common } internal void SignOut( - Uri serverUrl, - Uri serviceLocation, + Uri serverUrl, + Uri serviceLocation, string identityProvider) { // Remove the token in the storage and the current token provider. Note that we don't @@ -450,110 +344,6 @@ namespace GitHub.Services.Common tokenProviderWithSignOut.SignOut(serviceLocation, serverUrl, identityProvider); } -#if !NETSTANDARD - /// - /// Loads stored credentials for the specified server if found. If no credentials are found in the windows - /// credential store for the specified server and options then default credentials are returned. - /// - /// The server location - /// A value indicating whether or not an exact or partial match of the server is required - /// A credentials object populated with stored credentials for the server if found - public static VssCredentials LoadCachedCredentials( - Uri serverUrl, - bool requireExactMatch) - { - return LoadCachedCredentials(null, serverUrl, requireExactMatch); - } - - /// - /// Loads stored credentials for the specified server if found. If no credentials are found for the specified server and options then default credentials are returned. - /// This overload assumes that the credentials are to be stored under the TFS server's registry root - /// - /// An optional application name for isolated credential storage in the registry - /// The server location - /// A value indicating whether or not an exact or partial match of the server is required - /// A credentials object populated with stored credentials for the server if found - [EditorBrowsable(EditorBrowsableState.Never)] - public static VssCredentials LoadCachedCredentials( - string featureRegistryKeyword, - Uri serverUrl, - bool requireExactMatch) - { - ArgumentUtility.CheckForNull(serverUrl, "serverUrl"); - - bool uriKnownToCachedProvider = false; - VssCredentials cred = LoadCachedCredentialsFromRegisteredProviders(serverUrl, out uriKnownToCachedProvider); - - // If one of the registered credential providers had the target URI in its cache but failed to return a valid credential it means - // we should have had a cred but something went wrong (user canceled, user failed, auth source unavailable, etc.). In that case - // we Do Not want to carry on with the fallback to the VS registry/windows store credential caches. Even if that worked to get a - // credential it would put the user in a bad state (having an active, authenticated connection with an unexpected credential type). - if (cred == null && !uriKnownToCachedProvider) - { - WindowsCredential windowsCredential = null; - FederatedCredential federatedCredential = null; - CredentialsCacheManager credentialsCacheManager = new CredentialsCacheManager(); - TfsCredentialCacheEntry cacheEntry = credentialsCacheManager.GetCredentials(featureRegistryKeyword, serverUrl, requireExactMatch, null); - if (cacheEntry != null) - { - if (cacheEntry.NonInteractive) - { - switch (cacheEntry.Type) - { - case CachedCredentialsType.ServiceIdentity: - VssServiceIdentityToken initialToken = null; - string initialTokenValue = ReadAuthorizationToken(cacheEntry.Attributes); - if (!string.IsNullOrEmpty(initialTokenValue)) - { - initialToken = new VssServiceIdentityToken(initialTokenValue); - } - - // Initialize the issued token credential using the stored token if it exists - federatedCredential = new VssServiceIdentityCredential(cacheEntry.Credentials.UserName, - cacheEntry.Credentials.Password, - initialToken); - break; - - case CachedCredentialsType.Windows: - windowsCredential = new WindowsCredential(cacheEntry.Credentials); - break; - } - } - } - - cred = new VssCredentials(windowsCredential ?? new WindowsCredential(true), federatedCredential, CredentialPromptType.DoNotPrompt); - } - - return cred ?? new VssCredentials(new WindowsCredential(true), null, CredentialPromptType.DoNotPrompt); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static VssCredentials LoadCachedCredentialsFromRegisteredProviders(Uri serverUri, out bool knownUri) - { - LoadRegisteredCachedVssCredentialProviders(); - bool uriKnownByAnyProvider = false; - VssCredentials cred = null; - foreach (var pair in m_loadedCachedVssCredentialProviders) - { - bool uriKnownToProvider = false; - cred = pair.Value?.GetCachedCredentials(serverUri, out uriKnownToProvider); - if (cred != null || uriKnownToProvider) - { - uriKnownByAnyProvider |= uriKnownToProvider; - break; - } - } - knownUri = uriKnownByAnyProvider; - return cred; - } - - private static void LoadRegisteredCachedVssCredentialProviders() - { - CredentialsProviderRegistryHelper.LoadCachedVssCredentialProviders(ref m_loadedCachedVssCredentialProviders); - } - private static ConcurrentDictionary m_loadedCachedVssCredentialProviders = new ConcurrentDictionary(); -#endif - [EditorBrowsable(EditorBrowsableState.Never)] public static void WriteAuthorizationToken( string token, @@ -604,7 +394,6 @@ namespace GitHub.Services.Common private object m_thisLock; private CredentialPromptType m_promptType; private IssuedTokenProvider m_currentProvider; - protected WindowsCredential m_windowsCredential; protected FederatedCredential m_federatedCredential; private IVssCredentialStorage m_credentialStorage; } diff --git a/src/Sdk/Common/Common/Authentication/VssServiceIdentityCredential.cs b/src/Sdk/Common/Common/Authentication/VssServiceIdentityCredential.cs deleted file mode 100644 index 8b22a5616..000000000 --- a/src/Sdk/Common/Common/Authentication/VssServiceIdentityCredential.cs +++ /dev/null @@ -1,164 +0,0 @@ -using System; -using System.Globalization; -using System.Linq; -using System.Net; -using System.Net.Http; - -namespace GitHub.Services.Common -{ - /// - /// Provides federated authentication as a service identity with a Visual Studio Service. - /// - [Serializable] - public sealed class VssServiceIdentityCredential : FederatedCredential - { - /// - /// Initializes a new VssServiceIdentityCredential instance with the specified user name and password. - /// - /// The user name - /// The password - public VssServiceIdentityCredential( - string userName, - string password) - : this(userName, password, null) - { - } - - /// - /// Initializes a new VssServiceIdentityCredential instance with the specified user name and password. The - /// provided token, if not null, will be used before attempting authentication with the credentials. - /// - /// The user name - /// The password - /// An optional token which, if present, should be used before obtaining a new token - public VssServiceIdentityCredential( - string userName, - string password, - VssServiceIdentityToken initialToken) - : this(userName, password, initialToken, null) - { - } - - /// - /// Initializes a new VssServiceIdentityCredential instance with the specified access token. - /// - /// A token which may be used for authorization as the desired service identity - public VssServiceIdentityCredential(VssServiceIdentityToken token) - : this(null, null, token, null) - { - } - - /// - /// Initializes a new VssServiceIdentityCredential instance with the specified user name and password. The - /// provided token, if not null, will be used before attempting authentication with the credentials. - /// - /// The user name - /// The password - /// An optional token which, if present, should be used before obtaining a new token - /// An optional HttpMessageHandler which if passed will be passed along to the TokenProvider when executing OnCreateTokenProvider - public VssServiceIdentityCredential( - string userName, - string password, - VssServiceIdentityToken initialToken, - DelegatingHandler innerHandler) - : base(initialToken) - { - m_userName = userName; - m_password = password; - m_innerHandler = innerHandler; - } - - public override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.ServiceIdentity; - } - } - - /// - /// Gets the user name. - /// - public String UserName - { - get - { - return m_userName; - } - } - - /// - /// Gets the password. - /// - internal String Password - { - get - { - return m_password; - } - } - - public override bool IsAuthenticationChallenge(IHttpResponse webResponse) - { - if (webResponse == null) - { - return false; - } - - if (webResponse.StatusCode == HttpStatusCode.Found || - webResponse.StatusCode == HttpStatusCode.Redirect || - webResponse.StatusCode == HttpStatusCode.Unauthorized) - { - var authRealm = webResponse.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthRealm).FirstOrDefault(); - var authIssuer = webResponse.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthIssuer).FirstOrDefault(); - var wwwAuthenticate = webResponse.Headers.GetValues(Internal.HttpHeaders.WwwAuthenticate); - if (!String.IsNullOrEmpty(authIssuer) && !String.IsNullOrEmpty(authRealm)) - { - return webResponse.StatusCode != HttpStatusCode.Unauthorized || wwwAuthenticate.Any(x => x.StartsWith("TFS-Federated", StringComparison.OrdinalIgnoreCase)); - } - } - - return false; - } - - internal override string GetAuthenticationChallenge(IHttpResponse webResponse) - { - var authRealm = webResponse.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthRealm).FirstOrDefault(); - var authIssuer = webResponse.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthIssuer).FirstOrDefault(); - return string.Format(CultureInfo.InvariantCulture, "TFS-Federated realm={0}, issuer={1}", authRealm, authIssuer); - } - - /// - /// Creates a provider for retrieving security tokens for the provided credentials. - /// - /// An issued token provider for the current credential - protected override IssuedTokenProvider OnCreateTokenProvider( - Uri serverUrl, - IHttpResponse response) - { - // The response is only null when attempting to determine the most appropriate token provider to - // use for the connection. The only way we should do anything here is if we have an initial token - // since that means we can present something without making a server call. - if (response == null && base.InitialToken == null) - { - return null; - } - - Uri signInUrl = null; - String realm = string.Empty; - if (response != null) - { - realm = response.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthRealm).FirstOrDefault(); - signInUrl = new Uri(new Uri(response.Headers.GetValues(Internal.HttpHeaders.TfsFedAuthIssuer).FirstOrDefault()).GetLeftPart(UriPartial.Authority)); - } - - return new VssServiceIdentityTokenProvider(this, serverUrl, signInUrl, realm, m_innerHandler); - } - - private readonly String m_userName; - private readonly String m_password; - - [NonSerialized] - private readonly DelegatingHandler m_innerHandler = null; - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssServiceIdentityToken.cs b/src/Sdk/Common/Common/Authentication/VssServiceIdentityToken.cs deleted file mode 100644 index 8d102d06b..000000000 --- a/src/Sdk/Common/Common/Authentication/VssServiceIdentityToken.cs +++ /dev/null @@ -1,114 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using GitHub.Services.Common.Internal; - -namespace GitHub.Services.Common -{ - /// - /// Provides simple web token used for OAuth authentication. - /// - [Serializable] - public sealed class VssServiceIdentityToken : IssuedToken - { - /// - /// Initializes a new VssServiceIdentityToken instance with the specified token value. - /// - /// The token value as a string - public VssServiceIdentityToken(string token) - { - ArgumentUtility.CheckStringForNullOrEmpty(token, "token"); - - m_token = token; - //.ValidFrom = DateTime.UtcNow; - - // Read out the expiration time for the ValidTo field if we can find it - Dictionary nameValues; - if (TryGetNameValues(token, out nameValues)) - { - string expiresOnValue; - if (nameValues.TryGetValue(c_expiresName, out expiresOnValue)) - { - // The time is represented as standard epoch - // base.ValidTo = s_epoch.AddSeconds(Convert.ToUInt64(expiresOnValue, CultureInfo.CurrentCulture)); - } - } - } - - public String Token - { - get - { - return m_token; - } - } - - protected internal override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.ServiceIdentity; - } - } - - internal override void ApplyTo(IHttpRequest request) - { - request.Headers.SetValue(Internal.HttpHeaders.Authorization, "WRAP access_token=\"" + m_token + "\""); - } - - internal static VssServiceIdentityToken ExtractToken(string responseValue) - { - // Extract the actual token string - string token = UriUtility.UrlDecode(responseValue - .Split('&') - .Single(value => value.StartsWith("wrap_access_token=", StringComparison.OrdinalIgnoreCase)) - .Split('=')[1], VssHttpRequestSettings.Encoding); - - return new VssServiceIdentityToken(token); - } - - internal static bool TryGetNameValues( - string token, - out Dictionary tokenValues) - { - tokenValues = null; - - if (string.IsNullOrEmpty(token)) - { - return false; - } - - tokenValues = - token - .Split('&') - .Aggregate( - new Dictionary(), - (dict, rawNameValue) => - { - if (rawNameValue == string.Empty) - { - return dict; - } - - string[] nameValue = rawNameValue.Split('='); - - if (nameValue.Length != 2) - { - return dict; - } - - if (dict.ContainsKey(nameValue[0]) == true) - { - return dict; - } - - dict.Add(UriUtility.UrlDecode(nameValue[0]), UriUtility.UrlDecode(nameValue[1])); - return dict; - }); - return true; - } - - private string m_token; - private const string c_expiresName = "ExpiresOn"; - } -} diff --git a/src/Sdk/Common/Common/Authentication/VssServiceIdentityTokenProvider.cs b/src/Sdk/Common/Common/Authentication/VssServiceIdentityTokenProvider.cs deleted file mode 100644 index 2748afdc7..000000000 --- a/src/Sdk/Common/Common/Authentication/VssServiceIdentityTokenProvider.cs +++ /dev/null @@ -1,201 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Linq; -using System.Net; -using System.Net.Http; -using System.Threading; -using System.Threading.Tasks; -using GitHub.Services.Common.Diagnostics; -using GitHub.Services.Common.Internal; - -namespace GitHub.Services.Common -{ - internal sealed class VssServiceIdentityTokenProvider : IssuedTokenProvider - { - public VssServiceIdentityTokenProvider( - VssServiceIdentityCredential credential, - Uri serverUrl, - Uri signInUrl, - string realm, - DelegatingHandler innerHandler) - : this(credential, serverUrl, signInUrl, realm) - { - m_innerHandler = innerHandler; - } - - public VssServiceIdentityTokenProvider( - VssServiceIdentityCredential credential, - Uri serverUrl, - Uri signInUrl, - string realm) - : base(credential, serverUrl, signInUrl) - { - Realm = realm; - } - - protected override string AuthenticationParameter - { - get - { - if (string.IsNullOrEmpty(this.Realm) && this.SignInUrl == null) - { - return string.Empty; - } - else - { - return string.Format(CultureInfo.InvariantCulture, "issuer=\"{0}\", realm=\"{1}\"", this.SignInUrl, this.Realm); - } - } - } - - protected override String AuthenticationScheme - { - get - { - return "TFS-Federated"; - } - } - - /// - /// Gets the simple web token credential from which this provider was created. - /// - public new VssServiceIdentityCredential Credential - { - get - { - return (VssServiceIdentityCredential)base.Credential; - } - } - - /// - /// Gets a value indicating whether or not a call to get token will require interactivity. - /// - public override Boolean GetTokenIsInteractive - { - get - { - return false; - } - } - - /// - /// Gets the realm for the token provider. - /// - public String Realm - { - get; - } - - protected internal override bool IsAuthenticationChallenge(IHttpResponse webResponse) - { - if (!base.IsAuthenticationChallenge(webResponse)) - { - return false; - } - - // This means we were proactively constructed without any connection information. In this case - // we return false to ensure that a new provider is reconstructed with all appropriate configuration - // to retrieve a new token. - if (this.SignInUrl == null) - { - return false; - } - - string authRealm = webResponse.Headers.GetValues(HttpHeaders.TfsFedAuthRealm).FirstOrDefault(); - string authIssuer = webResponse.Headers.GetValues(HttpHeaders.TfsFedAuthIssuer).FirstOrDefault(); - Uri signInUrl = new Uri(new Uri(authIssuer).GetLeftPart(UriPartial.Authority), UriKind.Absolute); - - // Make sure that the values match our stored values. This way if the values change we will be thrown - // away and a new instance with correct values will be constructed. - return this.Realm.Equals(authRealm, StringComparison.OrdinalIgnoreCase) && - Uri.Compare(this.SignInUrl, signInUrl, UriComponents.AbsoluteUri, UriFormat.Unescaped, StringComparison.OrdinalIgnoreCase) == 0; - } - - /// - /// Issues a request to synchronously retrieve a token for the associated credential. - /// - /// - /// - /// - protected override async Task OnGetTokenAsync( - IssuedToken failedToken, - CancellationToken cancellationToken) - { - if (string.IsNullOrEmpty(this.Credential.UserName) || - string.IsNullOrEmpty(this.Credential.Password)) - { - return null; - } - - VssTraceActivity traceActivity = VssTraceActivity.Current; - using (HttpClient client = new HttpClient(CreateMessageHandler(), false)) - { - client.BaseAddress = this.SignInUrl; - - KeyValuePair[] values = new KeyValuePair[] - { - new KeyValuePair("wrap_name", this.Credential.UserName), - new KeyValuePair("wrap_password", this.Credential.Password), - new KeyValuePair("wrap_scope", this.Realm), - }; - - Uri url = new Uri("WRAPv0.9/", UriKind.Relative); - FormUrlEncodedContent content = new FormUrlEncodedContent(values); - using (HttpResponseMessage response = await client.PostAsync(url, content, cancellationToken).ConfigureAwait(false)) - { - string responseValue = await response.Content.ReadAsStringAsync().ConfigureAwait(false); - if (response.IsSuccessStatusCode) - { - return VssServiceIdentityToken.ExtractToken(responseValue); - } - else - { - VssHttpEventSource.Log.AuthenticationError(traceActivity, this, responseValue); - return null; - } - } - } - } - - private HttpMessageHandler CreateMessageHandler() - { - var retryOptions = new VssHttpRetryOptions() - { - RetryableStatusCodes = - { - VssNetworkHelper.TooManyRequests, - HttpStatusCode.InternalServerError, - }, - }; - - HttpMessageHandler innerHandler; - - if (m_innerHandler != null) - { - if (m_innerHandler.InnerHandler == null) - { - m_innerHandler.InnerHandler = new HttpClientHandler(); - } - - innerHandler = m_innerHandler; - } - else - { - innerHandler = new HttpClientHandler(); - } - - // Inherit proxy setting from VssHttpMessageHandler - var httpClientHandler = innerHandler as HttpClientHandler; - if (httpClientHandler != null && VssHttpMessageHandler.DefaultWebProxy != null) - { - httpClientHandler.Proxy = VssHttpMessageHandler.DefaultWebProxy; - httpClientHandler.UseProxy = true; - } - - return new VssHttpRetryMessageHandler(retryOptions, innerHandler); - } - - private DelegatingHandler m_innerHandler = null; - } -} diff --git a/src/Sdk/Common/Common/Authentication/WindowsCredential.cs b/src/Sdk/Common/Common/Authentication/WindowsCredential.cs deleted file mode 100644 index e42bec581..000000000 --- a/src/Sdk/Common/Common/Authentication/WindowsCredential.cs +++ /dev/null @@ -1,137 +0,0 @@ -using System; -using System.Linq; -using System.Net; - -namespace GitHub.Services.Common -{ - /// - /// Provides a credential for windows authentication against a Visual Studio Service. - /// - public sealed class WindowsCredential : IssuedTokenCredential - { - /// - /// Initializes a new WindowsCredential instance using a default user interface provider implementation - /// and the default network credentials. - /// - public WindowsCredential() - : this(true) - { - } - - /// - /// Initializes a new WindowsCredential instance using a default user interface provider implementation - /// and the default network credentials, if specified. - /// - /// True if the default credentials should be used; otherwise, false - public WindowsCredential(bool useDefaultCredentials) - : this(useDefaultCredentials ? CredentialCache.DefaultCredentials : null) - { - UseDefaultCredentials = useDefaultCredentials; - } - - /// - /// Initializes a new WindowsCredential instance using a default user interface provider implementation - /// and the specified network credentials. - /// - /// The windows credentials which should be used for authentication - public WindowsCredential(ICredentials credentials) - : this(null) - { - m_credentials = credentials; - UseDefaultCredentials = credentials == CredentialCache.DefaultCredentials; - } - - /// - /// Initializes a new WindowsCredential instance using the specified initial token. - /// - /// An optional token which, if present, should be used before obtaining a new token - public WindowsCredential(WindowsToken initialToken) - : base(initialToken) - { - } - - /// - /// Gets the credentials associated with this windows credential. - /// - public ICredentials Credentials - { - get - { - return m_credentials; - } - set - { - m_credentials = value; - UseDefaultCredentials = Credentials == CredentialCache.DefaultCredentials; - } - } - - public override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Windows; - } - } - - /// - /// Gets a value indicating what value was passed to WindowsCredential(bool useDefaultCredentials) constructor - /// - public Boolean UseDefaultCredentials - { - get; - private set; - } - - public override Boolean IsAuthenticationChallenge(IHttpResponse webResponse) - { - if (webResponse == null) - { - return false; - } - - if (webResponse.StatusCode == HttpStatusCode.Unauthorized && - webResponse.Headers.GetValues(Internal.HttpHeaders.WwwAuthenticate).Any(x => AuthenticationSchemeValid(x))) - { - return true; - } - - if (webResponse.StatusCode == HttpStatusCode.ProxyAuthenticationRequired && - webResponse.Headers.GetValues(Internal.HttpHeaders.ProxyAuthenticate).Any(x => AuthenticationSchemeValid(x))) - { - return true; - } - - return false; - } - - protected override IssuedTokenProvider OnCreateTokenProvider( - Uri serverUrl, - IHttpResponse response) - { - // If we have no idea what kind of credentials we are supposed to be using, don't play a windows token on - // the first request. - if (response == null) - { - return null; - } - - if (m_credentials != null) - { - this.InitialToken = new WindowsToken(m_credentials); - } - - return new WindowsTokenProvider(this, serverUrl); - } - - private static Boolean AuthenticationSchemeValid(String authenticateHeader) - { - return authenticateHeader.StartsWith("Basic", StringComparison.OrdinalIgnoreCase) || - authenticateHeader.StartsWith("Digest", StringComparison.OrdinalIgnoreCase) || - authenticateHeader.StartsWith("Negotiate", StringComparison.OrdinalIgnoreCase) || - authenticateHeader.StartsWith("Ntlm", StringComparison.OrdinalIgnoreCase); - } - - private ICredentials m_credentials; - } -} diff --git a/src/Sdk/Common/Common/Authentication/WindowsToken.cs b/src/Sdk/Common/Common/Authentication/WindowsToken.cs deleted file mode 100644 index 70d79eba3..000000000 --- a/src/Sdk/Common/Common/Authentication/WindowsToken.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System; -using System.Net; - -namespace GitHub.Services.Common -{ - public sealed class WindowsToken : IssuedToken, ICredentials - { - internal WindowsToken(ICredentials credentials) - { - this.Credentials = credentials; - } - - public ICredentials Credentials - { - get; - } - - protected internal override VssCredentialsType CredentialType - { - get - { - return VssCredentialsType.Windows; - } - } - - internal override void ApplyTo(IHttpRequest request) - { - // Special-cased by the caller because we implement ICredentials - throw new InvalidOperationException(); - } - - NetworkCredential ICredentials.GetCredential( - Uri uri, - String authType) - { - return this.Credentials?.GetCredential(uri, authType); - } - } -} diff --git a/src/Sdk/Common/Common/Authentication/WindowsTokenProvider.cs b/src/Sdk/Common/Common/Authentication/WindowsTokenProvider.cs deleted file mode 100644 index 4725de22b..000000000 --- a/src/Sdk/Common/Common/Authentication/WindowsTokenProvider.cs +++ /dev/null @@ -1,40 +0,0 @@ -using System; -using System.Globalization; -using System.Net; - -namespace GitHub.Services.Common -{ - internal sealed class WindowsTokenProvider : IssuedTokenProvider - { - public WindowsTokenProvider( - WindowsCredential credential, - Uri serverUrl) - : base(credential, serverUrl, serverUrl) - { - } - - protected override String AuthenticationScheme - { - get - { - return String.Format(CultureInfo.InvariantCulture, "{0} {1} {2} {3}", AuthenticationSchemes.Negotiate, AuthenticationSchemes.Ntlm, AuthenticationSchemes.Digest, AuthenticationSchemes.Basic); - } - } - - public new WindowsCredential Credential - { - get - { - return (WindowsCredential)base.Credential; - } - } - - public override Boolean GetTokenIsInteractive - { - get - { - return base.CurrentToken == null; - } - } - } -} diff --git a/src/Sdk/Common/Common/Diagnostics/VssHttpEventSource.cs b/src/Sdk/Common/Common/Diagnostics/VssHttpEventSource.cs index ee267cd60..69aa929a6 100644 --- a/src/Sdk/Common/Common/Diagnostics/VssHttpEventSource.cs +++ b/src/Sdk/Common/Common/Diagnostics/VssHttpEventSource.cs @@ -5,9 +5,6 @@ using System.Globalization; using System.Net; using System.Net.Http; using System.Net.Sockets; -#if !NETSTANDARD -using System.Diagnostics.Eventing; -#endif namespace GitHub.Services.Common.Diagnostics { @@ -838,13 +835,6 @@ namespace GitHub.Services.Common.Diagnostics [NonEvent] private void SetActivityId(VssTraceActivity activity) { -#if !NETSTANDARD - if (activity != null) - { - Guid activityId = activity.Id; - EventProvider.SetActivityId(ref activityId); - } -#endif } [NonEvent] @@ -876,15 +866,6 @@ namespace GitHub.Services.Common.Diagnostics Action writeEvent) { writeEvent(param0, message); -#if !NETSTANDARD - if (EventProvider.GetLastWriteEventError() == EventProvider.WriteEventErrorCode.EventTooBig) - { - foreach (String messagePart in SplitMessage(message)) - { - writeEvent(param0, messagePart); - } - } -#endif } [NonEvent] @@ -895,15 +876,6 @@ namespace GitHub.Services.Common.Diagnostics Action writeEvent) { writeEvent(param0, param1, message); -#if !NETSTANDARD - if (EventProvider.GetLastWriteEventError() == EventProvider.WriteEventErrorCode.EventTooBig) - { - foreach (String messagePart in SplitMessage(message)) - { - writeEvent(param0, param1, messagePart); - } - } -#endif } [NonEvent] @@ -914,23 +886,10 @@ namespace GitHub.Services.Common.Diagnostics Action writeEvent) { writeEvent(param0, param1, message); -#if !NETSTANDARD - if (EventProvider.GetLastWriteEventError() == EventProvider.WriteEventErrorCode.EventTooBig) - { - foreach (String messagePart in SplitMessage(message)) - { - writeEvent(param0, param1, messagePart); - } - } -#endif } [NonEvent] -#if !NETSTANDARD - private unsafe void WriteEvent( -#else private new unsafe void WriteEvent( -#endif Int32 eventId, Int32 param0, String param1) diff --git a/src/Sdk/Common/Common/Diagnostics/VssTraceActivity.cs b/src/Sdk/Common/Common/Diagnostics/VssTraceActivity.cs index b222f1a2f..291b6d05a 100644 --- a/src/Sdk/Common/Common/Diagnostics/VssTraceActivity.cs +++ b/src/Sdk/Common/Common/Diagnostics/VssTraceActivity.cs @@ -1,8 +1,5 @@ using System; using System.Diagnostics; -#if !NETSTANDARD -using System.Runtime.Remoting.Messaging; -#endif using System.Runtime.Serialization; namespace GitHub.Services.Common.Diagnostics @@ -38,22 +35,11 @@ namespace GitHub.Services.Common.Diagnostics /// public static VssTraceActivity Current { -#if !NETSTANDARD - get - { - return CallContext.LogicalGetData(VssTraceActivity.PropertyName) as VssTraceActivity; - } - private set - { - CallContext.LogicalSetData(VssTraceActivity.PropertyName, value); - } -#else get { return null; } set { } -#endif } /// diff --git a/src/Sdk/Common/Common/Utility/HttpHeaders.cs b/src/Sdk/Common/Common/Utility/HttpHeaders.cs index e91d0f28a..892fcd270 100644 --- a/src/Sdk/Common/Common/Utility/HttpHeaders.cs +++ b/src/Sdk/Common/Common/Utility/HttpHeaders.cs @@ -8,84 +8,28 @@ namespace GitHub.Services.Common.Internal public static class HttpHeaders { public const String ActivityId = "ActivityId"; - public const String ETag = "ETag"; - public const String TfsVersion = "X-TFS-Version"; - public const String TfsRedirect = "X-TFS-Redirect"; - public const String TfsException = "X-TFS-Exception"; public const String TfsServiceError = "X-TFS-ServiceError"; public const String TfsSessionHeader = "X-TFS-Session"; - public const String TfsSoapException = "X-TFS-SoapException"; public const String TfsFedAuthRealm = "X-TFS-FedAuthRealm"; public const String TfsFedAuthIssuer = "X-TFS-FedAuthIssuer"; public const String TfsFedAuthRedirect = "X-TFS-FedAuthRedirect"; - public const String VssAuthorizationEndpoint = "X-VSS-AuthorizationEndpoint"; - public const String VssPageHandlers = "X-VSS-PageHandlers"; public const String VssE2EID = "X-VSS-E2EID"; - public const String VssOrchestrationId = "X-VSS-OrchestrationId"; - public const String AuditCorrelationId = "X-VSS-Audit-CorrelationId"; - public const String VssOriginUserAgent = "X-VSS-OriginUserAgent"; - // Internal Headers that we use in our client. - public const string TfsInstanceHeader = "X-TFS-Instance"; - public const string TfsVersionOneHeader = "X-VersionControl-Instance"; - - [SuppressMessage("Microsoft.Naming", "CA1704:IdentifiersShouldBeSpelledCorrectly", MessageId = "Tfs")] - public const string TfsImpersonate = "X-TFS-Impersonate"; - public const string TfsSubjectDescriptorImpersonate = "X-TFS-SubjectDescriptorImpersonate"; - - public const string MsContinuationToken = "X-MS-ContinuationToken"; public const String VssUserData = "X-VSS-UserData"; public const String VssAgentHeader = "X-VSS-Agent"; public const String VssAuthenticateError = "X-VSS-AuthenticateError"; - public const string VssReauthenticationAction = "X-VSS-ReauthenticationAction"; - public const string RequestedWith = "X-Requested-With"; - public const String VssRateLimitResource = "X-RateLimit-Resource"; public const String VssRateLimitDelay = "X-RateLimit-Delay"; - public const String VssRateLimitLimit = "X-RateLimit-Limit"; - public const String VssRateLimitRemaining = "X-RateLimit-Remaining"; public const String VssRateLimitReset = "X-RateLimit-Reset"; - public const String RetryAfter = "Retry-After"; - - public const String VssGlobalMessage = "X-VSS-GlobalMessage"; - - public const String VssRequestRouted = "X-VSS-RequestRouted"; - public const String VssUseRequestRouting = "X-VSS-UseRequestRouting"; - - public const string VssResourceTenant = "X-VSS-ResourceTenant"; - public const String VssOverridePrompt = "X-VSS-OverridePrompt"; - - public const String VssOAuthS2STargetService = "X-VSS-S2STargetService"; + public const String VssHostOfflineError = "X-VSS-HostOfflineError"; - public const string VssForceMsaPassThrough = "X-VSS-ForceMsaPassThrough"; public const string VssRequestPriority = "X-VSS-RequestPriority"; - // This header represents set of ';' delimited mappings (usually one) that are considered by DetermineAccessMapping API - public const string VssClientAccessMapping = "X-VSS-ClientAccessMapping"; - - // This header is used to download artifacts anonymously. - // N.B. Some resources secured with download tickets (e.g. TFVC files) are still retrieved with the download - // ticket in the query string. - public const string VssDownloadTicket = "X-VSS-DownloadTicket"; - - public const string IfModifiedSince = "If-Modified-Since"; public const string Authorization = "Authorization"; - public const string Location = "Location"; public const string ProxyAuthenticate = "Proxy-Authenticate"; public const string WwwAuthenticate = "WWW-Authenticate"; - public const string AfdIncomingRouteKey = "X-FD-RouteKey"; - public const string AfdOutgoingRouteKey = "X-AS-RouteKey"; - public const string AfdIncomingEndpointList = "X-FD-RouteKeyApplicationEndpointList"; - public const string AfdOutgoingEndpointList = "X-AS-RouteKeyApplicationEndpointList"; public const string AfdResponseRef = "X-MSEdge-Ref"; - public const string AfdIncomingClientIp = "X-FD-ClientIP"; - public const string AfdIncomingSocketIp = "X-FD-SocketIP"; - public const string AfdIncomingRef = "X-FD-Ref"; - public const string AfdIncomingEventId = "X-FD-EventId"; - public const string AfdIncomingEdgeEnvironment = "X-FD-EdgeEnvironment"; - public const string AfdOutgoingQualityOfResponse = "X-AS-QualityOfResponse"; - public const string AfdOutgoingClientIp = "X-MSEdge-ClientIP"; } } diff --git a/src/Sdk/Common/Common/Utility/LongPathUtility.cs b/src/Sdk/Common/Common/Utility/LongPathUtility.cs deleted file mode 100644 index f179bbe9b..000000000 --- a/src/Sdk/Common/Common/Utility/LongPathUtility.cs +++ /dev/null @@ -1,553 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Diagnostics.CodeAnalysis; -using System.Globalization; -using System.IO; -using System.Linq; -using System.Runtime.ConstrainedExecution; -using System.Runtime.InteropServices; -using System.Text; -using System.Text.RegularExpressions; -using System.Threading.Tasks; - -namespace GitHub.Services.Common -{ - /// - /// Provides path normalization/expansion for absolute, relative and UNC-style paths - /// and supports paths that contain more than 248 characters. - /// - /// - /// This utility class can be used in place of the .NET Path and Directory classes - /// that throw System.IO.PathTooLongException when paths are longer than 248 characters - /// - public static class LongPathUtility - { - private static Regex AbsolutePathRegEx = new Regex(@"^([a-zA-Z]:\\|\\\\)", RegexOptions.CultureInvariant | RegexOptions.Compiled); - private const int ERROR_FILE_NOT_FOUND = 2; - - /// - /// Returns a list of directory names under the path specified, and optionally all subdirectories - /// - /// The directory to search - /// Specifies whether the search operation should include only the currect directory or all subdirectories - /// A list of all subdirectories - public static IEnumerable EnumerateDirectories(string path, bool recursiveSearch) - { - var directoryPaths = new List(); - EnumerateDirectoriesInternal(directoryPaths, path, recursiveSearch); - return directoryPaths; - } - - /// - /// Returns a list of file names under the path specified, and optionally within all subdirectories. - /// - /// The directory to search - /// Specifies whether the search operation should include only the current directory or all subdirectories - /// - /// A list of full file names(including path) contained in the directory specified that match the specified search pattern. - public static IEnumerable EnumerateFiles(string path, bool recursiveSearch) - { - return EnumerateFiles(path, "*", recursiveSearch); - } - - /// - /// Returns an enumerable collection of file names that match a search pattern in a specified path, - /// and optionally searches subdirectories. - /// - /// The directory to search - /// The search string to match against the names of the files - /// Specifies whether the search operation should include only the current directory or all subdirectories - /// - /// A list of full file names(including path) contained in the directory specified (and subdirectories optionally) that match the specified pattern. - /// - public static IEnumerable EnumerateFiles(string path, string matchPattern, bool recursiveSearch) - { - if (!DirectoryExists(path)) - { - throw new DirectoryNotFoundException($"The path '{path}' is not a valid directory."); - } - - var filePaths = new List(); - EnumerateFilesInternal(filePaths, path, matchPattern, recursiveSearch); - return filePaths; - } - - /// - /// Returns true/false whether the file exists. This method inspects the - /// file system attributes and supports files without extensions (ex: DIRS, Sources). This method - /// supports file paths that are longer than 260 characters. - /// - /// The file path to inspect - /// - /// True if the file exists or false if not - /// - public static bool FileExists(string filePath) - { - return FileOrDirectoryExists(filePath, isDirectory: false); - } - - /// - /// Returns true/false whether the directory exists. This method inspects the - /// file system attributes and supports files without extensions (ex: DIRS, Sources). This method - /// supports file paths that are longer than 260 characters. - /// - /// The file path to inspect - /// - /// True if the directory exists or false if not - /// - public static bool DirectoryExists(string directoryPath) - { - return FileOrDirectoryExists(directoryPath, isDirectory: true); - } - - private static bool FileOrDirectoryExists(string filePath, bool isDirectory) - { - if (String.IsNullOrWhiteSpace(filePath)) - { - throw new ArgumentException("A path to the file is required and cannot be null, empty or whitespace", "filePath"); - } - - bool pathExists = false; - - // File names may or may not include an extension (ex: DIRS, Sources). We have to look at the attributes - // on the file system object in order to distinguish a directory from a file - var attributes = (FlagsAndAttributes)NativeMethods.GetFileAttributes(filePath); - - if (attributes != FlagsAndAttributes.InvalidFileAttributes) - { - bool pathIsDirectory = (attributes & FlagsAndAttributes.Directory) == FlagsAndAttributes.Directory; - - if (pathIsDirectory == isDirectory) - { - pathExists = true; - } - } - - return pathExists; - } - - /// - /// Returns the fully expanded/normalized path. This method supports paths that are - /// longer than 248 characters. - /// - /// The file or directory path - /// - public static string GetFullNormalizedPath(string path) - { - if (String.IsNullOrWhiteSpace(path)) - { - throw new ArgumentException("A path is required and cannot be null, empty or whitespace", "path"); - } - - string outPath = path; - - // We need the length of the absolute path in order to prepare a buffer of - // the correct size - uint bufferSize = NativeMethods.GetFullPathName(path, 0, null, null); - int lastWin32Error = Marshal.GetLastWin32Error(); - - if (bufferSize > 0) - { - var absolutePath = new StringBuilder((int)bufferSize); - uint length = NativeMethods.GetFullPathName(path, bufferSize, absolutePath, null); - lastWin32Error = Marshal.GetLastWin32Error(); - - if (length > 0) - { - outPath = absolutePath.ToString(); - } - else - { - // Path resolution failed - throw new Win32Exception( - lastWin32Error, - String.Format( - CultureInfo.InvariantCulture, - "Path normalization/expansion failed. The path length was not returned by the Kernel32 subsystem for '{0}'.", - path - ) - ); - } - } - else - { - // Path resolution failed and the path length could not - // be determined - throw new Win32Exception( - lastWin32Error, - String.Format( - CultureInfo.InvariantCulture, - "Path normalization/expansion failed. A full path was not returned by the Kernel32 subsystem for '{0}'.", - path - ) - ); - } - - return outPath != null ? outPath.TrimEnd('\\') : null; - } - - /// - /// Determines whether the specified path is an absolute path or not. - /// - /// The path to be tested. - /// - /// true if the path is absolute; otherwise, false. - /// - public static bool IsAbsolutePath(string path) - { - return LongPathUtility.AbsolutePathRegEx.Match(path).Success; - } - - public static string RemoveExtendedLengthPathPrefix(string inPath) - { - string outPath = inPath; - - if (!String.IsNullOrWhiteSpace(inPath)) - { - if (inPath.StartsWith("\\", StringComparison.OrdinalIgnoreCase)) - { - // ex: \\?\UNC\server\share to \\server\share - outPath = inPath.Replace(@"\\?\UNC", @"\"); - - // ex: \\?\c:\windows to c:\windows - outPath = outPath.Replace(@"\\?\", String.Empty); - } - } - - return outPath; - } - - private static string CombinePaths(string pathA, string pathB) - { - if (pathA == null) - { - throw new ArgumentNullException("pathA"); - } - - if (pathB == null) - { - throw new ArgumentNullException("pathB"); - } - - // The Path class does not suffer from the 248/260 character limitation - // that the File and Directory classes do. - return Path.Combine( - pathA.TrimEnd('\\'), - pathB.TrimStart('\\') - ); - } - - private static string ConvertToExtendedLengthPath(string path) - { - string extendedLengthPath = GetFullNormalizedPath(path); - - if (!String.IsNullOrWhiteSpace(extendedLengthPath)) - { - //no need to modify- it's already unicode - if (!extendedLengthPath.StartsWith(@"\\?", StringComparison.OrdinalIgnoreCase)) - { - // ex: \\server\share - if (extendedLengthPath.StartsWith(@"\\", StringComparison.OrdinalIgnoreCase)) - { - // make it \\?\UNC\server\share - extendedLengthPath = String.Format( - CultureInfo.InvariantCulture, - @"\\?\UNC{0}", - extendedLengthPath.Substring(1) - ); - } - else //not unicode already, and not UNC - { - extendedLengthPath = String.Format( - CultureInfo.InvariantCulture, - @"\\?\{0}", - extendedLengthPath - ); - } - } - } - - return extendedLengthPath; - } - - private static IEnumerable EnumerateDirectoriesInPath(string path) - { - SafeFindHandle handle = null; - var findData = new FindData(); - var childDirectories = new List(); - - using (handle = NativeMethods.FindFirstFile(CombinePaths(ConvertToExtendedLengthPath(path), "*"), findData)) - { - if (!handle.IsInvalid) - { - bool searchComplete = false; - - do - { - // skip the dot directories - if (!findData.fileName.Equals(@".") && !findData.fileName.Equals(@"..")) - { - if ((findData.fileAttributes & (int)FileAttributes.Directory) != 0) - { - childDirectories.Add(RemoveExtendedLengthPathPrefix(CombinePaths(path, findData.fileName))); - } - } - - if (NativeMethods.FindNextFile(handle, findData)) - { - if (handle.IsInvalid) - { - throw new Win32Exception( - Marshal.GetLastWin32Error(), - String.Format( - CultureInfo.InvariantCulture, - "Enumerating subdirectories for path '{0}' failed.", - path - ) - ); - } - } - else - { - searchComplete = true; - } - - } while (!searchComplete); - } - } - - return childDirectories; - } - - private static IEnumerable EnumerateFilesInPath(string path, string matchPattern) - { - SafeFindHandle handle = null; - var findData = new FindData(); - var fullFilePaths = new List(); - - using (handle = NativeMethods.FindFirstFile(CombinePaths(ConvertToExtendedLengthPath(path), matchPattern), findData)) - { - int lastWin32Error = Marshal.GetLastWin32Error(); - - if (handle.IsInvalid) - { - if (lastWin32Error != ERROR_FILE_NOT_FOUND) - { - throw new Win32Exception( - lastWin32Error, - String.Format(CultureInfo.InvariantCulture, "Enumerating files for path '{0}' failed.", path) - ); - } - } - else - { - bool searchComplete = false; - - do - { - // skip the dot directories - if (!findData.fileName.Equals(@".") && !findData.fileName.Equals(@"..")) - { - if ((findData.fileAttributes & (int)FileAttributes.Directory) == 0) - { - fullFilePaths.Add(RemoveExtendedLengthPathPrefix(CombinePaths(path, findData.fileName))); - } - } - - if (NativeMethods.FindNextFile(handle, findData)) - { - lastWin32Error = Marshal.GetLastWin32Error(); - - if (handle.IsInvalid) - { - throw new Win32Exception( - lastWin32Error, - String.Format( - CultureInfo.InvariantCulture, - "Enumerating subdirectories for path '{0}' failed.", - path - ) - ); - } - } - else - { - searchComplete = true; - } - - } while (!searchComplete); - } - } - - return fullFilePaths; - } - - private static void EnumerateFilesInternal(List filePaths, string path, string matchPattern, bool recursiveSearch) - { - var fullFilePaths = EnumerateFilesInPath(path, matchPattern); - if (fullFilePaths.Any()) - { - lock (filePaths) - { - filePaths.AddRange(fullFilePaths); - } - } - - if (recursiveSearch) - { - var directorySearchPaths = EnumerateDirectoriesInPath(path); - if (directorySearchPaths.Any()) - { - Parallel.ForEach( - directorySearchPaths, - (searchPath) => - { - EnumerateFilesInternal(filePaths, searchPath, matchPattern, recursiveSearch); - } - ); - } - } - } - - public static void EnumerateDirectoriesInternal(List directoryPaths, string path, bool recursiveSearch) - { - var directorySearchPaths = EnumerateDirectoriesInPath(path); - if (directorySearchPaths.Any()) - { - lock (directoryPaths) - { - directoryPaths.AddRange(directorySearchPaths); - } - - if (recursiveSearch) - { - // This will not ensure that the directory paths are added to the list - // in alphabetical order but does provide performance 2 - 4 times better than the - // canonical Directory.GetDirectories() method. - Parallel.ForEach( - directorySearchPaths, - (searchPath) => - { - EnumerateDirectoriesInternal(directoryPaths, searchPath, recursiveSearch); - } - ); - } - } - } - - /// - /// Kernel32.dll native interop methods for use with utility file/path parsing - /// operations - /// - private static class NativeMethods - { - private const string Kernel32Dll = "kernel32.dll"; - - [DllImport(Kernel32Dll, CharSet = CharSet.Unicode, BestFitMapping = false, ThrowOnUnmappableChar = true)] - [return: MarshalAs(UnmanagedType.Bool)] - public static extern bool FindClose(IntPtr hFindFile); - - [SuppressMessage("Microsoft.Globalization", "CA2101:SpecifyMarshalingForPInvokeStringArguments", MessageId = "FindData.alternateFileName")] - [SuppressMessage("Microsoft.Globalization", "CA2101:SpecifyMarshalingForPInvokeStringArguments", MessageId = "FindData.fileName")] - [DllImport(Kernel32Dll, CharSet = CharSet.Unicode, BestFitMapping = false, ThrowOnUnmappableChar = true, SetLastError = true)] - public static extern SafeFindHandle FindFirstFile( - [MarshalAs(UnmanagedType.LPTStr)] - string fileName, - [In, Out] FindData findFileData - ); - [SuppressMessage("Microsoft.Globalization", "CA2101:SpecifyMarshalingForPInvokeStringArguments", MessageId = "FindData.alternateFileName")] - [SuppressMessage("Microsoft.Globalization", "CA2101:SpecifyMarshalingForPInvokeStringArguments", MessageId = "FindData.fileName")] - [DllImport(Kernel32Dll, CharSet = CharSet.Unicode, BestFitMapping = false, ThrowOnUnmappableChar = true, SetLastError = true)] - [return: MarshalAs(UnmanagedType.Bool)] - public static extern bool FindNextFile(SafeFindHandle hFindFile, [In, Out] FindData lpFindFileData); - - [DllImport(Kernel32Dll, CharSet = CharSet.Unicode, BestFitMapping = false, ThrowOnUnmappableChar = true, SetLastError = true)] - public static extern int GetFileAttributes(string lpFileName); - - [DllImport(Kernel32Dll, CharSet = CharSet.Unicode, BestFitMapping = false, ThrowOnUnmappableChar = true, SetLastError = true)] - public static extern uint GetFullPathName( - [MarshalAs(UnmanagedType.LPTStr)] - string lpFileName, - uint nBufferLength, - [Out] - StringBuilder lpBuffer, - StringBuilder lpFilePart - ); - } - - //for mapping to the WIN32_FIND_DATA native structure - [SuppressMessage("StyleCop.CSharp.NamingRules", "SA1307:AccessibleFieldsMustBeginWithUpperCaseLetter", Justification = "Reviewed.")] - [SuppressMessage("StyleCop.CSharp.MaintainabilityRules", "SA1401:FieldsMustBePrivate", Justification = "Reviewed.")] - [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)] - private sealed class FindData - { - // NOTE: - // Although it may seem correct to Marshal the string members of this class as UnmanagedType.LPWStr, they - // must explicitly remain UnmanagedType.ByValTStr with the size constraints noted. Otherwise we end up with - // COM Interop exceptions while trying to marshal the data across the PInvoke boundaries. We thus require the StyleCop - // suppressions on the NativeMethods.FindNextFile() method above. - public int fileAttributes; - public System.Runtime.InteropServices.ComTypes.FILETIME creationTime; - public System.Runtime.InteropServices.ComTypes.FILETIME lastAccessTime; - public System.Runtime.InteropServices.ComTypes.FILETIME lastWriteTime; - public int nFileSizeHigh; - public int nFileSizeLow; - public int dwReserved0; - public int dwReserved1; - [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 260)] - public string fileName; - [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 14)] - public string alternateFileName; - } - - //A Win32 safe find handle in which a return value of -1 indicates it's invalid - private sealed class SafeFindHandle : Microsoft.Win32.SafeHandles.SafeHandleMinusOneIsInvalid - { - public SafeFindHandle() - : base(true) - { - return; - } - - [ReliabilityContract(Consistency.WillNotCorruptState, Cer.Success)] - protected override bool ReleaseHandle() - { - return NativeMethods.FindClose(handle); - } - } - - [Flags] - private enum FlagsAndAttributes : uint - { - None = 0x00000000, - Readonly = 0x00000001, - Hidden = 0x00000002, - System = 0x00000004, - Directory = 0x00000010, - Archive = 0x00000020, - Device = 0x00000040, - Normal = 0x00000080, - Temporary = 0x00000100, - SparseFile = 0x00000200, - ReparsePoint = 0x00000400, - Compressed = 0x00000800, - Offline = 0x00001000, - NotContentIndexed = 0x00002000, - Encrypted = 0x00004000, - Write_Through = 0x80000000, - Overlapped = 0x40000000, - NoBuffering = 0x20000000, - RandomAccess = 0x10000000, - SequentialScan = 0x08000000, - DeleteOnClose = 0x04000000, - BackupSemantics = 0x02000000, - PosixSemantics = 0x01000000, - OpenReparsePoint = 0x00200000, - OpenNoRecall = 0x00100000, - FirstPipeInstance = 0x00080000, - - InvalidFileAttributes = 0xFFFFFFFF // Returned by GetFileAttributes on Non existant path - } - } -} diff --git a/src/Sdk/Common/Common/Utility/TypeExtensionMethods.cs b/src/Sdk/Common/Common/Utility/TypeExtensionMethods.cs index f1c68fbdf..4483b141f 100644 --- a/src/Sdk/Common/Common/Utility/TypeExtensionMethods.cs +++ b/src/Sdk/Common/Common/Utility/TypeExtensionMethods.cs @@ -218,7 +218,6 @@ namespace GitHub.Services.Common } } -#if NETSTANDARD /// /// Portable compliant way to get a constructor with specified arguments. This will return a constructor that is public or private as long as the arguments match. NULL will be returned if there is no match. /// Note that it will pick the first one it finds that matches, which is not necesarily the best match. @@ -263,7 +262,6 @@ namespace GitHub.Services.Common } return null; } -#endif private static PropertyInfo GetPublicInstancePropertyInfo(Type type, string name) { diff --git a/src/Sdk/Common/Common/Utility/VssStringComparer.cs b/src/Sdk/Common/Common/Utility/VssStringComparer.cs index c156da962..b08ffb68d 100644 --- a/src/Sdk/Common/Common/Utility/VssStringComparer.cs +++ b/src/Sdk/Common/Common/Utility/VssStringComparer.cs @@ -1,18 +1,4 @@ -// ************************************************************************************************ -// Microsoft Team Foundation -// -// Microsoft Confidential -// Copyright (c) Microsoft Corporation. All rights reserved. -// -// File: VssStringComparer.cs -// Area: Team Foundation -// Classes: VssStringComparer -// Contents: The Team Foundation string comparison class provides inner classes -// that are used to provide semantic-specific Equals and Compare methods -// and a semantic-specific StringComparer instance. New semantics should -// be added on an as-needed basis. -// ************************************************************************************************ -using System; +using System; using System.Diagnostics; namespace GitHub.Services.Common diff --git a/src/Sdk/Common/Common/Utility/XmlUtility.cs b/src/Sdk/Common/Common/Utility/XmlUtility.cs index 0c66b3a92..a6ef0bda7 100644 --- a/src/Sdk/Common/Common/Utility/XmlUtility.cs +++ b/src/Sdk/Common/Common/Utility/XmlUtility.cs @@ -13,9 +13,6 @@ namespace GitHub.Services.Common.Internal { [EditorBrowsable(EditorBrowsableState.Never)] -#if !NETSTANDARD - [CLSCompliant(false)] -#endif public static class XmlUtility { internal static FileStream OpenFile(String path, FileShare sharing, Boolean saveFile) diff --git a/src/Sdk/Common/Common/VssCommonConstants.cs b/src/Sdk/Common/Common/VssCommonConstants.cs index 7de2e3fb9..d713a75df 100644 --- a/src/Sdk/Common/Common/VssCommonConstants.cs +++ b/src/Sdk/Common/Common/VssCommonConstants.cs @@ -5,16 +5,6 @@ using System.Diagnostics.CodeAnalysis; namespace GitHub.Services.Common { - public static class AdminConstants - { - /// - /// Each incoming web request is assigned a server process id, this constant defines - /// an element within the Context.Items[] to hold that value. - /// - public const String ServerProcessID = "serverProcessID"; - public const String ApplicationName = "ApplicationName"; - } - [GenerateSpecificConstants] public static class IdentityConstants { @@ -352,370 +342,6 @@ namespace GitHub.Services.Common public static readonly ISet WhiteListedProperties = new HashSet(StringComparer.OrdinalIgnoreCase); } - public static class DirectoryRoleConstants - { - /// Name of the directory role that represents "Company Administrator/Global Admin" - public const string CompanyAdministrator = "Company Administrator"; - } - - // Used with Registration entries - [GenerateSpecificConstants] - public static class ToolNames - { - public const string Framework = "Framework"; - [GenerateConstant] - public const string VersionControl = "VersionControl"; - [GenerateConstant] - public const string WorkItemTracking = "WorkItemTracking"; - [GenerateConstant] - public const string RemoteWorkItemTracking = "RemoteWorkItemTracking"; - public const string CoreServices = "vstfs"; - public const string Warehouse = "Reports"; - [GenerateConstant] - public const string TeamBuild = "Build"; - public const string ProxyServer = "ps"; - public const string TeamFoundation = "vstfs"; - public const string SharePoint = "Wss"; - [GenerateConstant] - public const string TestManagement = "TestManagement"; - public const string LabManagement = "LabManagement"; - public const string ReleaseManagement = "ReleaseManagement"; - public const string SyncService = "SyncService"; - public const string TestRig = "TestRig"; - public const string TSWebAccess = "TSWebAccess"; - public const string ProjectServer = "ProjectServer"; - public const string DeploymentRig = "DeploymentRig"; - public const string TeamProjects = "TeamProjects"; // contains specific project registration entries (project portal, process guidance and doc url) - public const string Discussion = "Discussion"; - [GenerateConstant] - public const string Requirements = "Requirements"; - [GenerateConstant] - public const string Hyperlink = "Hyperlink"; - public const string Classification = "Classification"; - [GenerateConstant] - public const string Legacy = "Legacy"; - [GenerateConstant] - public const string CodeSense = "CodeSense"; - [GenerateConstant] - public const string Git = "Git"; - [GenerateConstant] - public const string CodeReview = "CodeReview"; - [GenerateConstant] - public const string ProjectDownload = "ProjectDownload"; - public const string DistributedTask = "DistributedTask"; - [GenerateConstant] - public const string Wiki = "Wiki"; - - public const string Search = "Search"; - [GenerateConstant] - public const string GitHub = "GitHub"; - } - - // Artifact types - [GenerateSpecificConstants] - public static class ArtifactTypeNames - { - public const string Project = "TeamProject"; - public const string Node = "Node"; - public const string Collector = "Collector"; - public const string TestResult = "TestResult"; - [GenerateConstant] - public const string TcmResult = "TcmResult"; - [GenerateConstant] - public const string TcmResultAttachment = "TcmResultAttachment"; - [GenerateConstant] - public const string TcmTest = "TcmTest"; - [GenerateConstant] - public const string Build = "Build"; - public const string BuildAgent = "Agent"; - public const string BuildDefinition = "Definition"; - public const string BuildController = "Controller"; - public const string BuildGroup = "Group"; - public const string BuildRequest = "Request"; - public const string BuildServiceHost = "ServiceHost"; - [GenerateConstant] - public const string VersionedItem = "VersionedItem"; - [GenerateConstant] - public const string LatestItemVersion = "LatestItemVersion"; - [GenerateConstant] - public const string Changeset = "Changeset"; - public const string Label = "Label"; - [GenerateConstant] - public const string Shelveset = "Shelveset"; - public const string ShelvedItem = "ShelvedItem"; - [GenerateConstant] - public const string WorkItem = "WorkItem"; - public const string Query = "Query"; - public const string Results = "Results"; - public const string LabEnvironment = "LabEnvironment"; - public const string LabTemplate = "LabTemplate"; - public const string LabSystem = "LabSystem"; - public const string TeamProjectHostGroup = "TeamProjectHostGroup"; - public const string TeamProjectLibraryShare = "TeamProjectLibraryShare"; - public const string TeamProjectCollectionLibraryShare = "TeamProjectCollectionLibraryShare"; - public const string TeamProjectCollectionHostGroup = "TeamProjectCollectionHostGroup"; - public const string TestMachine = "TestMachine"; - [GenerateConstant] - public const string Storyboard = "Storyboard"; - [GenerateConstant] - public const string Commit = "Commit"; - public const string LaunchLatestVersionedItem = "LaunchLatestVersionedItem"; - [GenerateConstant] - public const string CodeReviewId = "CodeReviewId"; - [GenerateConstant] - public const string CodeReviewSdkId = "ReviewId"; - [GenerateConstant] - public const string PullRequestId = "PullRequestId"; - [GenerateConstant] - public const string ProjectDownloadProject = "Project"; - /// - /// A Git Ref - /// - [GenerateConstant] - public const string Ref = "Ref"; - - public const string TaskAgentPoolMaintenance = "PoolMaintenance"; - [GenerateConstant] - public const string WikiPage = "WikiPage"; - - // GitHub - [GenerateConstant] - public const string PullRequest = "PullRequest"; - [GenerateConstant] - public const string Issue = "Issue"; - } - - /// - /// Constant strings used in Notifications - /// - public static class NotificationConstants - { - /// - /// Macro used in subscriptions which will be replaced by the project name when evaluated - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.MyProjectNameMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String MyProjectNameMacro = "@@MyProjectName@@"; - - /// - /// Macro used in subscriptions which will be replaced by the subscriber's Display Name when evaluated - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.MyDisplayNameMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String MyDisplayNameMacro = "@@MyDisplayName@@"; - - /// - /// Macro used in subscriptions which will be replaced by the subscriber's Unique User Name when evaluated - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.MyUniqueNameMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String MyUniqueNameMacro = "@@MyUniqueName@@"; - - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.SingleQuoteNameMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String SingleQuoteNameMacro = "@@SQBDQ@@"; //SingleQuoteBetweenDoubleQuotes - - [Obsolete] - public const String SingleQuoteValue = "\"'\""; //"'" - - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.DoubleQuoteNameMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String DoubleQuoteNameMacro = "@@DQBSQ@@"; //DoubleQuoteBetweenSingleQuotes - - [Obsolete] - public const String DoubleQuoteValue = "'\"'"; //'"' - - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.SingleQuoteCharMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String SingleQuoteCharMacro = "@@SingleQuote@@"; - - [Obsolete] - public const String SingleQuoteCharValue = "'"; - - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.DoubleQuoteCharMacro in assembly MS.VS.Services.Notifications.WebApi")] - public const String DoubleQuoteCharMacro = "@@DoubleQuote@@"; - - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.DoubleQuoteCharValue in assembly MS.VS.Services.Notifications.WebApi")] - public const String DoubleQuoteCharValue = "\""; - - /// - /// Token used in subscription addresses to identify dynamic delivery targets computed from the source event - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.DynamicTargetsToken in assembly MS.VS.Services.Notifications.WebApi")] - public const String DynamicTargetsToken = "@@"; - - /// - /// TeamFoundationIdentity property name for a user's custom list of Email addresses to receive notifications at - /// - public const String CustomNotificationAddressesIdentityProperty = "CustomNotificationAddresses"; - - /// - /// TeamFoundationIdentity propery name for a user's confirmed Email address to receive notifications. This is used in Hosted environments only. - /// - public const string ConfirmedNotificationAddressIdentityProperty = "ConfirmedNotificationAddress"; - - /// - /// The name of the WorkItemChangedEvent - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.WorkItemChangedEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const string WorkItemChangedEventTypeName = "WorkItemChangedEvent"; - - /// - /// The name of the BuildStatusChangedEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.BuildStatusChangeEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String BuildStatusChangeEventName = "BuildStatusChangeEvent"; - - /// - /// The name of the BuildCompletedEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.BuildCompletedEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String BuildCompletedEventName = "BuildCompletedEvent"; - - /// - /// The name of the CheckinEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.CheckinEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String CheckinEventName = "CheckinEvent"; - - /// - /// The name of the CodeReviewChangedEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.CodeReviewChangedEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String CodeReviewChangedEventName = "CodeReviewChangedEvent"; - - /// - /// The name of the GitPushEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.GitPushEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String GitPushEventName = "GitPushEvent"; - - /// - /// The name of the GitPullRequestEvent type - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.LegacyNames.GitPullRequestEvent in assembly MS.VS.Services.Notifications.WebApi")] - public const String GitPullRequestEventName = "GitPullRequestEvent"; - - /// - /// The relative path to the alerts admin web page - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationUrlConstants.AlertsPageRelativePath in assembly MS.VS.Services.Notifications.WebApi")] - public const String AlertsPageRelativePath = "{0}#id={1}&showteams={2}"; - - /// - /// The alerts page name - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationUrlConstants.AlertsPage in assembly MS.VS.Services.Notifications.WebApi")] - public const String AlertsPage = "_Alerts"; - - /// - /// The admin alerts page - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationUrlConstants.AlertsAdminPage in assembly MS.VS.Services.Notifications.WebApi")] - public const String AlertsAdminPage = "_admin/_Alerts"; - - /// - /// Property used to keep track of how many confirmations were sent for this user. Used to limit the number - /// of confirmations a single user is allowed to send out for their account. - /// The value is updated and monitored by the SendEmailConfirmationJob. - /// - public const string EmailConfirmationSendDates = "EmailConfirmationSendDates"; - - /// - /// Prefix to denote that identity field value have been processed - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.ProcessedFlagCharacter in assembly MS.VS.Services.Notifications.WebApi")] - public const Char ProcessedFlagCharacter = (Char)7; - - /// - /// Prefix to denote that identity field value have been processed and converted to TFID - /// - /// [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.ProcessedTfIdFlagCharacter in assembly MS.VS.Services.Notifications.WebApi")] - public const Char ProcessedTfIdFlagCharacter = (Char)11; - - /// - /// Prefix to denote that this is the start of displayname value for this identity field - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.DisplayNameFlagCharacter in assembly MS.VS.Services.Notifications.WebApi")] - public const Char DisplayNameFlagCharacter = '|'; - - /// - /// Prefix to denote that this is the start of TFID value for this identity field - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.TfIdFlagCharacter in assembly MS.VS.Services.Notifications.WebApi")] - public const Char TfIdFlagCharacter = '%'; - - /// - /// Optional Feature flag to enable escaping Regex expressions when creating Notification subscriptions. - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.FeatureFlags.AllowUserRegexInMatchConditionFeatureFlag in assembly MS.VS.Services.Notifications.WebApi")] - public const string AllowUserRegexInMatchConditionFeatureFlag = "VisualStudio.Services.Notifications.AllowUserRegexInMatchCondition"; - - /// - /// The MDM scope name for the notification job - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.MDMNotificationJobScope in assembly MS.VS.Services.Notifications.WebApi")] - public const string MDMNotificationJobScope = "NotificationJob"; - - /// - /// Event processing delay KPI name - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.EventProcessingDelayKPI in assembly MS.VS.Services.Notifications.WebApi")] - public const string EventProcessingDelayKPI = "EventProcessingDelayInMs"; - - /// - /// Event processing delay KPI description - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.EventProcessingDelayKPIDesc in assembly MS.VS.Services.Notifications.WebApi")] - public const string EventProcessingDelayKPIDesc = "Time taken to start processing an event"; - - /// - /// The MDM scope name for the delivery job - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.MDMDeliveryJobscope in assembly MS.VS.Services.Notifications.WebApi")] - public const string MDMDeliveryJobscope = "NotificationDeliveryJob"; - - /// - /// Notification delivery delay KPI name - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.DeliveryDelayKPI in assembly MS.VS.Services.Notifications.WebApi")] - public const string DeliveryDelayKPI = "NotificationDeliveryDelayInMs"; - - /// - /// Notification delivery delay with retries KPI name - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.DeliveryDelayWithRetriesKPI in assembly MS.VS.Services.Notifications.WebApi")] - public const string DeliveryDelayWithRetriesKPI = "NotificationDeliveryDelayWithRetriesInMs"; - - /// - /// Total time taken between the event creation till the notification delivery - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.TotalProcessingTimeKPI in assembly MS.VS.Services.Notifications.WebApi")] - public const string TotalProcessingTimeKPI = "EventProcessingTimeInMs"; - - /// - /// Total time taken between the event creation till the notification delivery - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.TotalProcessingTimeWithRetriesKPI in assembly MS.VS.Services.Notifications.WebApi")] - public const string TotalProcessingTimeWithRetriesKPI = "EventProcessingTimeWithRetriesInMs"; - - /// - /// Notification delivery delay KPI description - /// - [Obsolete("Moved to GitHub.Services.Notifications.Common.MDMConstants.DeliveryDelayKPIDesc in assembly MS.VS.Services.Notifications.WebApi")] - public const string DeliveryDelayKPIDesc = "Time taken to start deliverying a notification"; - - // caching key for our notification bridge interface - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.BridgeKey in assembly MS.VS.Services.Notifications.WebApi")] - public const String BridgeKey = "@NotifBridge"; - - // delivery retry count registryKey - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.RetryCountRegistryKey in assembly MS.VS.Services.Notifications.WebApi")] - public const string RetryCountRegistryKey = "NotificationRetryCount"; - - // delivery retry count default value - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.RetryCountDefaultValue in assembly MS.VS.Services.Notifications.WebApi")] - public const Int32 RetryCountDefaultValue = 5; - - // the collection scope Guid - [Obsolete("Moved to GitHub.Services.Notifications.Common.NotificationFrameworkConstants.CollectionScope in assembly MS.VS.Services.Notifications.WebApi")] - public static Guid CollectionScope = new Guid("00000000-0000-636f-6c6c-656374696f6e"); - } - [EditorBrowsable(EditorBrowsableState.Never)] public class LocationSecurityConstants { @@ -732,16 +358,6 @@ namespace GitHub.Services.Common public const Int32 AllPermissions = Read | Write; } - [EditorBrowsable(EditorBrowsableState.Never)] - public class SecuritySecurityConstants - { - public static readonly Guid NamespaceId = new Guid("9A82C708-BFBE-4F31-984C-E860C2196781"); - public const char Separator = '/'; - public const String RootToken = ""; - - public const int Read = 1; - } - [EditorBrowsable(EditorBrowsableState.Never)] public class GraphSecurityConstants { @@ -753,158 +369,6 @@ namespace GitHub.Services.Common public const int ReadByPersonalIdentifier = 2; } - [EditorBrowsable(EditorBrowsableState.Never)] - public static class TeamProjectSecurityConstants - { - public static readonly Guid NamespaceId = new Guid("52D39943-CB85-4d7f-8FA8-C6BAAC873819"); - - // Existed in Orcas - public static readonly Int32 GenericRead = 1; - public static readonly Int32 GenericWrite = 2; - public static readonly Int32 Delete = 4; - public static readonly Int32 PublishTestResults = 8; - public static readonly Int32 AdministerBuild = 16; - public static readonly Int32 StartBuild = 32; - public static readonly Int32 EditBuildStatus = 64; - public static readonly Int32 UpdateBuild = 128; - public static readonly Int32 DeleteTestResults = 256; - public static readonly Int32 ViewTestResults = 512; - - // Dev10 Beta1 - public static readonly Int32 ManageTestEnvironments = 2048; - - // Dev10 Beta2 - public static readonly Int32 ManageTestConfigurations = 4096; - - // Dev14 Update 2 / VSO (M91) - public static readonly Int32 WorkItemDelete = 8192; - - // Dev14 Update 2 / VSO (M92) - public static readonly Int32 WorkItemMove = 16384; - - // Dev14 Update 2 / VSO (M94) - public static readonly Int32 WorkItemPermanentlyDelete = 32768; - - // Dev15 / VSO (M99) - public static readonly Int32 Rename = 65536; - - /// - /// The permission required for setting project properties. - /// Introduced in Dev15 Update 2 / VSO (M116). - /// - public static readonly Int32 ManageProperties = 131072; - - /// - /// The permission required for setting system project properties. - /// Introduced in Dev15 Update 2 / VSO (M116). - /// - /// - /// This permission was excluded from AllPermissions to avoid being unintentionally granted. - /// - public static readonly Int32 ManageSystemProperties = 262144; - - /// - /// The permission required for bypassing the project property cache. - /// Introduced in Dev16 / VSO (M118). - /// - /// - /// This permission was excluded from AllPermissions to avoid being unintentionally granted. - /// - public static readonly Int32 BypassPropertyCache = 524288; - - /// - /// The permission required for bypassing the rules while updating work items. - /// Introduced in Dev16 / VSO (M126). - /// - public static readonly Int32 BypassRules= 1048576; - - /// - /// The permission required for suppressing notifications for work item updates. - /// Introduced in Dev16 / VSO (M126). - /// - public static readonly Int32 SuppressNotifications= 2097152; - - /// - /// The permission required for updating project visibility. - /// Introduced in Dev16 / VSO (M131). - /// - public static readonly Int32 UpdateVisibility = 4194304; - - /// - /// The permission required for changing the process of the team project - /// Introduced in Dev17 / VSO (M136). - /// - public static readonly Int32 ChangeProjectsProcess = 8388608; - - /// - /// The permission required for granting access to backlog management. For stakeholder, this would disabled for private project and enabled for public project. - /// Introduced in Dev17 / VSO (M137). - /// - /// - /// This permission was excluded from AllPermissions to avoid being unintentionally granted. - /// - public static readonly Int32 AgileToolsBacklogManagement = 16777216; - - /// - /// The permission required for granting access to backlog management. For stakeholder, this is always disabled. - /// Introduced in Dev17 / VSO (M150). - /// - /// - /// This permission was excluded from AllPermissions to avoid being unintentionally granted. - /// - public static readonly Int32 AgileToolsPlans = 33554432; - - public static readonly Int32 AllPermissions = - GenericRead | - GenericWrite | - Delete | - PublishTestResults | - AdministerBuild | - StartBuild | - EditBuildStatus | - UpdateBuild | - DeleteTestResults | - ViewTestResults | - ManageTestEnvironments | - ManageTestConfigurations | - WorkItemDelete | - WorkItemMove | - WorkItemPermanentlyDelete | - Rename | - ManageProperties | - BypassRules | - SuppressNotifications | - UpdateVisibility | - ChangeProjectsProcess; - - public const String ProjectTokenPrefix = "$PROJECT:"; - - public static String GetToken(String projectUri) - { - if (String.IsNullOrEmpty(projectUri) || !projectUri.StartsWith(ProjectTokenPrefix, StringComparison.OrdinalIgnoreCase)) - { - if (projectUri == null) - { - projectUri = String.Empty; - } - - return ProjectTokenPrefix + projectUri + ":"; - } - - return projectUri + ":"; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class ContentValidationSecurityConstants - { - public static readonly Guid NamespaceId = new Guid("B1982126-CB90-4479-BDFD-CBF193241CB8"); - public static readonly string ViolationsToken = "Violations"; - - public const int Read = 1; - public const int Write = 2; - } - public enum WinHttpErrorCode { WINHTTP_ERROR_BASE = 12000, diff --git a/src/Sdk/Common/Common/VssException.cs b/src/Sdk/Common/Common/VssException.cs index c711c0ed4..8226a0e0c 100644 --- a/src/Sdk/Common/Common/VssException.cs +++ b/src/Sdk/Common/Common/VssException.cs @@ -124,9 +124,6 @@ namespace GitHub.Services.Common LogException = (bool)info.GetValue("m_logException", typeof(bool)); ReportException = (bool)info.GetValue("m_reportException", typeof(bool)); ErrorCode = (int)info.GetValue("m_errorCode", typeof(int)); -#if !NETSTANDARD - LogLevel = (EventLogEntryType)info.GetValue("m_logLevel", typeof(EventLogEntryType)); -#endif EventId = (int)info.GetValue("m_eventId", typeof(int)); } @@ -137,9 +134,6 @@ namespace GitHub.Services.Common info.AddValue("m_logException", LogException); info.AddValue("m_reportException", ReportException); info.AddValue("m_errorCode", ErrorCode); -#if !NETSTANDARD - info.AddValue("m_logLevel", LogLevel); -#endif info.AddValue("m_eventId", EventId); } @@ -157,22 +151,6 @@ namespace GitHub.Services.Common } } -#if !NETSTANDARD - /// The event log entry type to use when logging the exception - /// One of the event log entry types: - public EventLogEntryType LogLevel - { - get - { - return m_logLevel; - } - set - { - m_logLevel = value; - } - } -#endif - /// A user-defined error code. public int ErrorCode { @@ -279,10 +257,6 @@ namespace GitHub.Services.Common private bool m_reportException; private int m_errorCode; -#if !NETSTANDARD - private EventLogEntryType m_logLevel = EventLogEntryType.Warning; -#endif - private int m_eventId = DefaultExceptionEventId; //From EventLog.cs in Framework. diff --git a/src/Sdk/Common/Common/VssHttpMessageHandler.cs b/src/Sdk/Common/Common/VssHttpMessageHandler.cs index f51c3553b..039db2596 100644 --- a/src/Sdk/Common/Common/VssHttpMessageHandler.cs +++ b/src/Sdk/Common/Common/VssHttpMessageHandler.cs @@ -33,13 +33,7 @@ namespace GitHub.Services.Common public VssHttpMessageHandler( VssCredentials credentials, VssHttpRequestSettings settings) - : this(credentials, settings, -#if !NETSTANDARD - new WebRequestHandler() -#else - new HttpClientHandler() -#endif - ) + : this(credentials, settings, new HttpClientHandler()) { } @@ -76,13 +70,7 @@ namespace GitHub.Services.Common m_transportHandler = transportHandler; } -#if NETSTANDARD - //.Net Core does not recognize CredentialCache.DefaultCredentials if we wrap them with CredentialWrapper - bool isDefaultCredentials = credentials != null && credentials.Windows != null && credentials.Windows.UseDefaultCredentials; - ApplySettings(m_transportHandler, isDefaultCredentials ? CredentialCache.DefaultCredentials : m_credentialWrapper, this.Settings); -#else ApplySettings(m_transportHandler, m_credentialWrapper, this.Settings); -#endif } /// @@ -139,35 +127,6 @@ namespace GitHub.Services.Common var traceInfo = VssHttpMessageHandlerTraceInfo.GetTraceInfo(request); traceInfo?.TraceHandlerStartTime(); -#if !NETSTANDARD - // This action is deferred from ApplySettings because we want don't want to do it if we aren't - // talking to an HTTPS endpoint. - if (!m_appliedClientCertificatesToTransportHandler && - request.RequestUri.Scheme == "https") - { - WebRequestHandler webRequestHandler = m_transportHandler as WebRequestHandler; - if (webRequestHandler != null && - this.Settings.ClientCertificateManager != null && - this.Settings.ClientCertificateManager.ClientCertificates != null && - this.Settings.ClientCertificateManager.ClientCertificates.Count > 0) - { - webRequestHandler.ClientCertificates.AddRange(this.Settings.ClientCertificateManager.ClientCertificates); - } - m_appliedClientCertificatesToTransportHandler = true; - } - - if (!m_appliedServerCertificateValidationCallbackToTransportHandler && - request.RequestUri.Scheme == "https") - { - WebRequestHandler webRequestHandler = m_transportHandler as WebRequestHandler; - if (webRequestHandler != null && - this.Settings.ServerCertificateValidationCallback != null) - { - webRequestHandler.ServerCertificateValidationCallback = this.Settings.ServerCertificateValidationCallback; - } - m_appliedServerCertificateValidationCallbackToTransportHandler = true; - } -#else if (!m_appliedClientCertificatesToTransportHandler && request.RequestUri.Scheme == "https") { @@ -201,7 +160,6 @@ namespace GitHub.Services.Common { request.Version = HttpVersion.Version11; } -#endif IssuedToken token = null; IssuedTokenProvider provider; @@ -540,16 +498,11 @@ namespace GitHub.Services.Common } } - private static IWebProxy s_defaultWebProxy = -#if !NETSTANDARD - WebRequest.DefaultWebProxy; -#else - // setting this to WebRequest.DefaultWebProxy in NETSTANDARD is causing a System.PlatformNotSupportedException - //.in System.Net.SystemWebProxy.IsBypassed. Comment in IsBypassed method indicates ".NET Core and .NET Native - // code will handle this exception and call into WinInet/WinHttp as appropriate to use the system proxy." - // This needs to be investigated further. - null; -#endif + // setting this to WebRequest.DefaultWebProxy in NETSTANDARD is causing a System.PlatformNotSupportedException + //.in System.Net.SystemWebProxy.IsBypassed. Comment in IsBypassed method indicates ".NET Core and .NET Native + // code will handle this exception and call into WinInet/WinHttp as appropriate to use the system proxy." + // This needs to be investigated further. + private static IWebProxy s_defaultWebProxy = null; /// /// Allows you to set a proxy to be used by all VssHttpMessageHandler requests without affecting the global WebRequest.DefaultWebProxy. If not set it returns the WebRequest.DefaultWebProxy. @@ -585,13 +538,9 @@ namespace GitHub.Services.Common private bool m_appliedServerCertificateValidationCallbackToTransportHandler; private readonly HttpMessageHandler m_transportHandler; -#if NETSTANDARD //.Net Core does not attempt NTLM schema on Linux, unless ICredentials is a CredentialCache instance //This workaround may not be needed after this corefx fix is consumed: https://github.com/dotnet/corefx/pull/7923 private sealed class CredentialWrapper : CredentialCache, ICredentials -#else - private sealed class CredentialWrapper : ICredentials -#endif { public ICredentials InnerCredentials { diff --git a/src/Sdk/Common/Common/VssHttpRequestSettings.cs b/src/Sdk/Common/Common/VssHttpRequestSettings.cs index 18f4c26d6..ac0dd9c3c 100644 --- a/src/Sdk/Common/Common/VssHttpRequestSettings.cs +++ b/src/Sdk/Common/Common/VssHttpRequestSettings.cs @@ -44,9 +44,7 @@ namespace GitHub.Services.Common this.SuppressFedAuthRedirects = true; this.ClientCertificateManager = null; this.ServerCertificateValidationCallback = null; -#if NETSTANDARD this.UseHttp11 = false; -#endif // If different, we'll also add CurrentCulture to the request headers, // but UICulture was added first, so it gets first preference @@ -99,9 +97,7 @@ namespace GitHub.Services.Common this.ClientCertificateManager = copy.ClientCertificateManager; this.ServerCertificateValidationCallback = copy.ServerCertificateValidationCallback; this.MaxRetryRequest = copy.MaxRetryRequest; -#if NETSTANDARD this.UseHttp11 = copy.UseHttp11; -#endif } /// @@ -144,7 +140,6 @@ namespace GitHub.Services.Common set; } -#if NETSTANDARD /// /// The .NET Core 2.1 runtime switched its HTTP default from HTTP 1.1 to HTTP 2. /// This causes problems with some versions of the Curl handler on Linux. @@ -156,7 +151,6 @@ namespace GitHub.Services.Common get; set; } -#endif /// /// Gets or sets the maximum size allowed for response content buffering. @@ -266,15 +260,6 @@ namespace GitHub.Services.Common set; } -#if !NETSTANDARD - /// - /// Optional implementation used to validate server certificate validation - /// - public RemoteCertificateValidationCallback ServerCertificateValidationCallback - { - get; set; - } -#else /// /// Optional implementation used to validate server certificate validation /// @@ -283,7 +268,6 @@ namespace GitHub.Services.Common get; set; } -#endif /// /// Number of times to retry a request that has an ambient failure @@ -359,13 +343,11 @@ namespace GitHub.Services.Common request.Headers.Add(Internal.HttpHeaders.VssAgentHeader, this.AgentId); } -#if NETSTANDARD // Content is being sent as chunked by default in dotnet5.4, which differs than the .net 4.5 behaviour. if (request.Content != null && !request.Content.Headers.ContentLength.HasValue && !request.Headers.TransferEncodingChunked.HasValue) { request.Content.Headers.ContentLength = request.Content.ReadAsByteArrayAsync().Result.Length; } -#endif return true; } diff --git a/src/Sdk/Common/Common/VssNetworkHelper.cs b/src/Sdk/Common/Common/VssNetworkHelper.cs index 49d69d99d..209b86825 100644 --- a/src/Sdk/Common/Common/VssNetworkHelper.cs +++ b/src/Sdk/Common/Common/VssNetworkHelper.cs @@ -216,21 +216,13 @@ namespace GitHub.Services.Common } } } -#if !NETSTANDARD - else if (ex is System.Data.Services.Client.DataServiceRequestException || - ex is System.Data.Services.Client.DataServiceClientException) - { - // WCF exceptions - return true; - } -#endif return false; } - /// - /// Gets the HttpStatusCode which represents a throttling error. - /// + /// + /// Gets the HttpStatusCode which represents a throttling error. + /// public const HttpStatusCode TooManyRequests = (HttpStatusCode)429; } } diff --git a/src/Sdk/Common/EmbeddedVersionInfo.cs b/src/Sdk/Common/EmbeddedVersionInfo.cs index ee0363567..57813453e 100644 --- a/src/Sdk/Common/EmbeddedVersionInfo.cs +++ b/src/Sdk/Common/EmbeddedVersionInfo.cs @@ -10,30 +10,14 @@ namespace GitHub.Services.Common // See Toolsets\Version\Version.props for more details. public const String MajorVersion = "16"; public const String MinorVersion = "0"; - public const String BuildVersion = "65000"; - public const String PatchVersion = "0"; public const String ProductVersion = MajorVersion + "." + MinorVersion; // Assembly version (i.e. strong name) public const String AssemblyMajorVersion = "16"; - public const String AssemblyMinorVersion = "0"; - public const String AssemblyBuildVersion = "0"; - public const String AssemblyPatchVersion = "0"; - public const String AssemblyVersion = AssemblyMajorVersion + "." + AssemblyMinorVersion + "." + AssemblyBuildVersion + "." + AssemblyPatchVersion; - - // File version - public const String FileMajorVersion = "16"; - public const String FileMinorVersion = "255"; - public const String FileBuildVersion = "65000"; - public const String FilePatchVersion = "0"; - public const String FileVersion = FileMajorVersion + "." + FileMinorVersion + "." + FileBuildVersion + "." + FilePatchVersion; // Derived versions public const String TfsMajorVersion = "8"; public const String TfsMinorVersion = "0"; public const String TfsProductVersion = TfsMajorVersion + "." + TfsMinorVersion; - - // On-premises TFS install folder - public const String TfsInstallDirectory = "Azure DevOps Server 2019"; } } diff --git a/src/Sdk/CoreWebApi/Core/ProjectClasses.cs b/src/Sdk/CoreWebApi/Core/ProjectClasses.cs deleted file mode 100644 index 7b6de8516..000000000 --- a/src/Sdk/CoreWebApi/Core/ProjectClasses.cs +++ /dev/null @@ -1,80 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.Common.Internal; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Patch; -using GitHub.Services.WebApi.Patch.Json; - -namespace GitHub.Core.WebApi -{ - [GenerateAllConstants] - public enum ProjectState - { - /// - /// Project is in the process of being deleted. - /// - [EnumMember] - Deleting = 2, - - /// - /// Project is in the process of being created. - /// - [EnumMember] - New = 0, - - /// - /// Project is completely created and ready to use. - /// - [EnumMember] - WellFormed = 1, - - /// - /// Project has been queued for creation, but the process has not yet started. - /// - [EnumMember] - CreatePending = 3, - - /// - /// All projects regardless of state. - /// - [EnumMember] - All = -1, // Used for filtering. - - /// - /// Project has not been changed. - /// - [EnumMember] - Unchanged = -2, // Used for updating projects. - - /// - /// Project has been deleted. - /// - [EnumMember] - Deleted = 4, // Used for the project history. - } - - public enum ProjectVisibility // Stored as a TINYINT - { - [ClientInternalUseOnly] - Unchanged = -1, // Used for updating projects. - /// - /// The project is only visible to users with explicit access. - /// - Private = 0, - /// - /// Enterprise level project visibility - /// - [ClientInternalUseOnly(omitFromTypeScriptDeclareFile: false)] - Organization = 1, - /// - /// The project is visible to all. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - Public = 2, - [ClientInternalUseOnly] - SystemPrivate = 3 // Soft-deleted projects - } -} diff --git a/src/Sdk/CoreWebApi/Core/TeamProjectReference.cs b/src/Sdk/CoreWebApi/Core/TeamProjectReference.cs deleted file mode 100644 index a46e880f7..000000000 --- a/src/Sdk/CoreWebApi/Core/TeamProjectReference.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.Core.WebApi -{ - /// - /// Represents a shallow reference to a TeamProject. - /// - [DataContract] - public class TeamProjectReference : ISecuredObject - { - /// - /// Default constructor to ensure we set up the project state correctly for serialization. - /// - public TeamProjectReference() - { - State = ProjectState.Unchanged; - Visibility = ProjectVisibility.Unchanged; - } - - /// - /// Project identifier. - /// - [DataMember(Order = 0, EmitDefaultValue = false)] - public Guid Id { get; set; } - - /// - /// Project abbreviation. - /// - [DataMember(Order = 1, EmitDefaultValue = false)] - public string Abbreviation { get; set; } - - /// - /// Project name. - /// - [DataMember(Order = 2, EmitDefaultValue = false)] - public string Name { get; set; } - - /// - /// The project's description (if any). - /// - [DataMember(Order = 3, EmitDefaultValue = false)] - public string Description { get; set; } - - /// - /// Url to the full version of the object. - /// - [DataMember(Order = 4, EmitDefaultValue = false)] - public string Url { get; set; } - - /// - /// Project state. - /// - [DataMember(Order = 5)] - public ProjectState State { get; set; } - - /// - /// Project revision. - /// - [DataMember(Order = 6, EmitDefaultValue = false)] - public Int64 Revision { get; set; } - - /// - /// Project visibility. - /// - [DataMember(Order = 7)] - public ProjectVisibility Visibility { get; set; } - - /// - /// Url to default team identity image. - /// - [DataMember(Order = 8, EmitDefaultValue = false)] - public String DefaultTeamImageUrl { get; set; } - - /// - /// Project last update time. - /// - [DataMember(Order = 9)] - public DateTime LastUpdateTime { get; set; } - - #region ISecuredObject - Guid ISecuredObject.NamespaceId => NamespaceId; - - int ISecuredObject.RequiredPermissions => RequiredPermissions; - - string ISecuredObject.GetToken() - { - return GetToken(); - } - - protected virtual Guid NamespaceId => TeamProjectSecurityConstants.NamespaceId; - - protected virtual int RequiredPermissions => TeamProjectSecurityConstants.GenericRead; - - protected virtual string GetToken() - { - // WE DON'T CARE THIS FOR NOW - return TeamProjectSecurityConstants.GetToken(Id.ToString("D")); - } - - #endregion - } -} diff --git a/src/Sdk/DTContracts/Contracts/AuthorizationHeader.cs b/src/Sdk/DTContracts/Contracts/AuthorizationHeader.cs deleted file mode 100644 index 088d919a5..000000000 --- a/src/Sdk/DTContracts/Contracts/AuthorizationHeader.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - [DataContract] - public class AuthorizationHeader : BaseSecuredObject - { - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Value { get; set; } - } -} diff --git a/src/Sdk/DTContracts/Contracts/DataSourceBinding.cs b/src/Sdk/DTContracts/Contracts/DataSourceBinding.cs deleted file mode 100644 index b8e55c285..000000000 --- a/src/Sdk/DTContracts/Contracts/DataSourceBinding.cs +++ /dev/null @@ -1,149 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - /// - /// Represents binding of data source for the service endpoint request. - /// - [DataContract] - public class DataSourceBindingBase : BaseSecuredObject - { - public DataSourceBindingBase() - { - } - - protected DataSourceBindingBase(DataSourceBindingBase inputDefinitionToClone) - : this(inputDefinitionToClone, null) - { - } - - protected DataSourceBindingBase(DataSourceBindingBase inputDefinitionToClone, ISecuredObject securedObject) - : base(securedObject) - { - this.DataSourceName = inputDefinitionToClone.DataSourceName; - this.EndpointId = inputDefinitionToClone.EndpointId; - this.Target = inputDefinitionToClone.Target; - this.ResultTemplate = inputDefinitionToClone.ResultTemplate; - this.EndpointUrl = inputDefinitionToClone.EndpointUrl; - this.ResultSelector = inputDefinitionToClone.ResultSelector; - this.RequestVerb = inputDefinitionToClone.RequestVerb; - this.RequestContent = inputDefinitionToClone.RequestContent; - this.CallbackContextTemplate = inputDefinitionToClone.CallbackContextTemplate; - this.CallbackRequiredTemplate = inputDefinitionToClone.CallbackRequiredTemplate; - this.InitialContextTemplate = inputDefinitionToClone.InitialContextTemplate; - inputDefinitionToClone.Parameters.Copy(this.Parameters); - this.CloneHeaders(inputDefinitionToClone.Headers); - } - - /// - /// Gets or sets the name of the data source. - /// - [DataMember(EmitDefaultValue = false)] - public string DataSourceName { get; set; } - - /// - /// Gets or sets the parameters for the data source. - /// - [DataMember(EmitDefaultValue = false)] - public Dictionary Parameters - { - get - { - if (m_parameters == null) - { - m_parameters = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - return m_parameters; - } - } - - public DataSourceBindingBase Clone(ISecuredObject securedObject) - { - return new DataSourceBindingBase(this, securedObject); - } - - private void CloneHeaders(List headers) - { - if (headers == null) - { - return; - } - - this.Headers = headers.Select(header => new AuthorizationHeader { Name = header.Name, Value = header.Value }).ToList(); - } - - /// - /// Gets or sets the endpoint Id. - /// - [DataMember(EmitDefaultValue = false)] - public String EndpointId { get; set; } - - /// - /// Gets or sets the target of the data source. - /// - [DataMember(EmitDefaultValue = false)] - public String Target { get; set; } - - /// - /// Gets or sets the result template. - /// - [DataMember(EmitDefaultValue = false)] - public String ResultTemplate { get; set; } - - /// - /// Gets or sets http request verb - /// - [DataMember(EmitDefaultValue = false)] - public String RequestVerb { get; set; } - - /// - /// Gets or sets http request body - /// - [DataMember(EmitDefaultValue = false)] - public String RequestContent { get; set; } - - /// - /// Gets or sets the url of the service endpoint. - /// - [DataMember(EmitDefaultValue = false)] - public String EndpointUrl { get; set; } - - /// - /// Gets or sets the result selector. - /// - [DataMember(EmitDefaultValue = false)] - public String ResultSelector { get; set; } - - /// - /// Pagination format supported by this data source(ContinuationToken/SkipTop). - /// - [DataMember(EmitDefaultValue = false)] - public String CallbackContextTemplate { get; set; } - - /// - /// Subsequent calls needed? - /// - [DataMember(EmitDefaultValue = false)] - public String CallbackRequiredTemplate { get; set; } - - /// - /// Defines the initial value of the query params - /// - [DataMember(EmitDefaultValue = false)] - public String InitialContextTemplate { get; set; } - - /// - /// Gets or sets the authorization headers. - /// - [DataMember(EmitDefaultValue = false)] - public List Headers { get; set; } - - private Dictionary m_parameters; - } -} diff --git a/src/Sdk/DTContracts/Contracts/ProcessParameters.cs b/src/Sdk/DTContracts/Contracts/ProcessParameters.cs deleted file mode 100644 index 7e7798701..000000000 --- a/src/Sdk/DTContracts/Contracts/ProcessParameters.cs +++ /dev/null @@ -1,163 +0,0 @@ -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - [DataContract] - public class ProcessParameters : BaseSecuredObject - { - public ProcessParameters() - : this(null) - { - } - - public ProcessParameters(ISecuredObject securedObject) - : this(null, securedObject) - { - } - - private ProcessParameters(ProcessParameters toClone, ISecuredObject securedObject) - : base(securedObject) - { - if (toClone != null) - { - if (toClone.Inputs.Count > 0) - { - Inputs.AddRange(toClone.Inputs.Select(i => i.Clone(securedObject))); - } - - if (toClone.SourceDefinitions.Count > 0) - { - SourceDefinitions.AddRange(toClone.SourceDefinitions.Select(sd => sd.Clone(securedObject))); - } - - if (toClone.DataSourceBindings.Count > 0) - { - DataSourceBindings.AddRange(toClone.DataSourceBindings.Select(dsb => dsb.Clone(securedObject))); - } - } - } - - public IList Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new List(); - } - return m_inputs; - } - } - - public IList SourceDefinitions - { - get - { - if (m_sourceDefinitions == null) - { - m_sourceDefinitions = new List(); - } - return m_sourceDefinitions; - } - } - - public IList DataSourceBindings - { - get - { - if (m_dataSourceBindings == null) - { - m_dataSourceBindings = new List(); - } - return m_dataSourceBindings; - } - } - - public override int GetHashCode() - { - return base.GetHashCode(); - } - - public override bool Equals(object obj) - { - var processParameters2 = obj as ProcessParameters; - if (processParameters2 == null) - { - return false; - } - - if (this.Inputs == null && processParameters2.Inputs == null) - { - return true; - } - - if ((this.Inputs != null && processParameters2.Inputs == null) - || (this.Inputs == null && processParameters2.Inputs != null)) - { - return false; - } - - if (this.Inputs.Count != processParameters2.Inputs.Count) - { - return false; - } - - var orderedProcessParameters1 = this.Inputs.Where(i => i != null).OrderBy(i => i.Name); - var orderedProcessParameters2 = processParameters2.Inputs.Where(i => i != null).OrderBy(i => i.Name); - - if (!orderedProcessParameters1.OrderBy(i => i.Name).SequenceEqual(orderedProcessParameters2)) - { - return false; - } - - return true; - } - - public ProcessParameters Clone(ISecuredObject securedObject = null) - { - return new ProcessParameters(this, securedObject); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedInputs, ref m_inputs, true); - SerializationHelper.Copy(ref m_serializedSourceDefinitions, ref m_sourceDefinitions, true); - SerializationHelper.Copy(ref m_serializedDataSourceBindings, ref m_dataSourceBindings, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_inputs, ref m_serializedInputs); - SerializationHelper.Copy(ref m_sourceDefinitions, ref m_serializedSourceDefinitions); - SerializationHelper.Copy(ref m_dataSourceBindings, ref m_serializedDataSourceBindings); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedInputs = null; - m_serializedSourceDefinitions = null; - m_serializedDataSourceBindings = null; - } - - [DataMember(Name = "Inputs", EmitDefaultValue = false)] - private List m_serializedInputs; - - [DataMember(Name = "SourceDefinitions", EmitDefaultValue = false)] - private List m_serializedSourceDefinitions; - - [DataMember(Name = "DataSourceBindings", EmitDefaultValue = false)] - private List m_serializedDataSourceBindings; - - private List m_inputs; - private List m_sourceDefinitions; - private List m_dataSourceBindings; - } -} diff --git a/src/Sdk/DTContracts/Contracts/TaskInputDefinition.cs b/src/Sdk/DTContracts/Contracts/TaskInputDefinition.cs deleted file mode 100644 index 49e5091b6..000000000 --- a/src/Sdk/DTContracts/Contracts/TaskInputDefinition.cs +++ /dev/null @@ -1,254 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - [DataContract] - public class TaskInputDefinitionBase : BaseSecuredObject - { - public TaskInputDefinitionBase() - { - InputType = TaskInputType.String; - DefaultValue = String.Empty; - Required = false; - HelpMarkDown = String.Empty; - } - - protected TaskInputDefinitionBase(TaskInputDefinitionBase inputDefinitionToClone) - : this(inputDefinitionToClone, null) - { - } - - protected TaskInputDefinitionBase(TaskInputDefinitionBase inputDefinitionToClone, ISecuredObject securedObject) - : base(securedObject) - { - this.DefaultValue = inputDefinitionToClone.DefaultValue; - this.InputType = inputDefinitionToClone.InputType; - this.Label = inputDefinitionToClone.Label; - this.Name = inputDefinitionToClone.Name; - this.Required = inputDefinitionToClone.Required; - this.HelpMarkDown = inputDefinitionToClone.HelpMarkDown; - this.VisibleRule = inputDefinitionToClone.VisibleRule; - this.GroupName = inputDefinitionToClone.GroupName; - - if (inputDefinitionToClone.Validation != null) - { - this.Validation = inputDefinitionToClone.Validation.Clone(securedObject); - } - - if (inputDefinitionToClone.m_aliases != null) - { - this.m_aliases = new List(inputDefinitionToClone.m_aliases); - } - - if (inputDefinitionToClone.m_options != null) - { - this.m_options = new Dictionary(inputDefinitionToClone.m_options); - } - if (inputDefinitionToClone.m_properties != null) - { - this.m_properties = new Dictionary(inputDefinitionToClone.m_properties); - } - } - - public IList Aliases - { - get - { - if (m_aliases == null) - { - m_aliases = new List(); - } - return m_aliases; - } - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Label - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String DefaultValue - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Required - { - get; - set; - } - - [DataMember(Name = "Type")] - public String InputType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String HelpMarkDown - { - get; - set; - } - - // VisibleRule should specify the condition at which this input is to be shown/displayed - // Typical format is "NAME OF THE DEPENDENT INPUT = VALUE TOBE BOUND" - [DataMember(EmitDefaultValue = false)] - public string VisibleRule - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public string GroupName - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskInputValidation Validation - { - get; - set; - } - - public Dictionary Options - { - get - { - if (m_options == null) - { - m_options = new Dictionary(); - } - return m_options; - } - } - - public Dictionary Properties - { - get - { - if (m_properties == null) - { - m_properties = new Dictionary(); - } - return m_properties; - } - } - - public virtual TaskInputDefinitionBase Clone( - ISecuredObject securedObject) - { - return new TaskInputDefinitionBase(this, securedObject); - } - - public override int GetHashCode() - { - return this.Name.GetHashCode() ^ this.DefaultValue.GetHashCode() ^ this.Label.GetHashCode(); - } - - public override bool Equals(object obj) - { - var taskInput2 = obj as TaskInputDefinitionBase; - if (taskInput2 == null - || !string.Equals(InputType, taskInput2.InputType, StringComparison.OrdinalIgnoreCase) - || !string.Equals(Label, taskInput2.Label, StringComparison.OrdinalIgnoreCase) - || !string.Equals(Name, taskInput2.Name, StringComparison.OrdinalIgnoreCase) - || !string.Equals(GroupName, taskInput2.GroupName, StringComparison.OrdinalIgnoreCase) - || !string.Equals(DefaultValue, taskInput2.DefaultValue, StringComparison.OrdinalIgnoreCase) - || !string.Equals(HelpMarkDown, taskInput2.HelpMarkDown, StringComparison.OrdinalIgnoreCase) - || !string.Equals(VisibleRule, taskInput2.VisibleRule, StringComparison.OrdinalIgnoreCase) - || !this.Required.Equals(taskInput2.Required)) - { - return false; - } - - if (!AreListsEqual(Aliases, taskInput2.Aliases) - || !AreDictionariesEqual(Properties, taskInput2.Properties) - || !AreDictionariesEqual(Options, taskInput2.Options)) - { - return false; - } - - if ((Validation != null && taskInput2.Validation == null) - || (Validation == null && taskInput2.Validation != null) - || ((Validation != null && taskInput2.Validation != null) - && !Validation.Equals(taskInput2.Validation))) - { - return false; - } - - return true; - } - - private bool AreDictionariesEqual(Dictionary input1, Dictionary input2) - { - if (input1 == null && input2 == null) - { - return true; - } - - if ((input1 == null && input2 != null) - || (input1 != null && input2 == null) - || (input1.Count != input2.Count)) - { - return false; - } - - foreach (var key in input1.Keys) - { - if (!(input2.ContainsKey(key) && String.Equals(input1[key], input2[key], StringComparison.OrdinalIgnoreCase))) - { - return false; - } - } - - return true; - } - - private Boolean AreListsEqual(IList list1, IList list2) - { - if (list1.Count != list2.Count) - { - return false; - } - - for (Int32 i = 0; i < list1.Count; i++) - { - if (!String.Equals(list1[i], list2[i], StringComparison.OrdinalIgnoreCase)) - { - return false; - } - } - - return true; - } - - [DataMember(Name = "Aliases", EmitDefaultValue = false)] - private List m_aliases; - - [DataMember(Name = "Options", EmitDefaultValue = false)] - private Dictionary m_options; - - [DataMember(Name = "Properties", EmitDefaultValue = false)] - private Dictionary m_properties; - } -} diff --git a/src/Sdk/DTContracts/Contracts/TaskInputType.cs b/src/Sdk/DTContracts/Contracts/TaskInputType.cs deleted file mode 100644 index 44f73df39..000000000 --- a/src/Sdk/DTContracts/Contracts/TaskInputType.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System.Runtime.Serialization; -using System; - -namespace GitHub.DistributedTask.Common.Contracts -{ - public static class TaskInputType - { - public const String String = "string"; - public const String Repository = "repository"; - public const String Boolean = "boolean"; - public const String KeyValue = "keyvalue"; - public const String FilePath = "filepath"; - } -} diff --git a/src/Sdk/DTContracts/Contracts/TaskInputValidation.cs b/src/Sdk/DTContracts/Contracts/TaskInputValidation.cs deleted file mode 100644 index 839e7bf02..000000000 --- a/src/Sdk/DTContracts/Contracts/TaskInputValidation.cs +++ /dev/null @@ -1,59 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - [DataContract] - public class TaskInputValidation : BaseSecuredObject - { - public TaskInputValidation() - { - } - - private TaskInputValidation(TaskInputValidation toClone, ISecuredObject securedObject) - : base(securedObject) - { - if (toClone != null) - { - this.Expression = toClone.Expression; - this.Message = toClone.Message; - } - } - - /// - /// Conditional expression - /// - [DataMember(EmitDefaultValue = false)] - public String Expression - { - get; - set; - } - - /// - /// Message explaining how user can correct if validation fails - /// - [DataMember(EmitDefaultValue = false)] - public String Message - { - get; - set; - } - - public override int GetHashCode() - { - return Expression.GetHashCode() ^ Message.GetHashCode(); - } - - public TaskInputValidation Clone() - { - return this.Clone(null); - } - - public TaskInputValidation Clone(ISecuredObject securedObject) - { - return new TaskInputValidation(this, securedObject); - } - } -} diff --git a/src/Sdk/DTContracts/Contracts/TaskSourceDefinition.cs b/src/Sdk/DTContracts/Contracts/TaskSourceDefinition.cs deleted file mode 100644 index 20407f51d..000000000 --- a/src/Sdk/DTContracts/Contracts/TaskSourceDefinition.cs +++ /dev/null @@ -1,74 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Common.Contracts -{ - [DataContract] - public class TaskSourceDefinitionBase : BaseSecuredObject - { - public TaskSourceDefinitionBase() - { - AuthKey = String.Empty; - Endpoint = String.Empty; - Selector = String.Empty; - Target = String.Empty; - KeySelector = String.Empty; - } - - protected TaskSourceDefinitionBase(TaskSourceDefinitionBase inputDefinitionToClone) - : this(inputDefinitionToClone, null) - { - } - - protected TaskSourceDefinitionBase(TaskSourceDefinitionBase inputDefinitionToClone, ISecuredObject securedObject) - : base(securedObject) - { - this.Endpoint = inputDefinitionToClone.Endpoint; - this.Target = inputDefinitionToClone.Target; - this.AuthKey = inputDefinitionToClone.AuthKey; - this.Selector = inputDefinitionToClone.Selector; - this.KeySelector = inputDefinitionToClone.KeySelector; - } - - public virtual TaskSourceDefinitionBase Clone(ISecuredObject securedObject) - { - return new TaskSourceDefinitionBase(this, securedObject); - } - - [DataMember(EmitDefaultValue = false)] - public String Endpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Target - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String AuthKey - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Selector - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String KeySelector - { - get; - set; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/AndNode.cs b/src/Sdk/DTExpressions/Expressions/AndNode.cs deleted file mode 100644 index 47411f8c7..000000000 --- a/src/Sdk/DTExpressions/Expressions/AndNode.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class AndNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - foreach (ExpressionNode parameter in Parameters) - { - if (!parameter.EvaluateBoolean(context)) - { - return false; - } - } - - return true; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CoalesceNode.cs b/src/Sdk/DTExpressions/Expressions/CoalesceNode.cs deleted file mode 100644 index 87ff6ff6b..000000000 --- a/src/Sdk/DTExpressions/Expressions/CoalesceNode.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class CoalesceNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - EvaluationResult result = null; - foreach (ExpressionNode parameter in Parameters) - { - result = parameter.Evaluate(context); - if (result.Kind == ValueKind.Null) - { - continue; - } - - if (result.Kind == ValueKind.String && String.IsNullOrEmpty(result.Value as String)) - { - continue; - } - - break; - } - - return result?.Value; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JArrayAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JArrayAccessor.cs deleted file mode 100644 index 3ee25afa9..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JArrayAccessor.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class JArrayAccessor : IReadOnlyArray - { - public JArrayAccessor(JArray jarray) - { - m_jarray = jarray; - } - - public Int32 Count => m_jarray.Count; - - public Object this[Int32 index] => m_jarray[index]; - - public IEnumerator GetEnumerator() - { - return m_jarray.GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return m_jarray.GetEnumerator(); - } - - private readonly JArray m_jarray; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JObjectAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JObjectAccessor.cs deleted file mode 100644 index 4484812fa..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JObjectAccessor.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Linq; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class JObjectAccessor : IReadOnlyObject - { - public JObjectAccessor(JObject jobject) - { - m_jobject = jobject; - } - - public Int32 Count => m_jobject.Count; - - public IEnumerable Keys => (m_jobject as IDictionary).Keys; - - // This uses Select. Calling .Values directly throws an exception. - public IEnumerable Values => (m_jobject as IDictionary).Select(x => x.Value); - - public Object this[String key] => m_jobject[key]; - - public Boolean ContainsKey(String key) - { - return (m_jobject as IDictionary).ContainsKey(key); - } - - public IEnumerator> GetEnumerator() - { - return (m_jobject as IDictionary).Select(x => new KeyValuePair(x.Key, x.Value)).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return (m_jobject as IDictionary).Select(x => new KeyValuePair(x.Key, x.Value)).GetEnumerator(); - } - - public Boolean TryGetValue( - String key, - out Object value) - { - if ((m_jobject as IDictionary).TryGetValue(key, out JToken val)) - { - value = val; - return true; - } - - value = null; - return false; - } - - private readonly JObject m_jobject; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonDictionaryContractAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonDictionaryContractAccessor.cs deleted file mode 100644 index 9b1821985..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonDictionaryContractAccessor.cs +++ /dev/null @@ -1,106 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using Newtonsoft.Json.Serialization; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class JsonDictionaryContractAccessor : IReadOnlyObject - { - public JsonDictionaryContractAccessor( - JsonDictionaryContract contract, - Object obj) - { - m_contract = contract; - m_obj = obj; - } - - public Int32 Count - { - get - { - var genericMethod = s_getCountTemplate.Value.MakeGenericMethod(m_contract.DictionaryValueType); - return (Int32)genericMethod.Invoke(null, new[] { m_obj }); - } - } - - public IEnumerable Keys - { - get - { - var genericMethod = s_getKeysTemplate.Value.MakeGenericMethod(m_contract.DictionaryValueType); - return genericMethod.Invoke(null, new[] { m_obj }) as IEnumerable; - } - } - - public IEnumerable Values => Keys.Select(x => this[x]); - - public Object this[String key] - { - get - { - if (TryGetValue(key, out Object value)) - { - return value; - } - - throw new KeyNotFoundException(ExpressionResources.KeyNotFound(key)); - } - } - - public Boolean ContainsKey(String key) - { - return TryGetValue(key, out _); - } - - public IEnumerator> GetEnumerator() - { - return Keys.Select(x => new KeyValuePair(x, this[x])).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return Keys.Select(x => new KeyValuePair(x, this[x])).GetEnumerator(); - } - - public Boolean TryGetValue( - String key, - out Object value) - { - var genericMethod = s_tryGetValueTemplate.Value.MakeGenericMethod(m_contract.DictionaryValueType); - var tuple = genericMethod.Invoke(null, new[] { m_obj, key }) as Tuple; - value = tuple.Item2; - return tuple.Item1; - } - - private static Int32 GetCount(IDictionary dictionary) - { - return dictionary.Count; - } - - private static IEnumerable GetKeys(IDictionary dictionary) - { - return dictionary.Keys; - } - - private static Tuple TryGetValue( - IDictionary dictionary, - String key) - { - if (dictionary.TryGetValue(key, out TValue value)) - { - return new Tuple(true, value); - } - - return new Tuple(false, null); - } - - private static Lazy s_getCountTemplate = new Lazy(() => typeof(JsonDictionaryContractAccessor).GetTypeInfo().GetMethod(nameof(GetCount), BindingFlags.NonPublic | BindingFlags.Static)); - private static Lazy s_getKeysTemplate = new Lazy(() => typeof(JsonDictionaryContractAccessor).GetTypeInfo().GetMethod(nameof(GetKeys), BindingFlags.NonPublic | BindingFlags.Static)); - private static Lazy s_tryGetValueTemplate = new Lazy(() => typeof(JsonDictionaryContractAccessor).GetTypeInfo().GetMethod(nameof(TryGetValue), BindingFlags.NonPublic | BindingFlags.Static)); - private readonly JsonDictionaryContract m_contract; - private readonly Object m_obj; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonObjectContractAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonObjectContractAccessor.cs deleted file mode 100644 index 56928166f..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/JsonObjectContractAccessor.cs +++ /dev/null @@ -1,89 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Linq; -using Newtonsoft.Json.Serialization; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class JsonObjectContractAccessor : IReadOnlyObject - { - public JsonObjectContractAccessor( - JsonObjectContract contract, - Object obj) - { - m_contract = contract; - m_obj = obj; - } - - public Int32 Count => GetProperties().Count(); - - public IEnumerable Keys => GetProperties().Select(x => x.PropertyName); - - public IEnumerable Values => GetProperties().Select(x => x.ValueProvider.GetValue(m_obj)); - - public Object this[String key] - { - get - { - if (TryGetValue(key, out Object value)) - { - return value; - } - - throw new KeyNotFoundException(ExpressionResources.KeyNotFound(key)); - } - } - - public Boolean ContainsKey(String key) - { - return TryGetProperty(key, out _); - } - - public IEnumerator> GetEnumerator() - { - return Keys.Select(x => new KeyValuePair(x, this[x])).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return Keys.Select(x => new KeyValuePair(x, this[x])).GetEnumerator(); - } - - public Boolean TryGetValue( - String key, - out Object value) - { - if (TryGetProperty(key, out JsonProperty property)) - { - value = property.ValueProvider.GetValue(m_obj); - return true; - } - - value = null; - return false; - } - - private IEnumerable GetProperties() - { - return m_contract.Properties.Where(x => !x.Ignored); - } - - private Boolean TryGetProperty( - String key, - out JsonProperty property) - { - property = m_contract.Properties.GetClosestMatchProperty(key); - if (property != null && !property.Ignored) - { - return true; - } - - property = null; - return false; - } - - private readonly JsonObjectContract m_contract; - private readonly Object m_obj; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ListOfObjectAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ListOfObjectAccessor.cs deleted file mode 100644 index 2bf375d12..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ListOfObjectAccessor.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class ListOfObjectAccessor : IReadOnlyArray - { - public ListOfObjectAccessor(IList list) - { - m_list = list; - } - - public Int32 Count => m_list.Count; - - public Object this[Int32 index] => m_list[index]; - - public IEnumerator GetEnumerator() - { - return m_list.GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return m_list.GetEnumerator(); - } - - private readonly IList m_list; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringObjectAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringObjectAccessor.cs deleted file mode 100644 index c1a1bf0bf..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringObjectAccessor.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class ReadOnlyDictionaryOfStringObjectAccessor : IReadOnlyObject - { - public ReadOnlyDictionaryOfStringObjectAccessor(IReadOnlyDictionary dictionary) - { - m_dictionary = dictionary; - } - - public Int32 Count => m_dictionary.Count; - - public IEnumerable Keys => m_dictionary.Keys; - - public IEnumerable Values => m_dictionary.Values; - - public Object this[String key] => m_dictionary[key]; - - public Boolean ContainsKey(String key) => m_dictionary.ContainsKey(key); - - public IEnumerator> GetEnumerator() => m_dictionary.GetEnumerator(); - - IEnumerator IEnumerable.GetEnumerator() => m_dictionary.GetEnumerator(); - - public Boolean TryGetValue( - String key, - out Object value) - { - return m_dictionary.TryGetValue(key, out value); - } - - private readonly IReadOnlyDictionary m_dictionary; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringStringAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringStringAccessor.cs deleted file mode 100644 index 5421608cb..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyDictionaryOfStringStringAccessor.cs +++ /dev/null @@ -1,54 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Linq; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class ReadOnlyDictionaryOfStringStringAccessor : IReadOnlyObject - { - public ReadOnlyDictionaryOfStringStringAccessor(IReadOnlyDictionary dictionary) - { - m_dictionary = dictionary; - } - - public Int32 Count => m_dictionary.Count; - - public IEnumerable Keys => m_dictionary.Keys; - - public IEnumerable Values => m_dictionary.Values.OfType(); - - public Object this[String key] => m_dictionary[key]; - - public Boolean ContainsKey(String key) - { - return m_dictionary.ContainsKey(key); - } - - public IEnumerator> GetEnumerator() - { - return m_dictionary.Select(x => new KeyValuePair(x.Key, x.Value)).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return m_dictionary.Select(x => new KeyValuePair(x.Key, x.Value)).GetEnumerator(); - } - - public Boolean TryGetValue( - String key, - out Object value) - { - if (m_dictionary.TryGetValue(key, out String val)) - { - value = val; - return true; - } - - value = default; - return false; - } - - private readonly IReadOnlyDictionary m_dictionary; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyListOfObjectAccessor.cs b/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyListOfObjectAccessor.cs deleted file mode 100644 index 74b56bd79..000000000 --- a/src/Sdk/DTExpressions/Expressions/CollectionAccessors/ReadOnlyListOfObjectAccessor.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Expressions.CollectionAccessors -{ - internal sealed class ReadOnlyListOfObjectAccessor : IReadOnlyArray - { - public ReadOnlyListOfObjectAccessor(IReadOnlyList list) - { - m_list = list; - } - - public Int32 Count => m_list.Count; - - public Object this[Int32 index] => m_list[index]; - - public IEnumerator GetEnumerator() => m_list.GetEnumerator(); - - IEnumerator IEnumerable.GetEnumerator() => m_list.GetEnumerator(); - - private readonly IReadOnlyList m_list; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ContainerNode.cs b/src/Sdk/DTExpressions/Expressions/ContainerNode.cs deleted file mode 100644 index 372304d0f..000000000 --- a/src/Sdk/DTExpressions/Expressions/ContainerNode.cs +++ /dev/null @@ -1,49 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Reflection; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class ContainerNode : ExpressionNode - { - public IReadOnlyList Parameters => m_parameters.AsReadOnly(); - - public void AddParameter(ExpressionNode node) - { - m_parameters.Add(node); - node.Container = this; - } - - public void ReplaceParameter(Int32 index, ExpressionNode node) - { - m_parameters[index] = node; - node.Container = this; - } - - public override IEnumerable GetParameters() - { - List matched = new List(); - Queue parameters = new Queue(this.Parameters); - - while (parameters.Count > 0) - { - var parameter = parameters.Dequeue(); - if (typeof(T).GetTypeInfo().IsAssignableFrom(parameter.GetType().GetTypeInfo())) - { - matched.Add((T)parameter); - } - - foreach (var childParameter in parameter.GetParameters()) - { - parameters.Enqueue(childParameter); - } - } - - return matched; - } - - private readonly List m_parameters = new List(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ContainsNode.cs b/src/Sdk/DTExpressions/Expressions/ContainsNode.cs deleted file mode 100644 index eca9e2c85..000000000 --- a/src/Sdk/DTExpressions/Expressions/ContainsNode.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class ContainsNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - String left = Parameters[0].EvaluateString(context) as String ?? String.Empty; - String right = Parameters[1].EvaluateString(context) as String ?? String.Empty; - return left.IndexOf(right, StringComparison.OrdinalIgnoreCase) >= 0; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ContainsValueNode.cs b/src/Sdk/DTExpressions/Expressions/ContainsValueNode.cs deleted file mode 100644 index d86de2e14..000000000 --- a/src/Sdk/DTExpressions/Expressions/ContainsValueNode.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class ContainsValueNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override object EvaluateCore(EvaluationContext context) - { - EvaluationResult left = Parameters[0].Evaluate(context); - - if (left.TryGetCollectionInterface(out Object collection)) - { - EvaluationResult right = Parameters[1].Evaluate(context); - - if (collection is IReadOnlyArray array) - { - foreach (var item in array) - { - var itemResult = EvaluationResult.CreateIntermediateResult(context, item, out _); - - if (right.Equals(context, itemResult)) - { - return true; - } - } - } - else if (collection is IReadOnlyObject obj) - { - foreach (var value in obj.Values) - { - var valueResult = EvaluationResult.CreateIntermediateResult(context, value, out _); - - if (right.Equals(context, valueResult)) - { - return true; - } - } - } - } - - return false; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ConversionResult.cs b/src/Sdk/DTExpressions/Expressions/ConversionResult.cs deleted file mode 100644 index 018f65d02..000000000 --- a/src/Sdk/DTExpressions/Expressions/ConversionResult.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public struct ConversionResult - { - /// - /// Result object after the conversion - /// - public Object Result; - - /// - /// Memory overhead for the result object - /// - public ResultMemory ResultMemory; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EndsWithNode.cs b/src/Sdk/DTExpressions/Expressions/EndsWithNode.cs deleted file mode 100644 index b09a561af..000000000 --- a/src/Sdk/DTExpressions/Expressions/EndsWithNode.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class EndsWithNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - String left = Parameters[0].EvaluateString(context) ?? String.Empty; - String right = Parameters[1].EvaluateString(context) ?? String.Empty; - return left.EndsWith(right, StringComparison.OrdinalIgnoreCase); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EqualNode.cs b/src/Sdk/DTExpressions/Expressions/EqualNode.cs deleted file mode 100644 index 2361c5c3d..000000000 --- a/src/Sdk/DTExpressions/Expressions/EqualNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class EqualNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].Evaluate(context).Equals(context, Parameters[1].Evaluate(context)); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EvaluationContext.cs b/src/Sdk/DTExpressions/Expressions/EvaluationContext.cs deleted file mode 100644 index 1d339c928..000000000 --- a/src/Sdk/DTExpressions/Expressions/EvaluationContext.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Logging; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class EvaluationContext - { - internal EvaluationContext( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options, - ExpressionNode node) - { - ArgumentUtility.CheckForNull(trace, nameof(trace)); - ArgumentUtility.CheckForNull(secretMasker, nameof(secretMasker)); - Trace = trace; - SecretMasker = secretMasker; - State = state; - - // Copy the options - options = new EvaluationOptions(copy: options); - if (options.MaxMemory == 0) - { - // Set a reasonable default max memory - options.MaxMemory = 1048576; // 1 mb - } - Options = options; - Memory = new EvaluationMemory(options.MaxMemory, node); - - m_traceResults = new Dictionary(); - m_traceMemory = new MemoryCounter(null, options.MaxMemory); - } - - public ITraceWriter Trace { get; } - - public ISecretMasker SecretMasker { get; } - - public Object State { get; } - - internal EvaluationMemory Memory { get; } - - internal EvaluationOptions Options { get; } - - internal void SetTraceResult( - ExpressionNode node, - EvaluationResult result) - { - // Remove if previously added. This typically should not happen. This could happen - // due to a badly authored function. So we'll handle it and track memory correctly. - if (m_traceResults.TryGetValue(node, out String oldValue)) - { - m_traceMemory.Remove(oldValue); - m_traceResults.Remove(node); - } - - // Check max memory - String value = ExpressionUtil.FormatValue(SecretMasker, result); - if (m_traceMemory.TryAdd(value)) - { - // Store the result - m_traceResults[node] = value; - } - } - - internal Boolean TryGetTraceResult(ExpressionNode node, out String value) - { - return m_traceResults.TryGetValue(node, out value); - } - - private readonly Dictionary m_traceResults = new Dictionary(); - private readonly MemoryCounter m_traceMemory; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EvaluationMemory.cs b/src/Sdk/DTExpressions/Expressions/EvaluationMemory.cs deleted file mode 100644 index e35985197..000000000 --- a/src/Sdk/DTExpressions/Expressions/EvaluationMemory.cs +++ /dev/null @@ -1,111 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Expressions -{ - /// - /// This is an internal class only. - /// - /// This class is used to track current memory consumption - /// across the entire expression evaluation. - /// - internal sealed class EvaluationMemory - { - internal EvaluationMemory( - Int32 maxBytes, - ExpressionNode node) - { - m_maxAmount = maxBytes; - m_node = node; - } - - internal void AddAmount( - Int32 depth, - Int32 bytes, - Boolean trimDepth = false) - { - // Trim deeper depths - if (trimDepth) - { - while (m_maxActiveDepth > depth) - { - var amount = m_depths[m_maxActiveDepth]; - - if (amount > 0) - { - // Sanity check - if (amount > m_totalAmount) - { - throw new InvalidOperationException("Bytes to subtract exceeds total bytes"); - } - - // Subtract from the total - checked - { - m_totalAmount -= amount; - } - - // Reset the amount - m_depths[m_maxActiveDepth] = 0; - } - - m_maxActiveDepth--; - } - } - - // Grow the depths - if (depth > m_maxActiveDepth) - { - // Grow the list - while (m_depths.Count <= depth) - { - m_depths.Add(0); - } - - // Adjust the max active depth - m_maxActiveDepth = depth; - } - - checked - { - // Add to the depth - m_depths[depth] += bytes; - - // Add to the total - m_totalAmount += bytes; - } - - // Check max - if (m_totalAmount > m_maxAmount) - { - throw new InvalidOperationException(ExpressionResources.ExceededAllowedMemory(m_node?.ConvertToExpression())); - } - } - - internal static Int32 CalculateBytes(Object obj) - { - if (obj is String str) - { - // This measurement doesn't have to be perfect - // https://codeblog.jonskeet.uk/2011/04/05/of-memory-and-strings/ - - checked - { - return c_stringBaseOverhead + ((str?.Length ?? 0) * sizeof(Char)); - } - } - else - { - return c_minObjectSize; - } - } - - private const Int32 c_minObjectSize = 24; - private const Int32 c_stringBaseOverhead = 26; - private readonly List m_depths = new List(); - private readonly Int32 m_maxAmount; - private readonly ExpressionNode m_node; - private Int32 m_maxActiveDepth = -1; - private Int32 m_totalAmount; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EvaluationOptions.cs b/src/Sdk/DTExpressions/Expressions/EvaluationOptions.cs deleted file mode 100644 index e42260056..000000000 --- a/src/Sdk/DTExpressions/Expressions/EvaluationOptions.cs +++ /dev/null @@ -1,43 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class EvaluationOptions - { - public EvaluationOptions() - { - } - - public EvaluationOptions(EvaluationOptions copy) - { - if (copy != null) - { - Converters = copy.Converters; - MaxMemory = copy.MaxMemory; - TimeZone = copy.TimeZone; - UseCollectionInterfaces = copy.UseCollectionInterfaces; - } - } - - /// - /// Converters allow types to be coerced into data that is friendly - /// for expression functions to operate on it. - /// - /// As each node in the expression tree is evaluated, converters are applied. - /// When a node's result matches a converter type, the result is intercepted - /// by the converter, and converter result is used instead. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public IDictionary> Converters { get; set; } - - public Int32 MaxMemory { get; set; } - - public TimeZoneInfo TimeZone { get; set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public Boolean UseCollectionInterfaces { get; set; } // Feature flag for now behavior - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EvaluationResult.cs b/src/Sdk/DTExpressions/Expressions/EvaluationResult.cs deleted file mode 100644 index cb1d1cb3e..000000000 --- a/src/Sdk/DTExpressions/Expressions/EvaluationResult.cs +++ /dev/null @@ -1,828 +0,0 @@ -using GitHub.DistributedTask.Expressions.CollectionAccessors; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using Newtonsoft.Json.Serialization; -using System; -using System.Collections.Generic; -using System.Collections.ObjectModel; -using System.ComponentModel; -using System.Globalization; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class EvaluationResult - { - internal EvaluationResult( - EvaluationContext context, - Int32 level, - Object val, - ValueKind kind, - Object raw) - : this(context, level, val, kind, raw, false) - { - } - - internal EvaluationResult( - EvaluationContext context, - Int32 level, - Object val, - ValueKind kind, - Object raw, - Boolean omitTracing) - { - m_level = level; - Value = val; - Kind = kind; - Raw = raw; - m_omitTracing = omitTracing; - - if (!omitTracing) - { - TraceValue(context); - } - } - - public ValueKind Kind { get; } - - /// - /// When a custom converter is applied to the node result, raw contains the original value - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public Object Raw { get; } - - public Object Value { get; } - - public int CompareTo( - EvaluationContext context, - EvaluationResult right) - { - Object leftValue; - ValueKind leftKind; - switch (Kind) - { - case ValueKind.Boolean: - case ValueKind.DateTime: - case ValueKind.Number: - case ValueKind.String: - case ValueKind.Version: - leftValue = Value; - leftKind = Kind; - break; - default: - leftValue = ConvertToNumber(context); // Will throw or succeed - leftKind = ValueKind.Number; - break; - } - - if (leftKind == ValueKind.Boolean) - { - Boolean b = right.ConvertToBoolean(context); - return ((Boolean)leftValue).CompareTo(b); - } - else if (leftKind == ValueKind.DateTime) - { - DateTimeOffset d = right.ConvertToDateTime(context); - return ((DateTimeOffset)leftValue).CompareTo(d); - } - else if (leftKind == ValueKind.Number) - { - Decimal d = right.ConvertToNumber(context); - return ((Decimal)leftValue).CompareTo(d); - } - else if (leftKind == ValueKind.String) - { - String s = right.ConvertToString(context); - return String.Compare(leftValue as String ?? String.Empty, s ?? String.Empty, StringComparison.OrdinalIgnoreCase); - } - else //if (leftKind == ValueKind.Version) - { - Version v = right.ConvertToVersion(context); - return (leftValue as Version).CompareTo(v); - } - } - - public Boolean ConvertToBoolean(EvaluationContext context) - { - Boolean result; - switch (Kind) - { - case ValueKind.Boolean: - return (Boolean)Value; // Not converted. Don't trace. - - case ValueKind.Number: - result = (Decimal)Value != 0m; // 0 converts to false, otherwise true. - TraceValue(context, result, ValueKind.Boolean); - return result; - - case ValueKind.String: - result = !String.IsNullOrEmpty(Value as String); - TraceValue(context, result, ValueKind.Boolean); - return result; - - case ValueKind.Array: - case ValueKind.DateTime: - case ValueKind.Object: - case ValueKind.Version: - result = true; - TraceValue(context, result, ValueKind.Boolean); - return result; - - case ValueKind.Null: - result = false; - TraceValue(context, result, ValueKind.Boolean); - return result; - - default: // Should never reach here. - throw new NotSupportedException($"Unable to convert value to Boolean. Unexpected value kind '{Kind}'."); - } - } - - public DateTimeOffset ConvertToDateTime(EvaluationContext context) - { - DateTimeOffset result; - if (TryConvertToDateTime(context, out result)) - { - return result; - } - - throw new TypeCastException(context?.SecretMasker, Value, fromKind: Kind, toKind: ValueKind.DateTime); - } - - public Object ConvertToNull(EvaluationContext context) - { - Object result; - if (TryConvertToNull(context, out result)) - { - return result; - } - - throw new TypeCastException(context?.SecretMasker, Value, fromKind: Kind, toKind: ValueKind.Null); - } - - public Decimal ConvertToNumber(EvaluationContext context) - { - Decimal result; - if (TryConvertToNumber(context, out result)) - { - return result; - } - - throw new TypeCastException(context?.SecretMasker, Value, fromKind: Kind, toKind: ValueKind.Number); - } - - public String ConvertToString(EvaluationContext context) - { - String result; - if (TryConvertToString(context, out result)) - { - return result; - } - - throw new TypeCastException(context?.SecretMasker, Value, fromKind: Kind, toKind: ValueKind.String); - } - - public Version ConvertToVersion(EvaluationContext context) - { - Version result; - if (TryConvertToVersion(context, out result)) - { - return result; - } - - throw new TypeCastException(context?.SecretMasker, Value, fromKind: Kind, toKind: ValueKind.Version); - } - - public Boolean Equals( - EvaluationContext context, - EvaluationResult right) - { - if (Kind == ValueKind.Boolean) - { - Boolean b = right.ConvertToBoolean(context); - return (Boolean)Value == b; - } - else if (Kind == ValueKind.DateTime) - { - DateTimeOffset d; - if (right.TryConvertToDateTime(context, out d)) - { - return (DateTimeOffset)Value == d; - } - } - else if (Kind == ValueKind.Number) - { - Decimal d; - if (right.TryConvertToNumber(context, out d)) - { - return (Decimal)Value == d; - } - } - else if (Kind == ValueKind.Version) - { - Version v; - if (right.TryConvertToVersion(context, out v)) - { - return (Version)Value == v; - } - } - else if (Kind == ValueKind.String) - { - String s; - if (right.TryConvertToString(context, out s)) - { - return String.Equals( - Value as String ?? String.Empty, - s ?? String.Empty, - StringComparison.OrdinalIgnoreCase); - } - } - else if (Kind == ValueKind.Array || Kind == ValueKind.Object) - { - return Kind == right.Kind && Object.ReferenceEquals(Value, right.Value); - } - else if (Kind == ValueKind.Null) - { - Object n; - if (right.TryConvertToNull(context, out n)) - { - return true; - } - } - - return false; - } - - public Boolean TryConvertToDateTime( - EvaluationContext context, - out DateTimeOffset result) - { - switch (Kind) - { - case ValueKind.DateTime: - result = (DateTimeOffset)Value; // Not converted. Don't trace again. - return true; - - case ValueKind.String: - if (TryParseDateTime(context?.Options, Value as String, out result)) - { - TraceValue(context, result, ValueKind.DateTime); - return true; - } - - TraceCoercionFailed(context, toKind: ValueKind.DateTime); - return false; - - case ValueKind.Array: - case ValueKind.Boolean: - case ValueKind.Null: - case ValueKind.Number: - case ValueKind.Object: - case ValueKind.Version: - result = default; - TraceCoercionFailed(context, toKind: ValueKind.DateTime); - return false; - - default: // Should never reach here. - throw new NotSupportedException($"Unable to determine whether value can be converted to Number. Unexpected value kind '{Kind}'."); - } - } - - public Boolean TryConvertToNull( - EvaluationContext context, - out Object result) - { - switch (Kind) - { - case ValueKind.Null: - result = null; // Not converted. Don't trace again. - return true; - - case ValueKind.String: - if (String.IsNullOrEmpty(Value as String)) - { - result = null; - TraceValue(context, result, ValueKind.Null); - return true; - } - - break; - } - - result = null; - TraceCoercionFailed(context, toKind: ValueKind.Null); - return false; - } - - public Boolean TryConvertToNumber( - EvaluationContext context, - out Decimal result) - { - switch (Kind) - { - case ValueKind.Boolean: - result = (Boolean)Value ? 1m : 0m; - TraceValue(context, result, ValueKind.Number); - return true; - - case ValueKind.Number: - result = (Decimal)Value; // Not converted. Don't trace again. - return true; - - case ValueKind.String: - String s = Value as String ?? String.Empty; - if (String.IsNullOrEmpty(s)) - { - result = 0m; - TraceValue(context, result, ValueKind.Number); - return true; - } - - if (Decimal.TryParse(s, s_numberStyles, CultureInfo.InvariantCulture, out result)) - { - TraceValue(context, result, ValueKind.Number); - return true; - } - - TraceCoercionFailed(context, toKind: ValueKind.Number); - return false; - - case ValueKind.Array: - case ValueKind.DateTime: - case ValueKind.Object: - case ValueKind.Version: - result = default(Decimal); - TraceCoercionFailed(context, toKind: ValueKind.Number); - return false; - - case ValueKind.Null: - result = 0m; - TraceValue(context, result, ValueKind.Number); - return true; - - default: // Should never reach here. - throw new NotSupportedException($"Unable to determine whether value can be converted to Number. Unexpected value kind '{Kind}'."); - } - } - - public Boolean TryConvertToString( - EvaluationContext context, - out String result) - { - switch (Kind) - { - case ValueKind.Boolean: - result = String.Format(CultureInfo.InvariantCulture, "{0}", Value); - TraceValue(context, result, ValueKind.String); - return true; - - case ValueKind.DateTime: - result = ((DateTimeOffset)Value).ToString(ExpressionConstants.DateTimeFormat, CultureInfo.InvariantCulture); - TraceValue(context, result, ValueKind.String); - return true; - - case ValueKind.Number: - result = ((Decimal)Value).ToString(ExpressionConstants.NumberFormat, CultureInfo.InvariantCulture); - TraceValue(context, result, ValueKind.String); - return true; - - case ValueKind.String: - result = Value as String; // Not converted. Don't trace. - return true; - - case ValueKind.Version: - result = (Value as Version).ToString(); - TraceValue(context, result, ValueKind.String); - return true; - - case ValueKind.Null: - result = String.Empty; - TraceValue(context, result, ValueKind.Null); - return true; - - case ValueKind.Array: - case ValueKind.Object: - result = null; - TraceCoercionFailed(context, toKind: ValueKind.String); - return false; - - default: // Should never reach here. - throw new NotSupportedException($"Unable to convert to String. Unexpected value kind '{Kind}'."); - } - } - - public Boolean TryConvertToVersion( - EvaluationContext context, - out Version result) - { - switch (Kind) - { - case ValueKind.Boolean: - result = null; - TraceCoercionFailed(context, toKind: ValueKind.Version); - return false; - - case ValueKind.Number: - if (Version.TryParse(ConvertToString(context), out result)) - { - TraceValue(context, result, ValueKind.Version); - return true; - } - - TraceCoercionFailed(context, toKind: ValueKind.Version); - return false; - - case ValueKind.String: - String s = Value as String ?? String.Empty; - if (Version.TryParse(s, out result)) - { - TraceValue(context, result, ValueKind.Version); - return true; - } - - TraceCoercionFailed(context, toKind: ValueKind.Version); - return false; - - case ValueKind.Version: - result = Value as Version; // Not converted. Don't trace again. - return true; - - case ValueKind.Array: - case ValueKind.DateTime: - case ValueKind.Object: - case ValueKind.Null: - result = null; - TraceCoercionFailed(context, toKind: ValueKind.Version); - return false; - - default: // Should never reach here. - throw new NotSupportedException($"Unable to convert to Version. Unexpected value kind '{Kind}'."); - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public Boolean TryGetCollectionInterface(out Object collection) - { - if ((Kind == ValueKind.Object || Kind == ValueKind.Array)) - { - var obj = Value; - if (obj is IReadOnlyObject) - { - collection = obj; - return true; - } - else if (obj is IDictionary dictionary1) - { - collection = new ReadOnlyDictionaryOfStringStringAccessor(new ReadOnlyDictionary(dictionary1)); - return true; - } - else if (obj is IDictionary dictionary2) - { - collection = new ReadOnlyDictionaryOfStringObjectAccessor(new ReadOnlyDictionary(dictionary2)); - return true; - } - else if (obj is IReadOnlyDictionary dictionary3) - { - collection = new ReadOnlyDictionaryOfStringStringAccessor(dictionary3); - return true; - } - else if (obj is IReadOnlyDictionary dictionary4) - { - collection = new ReadOnlyDictionaryOfStringObjectAccessor(dictionary4); - return true; - } - else if (obj is JObject jobject) - { - collection = new JObjectAccessor(jobject); - return true; - } - else if (obj is IReadOnlyArray) - { - collection = obj; - return true; - } - else if (obj is IList list1) - { - collection = new ListOfObjectAccessor(list1); - return true; - } - else if (obj is IReadOnlyList list2) - { - collection = new ReadOnlyListOfObjectAccessor(list2); - return true; - } - else if (obj is JArray jarray) - { - collection = new JArrayAccessor(jarray); - return true; - } - - var contract = s_serializer.Value.ContractResolver.ResolveContract(obj.GetType()); - if (contract is JsonObjectContract objectContract) - { - collection = new JsonObjectContractAccessor(objectContract, obj); - return true; - } - else if (contract is JsonDictionaryContract dictionaryContract && dictionaryContract.DictionaryKeyType == typeof(String)) - { - collection = new JsonDictionaryContractAccessor(dictionaryContract, obj); - return true; - } - } - - collection = null; - return false; - } - - /// - /// Useful for working with values that are not the direct evaluation result of a parameter. - /// This allows ExpressionNode authors to leverage the coercion and comparision functions - /// for any values. - /// - /// Also note, the value will be canonicalized (for example numeric types converted to decimal) and any - /// matching converters applied. - /// - public static EvaluationResult CreateIntermediateResult( - EvaluationContext context, - Object obj, - out ResultMemory conversionResultMemory) - { - var val = ExpressionUtil.ConvertToCanonicalValue(context?.Options, obj, out ValueKind kind, out Object raw, out conversionResultMemory); - return new EvaluationResult(context, 0, val, kind, raw, omitTracing: true); - } - - private void TraceCoercionFailed( - EvaluationContext context, - ValueKind toKind) - { - if (!m_omitTracing) - { - TraceVerbose(context, String.Format(CultureInfo.InvariantCulture, "=> Unable to coerce {0} to {1}.", Kind, toKind)); - } - } - - private void TraceValue(EvaluationContext context) - { - if (!m_omitTracing) - { - TraceValue(context, Value, Kind); - } - } - - private void TraceValue( - EvaluationContext context, - Object val, - ValueKind kind) - { - if (!m_omitTracing) - { - TraceVerbose(context, String.Concat("=> ", ExpressionUtil.FormatValue(context?.SecretMasker, val, kind))); - } - } - - private void TraceVerbose( - EvaluationContext context, - String message) - { - if (!m_omitTracing) - { - context?.Trace.Verbose(String.Empty.PadLeft(m_level * 2, '.') + (message ?? String.Empty)); - } - } - - private static Boolean TryParseDateTime( - EvaluationOptions options, - String s, - out DateTimeOffset result) - { - if (String.IsNullOrEmpty(s)) - { - result = default; - return false; - } - - s = s.Trim(); - var i = 0; - - // Year, month, day, hour, min, sec - if (!ReadInt32(s, 4, 4, ref i, out Int32 year) || - !ReadSeparator(s, ref i, new[] { '-', '/' }, out Char dateSeparator) || - !ReadInt32(s, 1, 2, ref i, out Int32 month) || - !ReadSeparator(s, ref i, dateSeparator) || - !ReadInt32(s, 1, 2, ref i, out Int32 day) || - !ReadSeparator(s, ref i, ' ', 'T') || - !ReadInt32(s, 1, 2, ref i, out Int32 hour) || - !ReadSeparator(s, ref i, ':') || - !ReadInt32(s, 1, 2, ref i, out Int32 minute) || - !ReadSeparator(s, ref i, ':') || - !ReadInt32(s, 1, 2, ref i, out Int32 second)) - { - result = default; - return false; - } - - // Fraction of second - Int32 ticks; - if (ExpressionUtil.SafeCharAt(s, i) == '.') - { - i++; - if (!ReadDigits(s, 1, 7, ref i, out String digits)) - { - result = default; - return false; - } - - if (digits.Length < 7) - { - digits = digits.PadRight(7, '0'); - } - - ticks = Int32.Parse(digits, NumberStyles.None, CultureInfo.InvariantCulture); - } - else - { - ticks = 0; - } - - TimeSpan offset; - - // End of string indicates local time zone - if (i >= s.Length) - { - // Determine the offset - var timeZone = options?.TimeZone ?? TimeZoneInfo.Local; - try - { - var dateTime = new DateTime(year, month, day, hour, minute, second, DateTimeKind.Unspecified); - offset = timeZone.GetUtcOffset(dateTime); - } - catch - { - result = default; - return false; - } - } - // Offset, then end of string - else if (!ReadOffset(s, ref i, out offset) || - i < s.Length) - { - result = default; - return false; - } - - // Construct the DateTimeOffset - try - { - result = new DateTimeOffset(year, month, day, hour, minute, second, offset); - } - catch - { - result = default; - return false; - } - - // Add fraction of second - if (ticks > 0) - { - result = result.AddTicks(ticks); - } - - return true; - } - - private static Boolean ReadDigits( - String str, - Int32 minLength, - Int32 maxLength, - ref Int32 index, - out String result) - { - var startIndex = index; - while (Char.IsDigit(ExpressionUtil.SafeCharAt(str, index))) - { - index++; - } - - var length = index - startIndex; - if (length < minLength || length > maxLength) - { - result = default; - return false; - } - - result = str.Substring(startIndex, length); - return true; - } - - private static Boolean ReadInt32( - String str, - Int32 minLength, - Int32 maxLength, - ref Int32 index, - out Int32 result) - { - if (!ReadDigits(str, minLength, maxLength, ref index, out String digits)) - { - result = default; - return false; - } - - result = Int32.Parse(digits, NumberStyles.None, CultureInfo.InvariantCulture); - return true; - } - - private static Boolean ReadSeparator( - String str, - ref Int32 index, - params Char[] allowed) - { - return ReadSeparator(str, ref index, allowed, out _); - } - - private static Boolean ReadSeparator( - String str, - ref Int32 index, - Char[] allowed, - out Char separator) - { - separator = ExpressionUtil.SafeCharAt(str, index++); - foreach (var a in allowed) - { - if (separator == a) - { - return true; - } - } - - separator = default; - return false; - } - - private static Boolean ReadOffset( - String str, - ref Int32 index, - out TimeSpan offset) - { - // Z indicates UTC - if (ExpressionUtil.SafeCharAt(str, index) == 'Z') - { - index++; - offset = TimeSpan.Zero; - return true; - } - - Boolean subtract; - - // Negative - if (ExpressionUtil.SafeCharAt(str, index) == '-') - { - index++; - subtract = true; - } - // Positive - else if (ExpressionUtil.SafeCharAt(str, index) == '+') - { - index++; - subtract = false; - } - // Invalid - else - { - offset = default; - return false; - } - - // Hour and minute - if (!ReadInt32(str, 1, 2, ref index, out Int32 hour) || - !ReadSeparator(str, ref index, ':') || - !ReadInt32(str, 1, 2, ref index, out Int32 minute)) - { - offset = default; - return false; - } - - // Construct the offset - if (subtract) - { - offset = TimeSpan.Zero.Subtract(new TimeSpan(hour, minute, 0)); - } - else - { - offset = new TimeSpan(hour, minute, 0); - } - - return true; - } - - private static readonly NumberStyles s_numberStyles = - NumberStyles.AllowDecimalPoint | - NumberStyles.AllowLeadingSign | - NumberStyles.AllowLeadingWhite | - NumberStyles.AllowThousands | - NumberStyles.AllowTrailingWhite; - private static readonly Lazy s_serializer = new Lazy(() => JsonUtility.CreateJsonSerializer()); - private readonly Int32 m_level; - private readonly Boolean m_omitTracing; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/EvaluationTraceWriter.cs b/src/Sdk/DTExpressions/Expressions/EvaluationTraceWriter.cs deleted file mode 100644 index 071317165..000000000 --- a/src/Sdk/DTExpressions/Expressions/EvaluationTraceWriter.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using GitHub.DistributedTask.Logging; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class EvaluationTraceWriter : ITraceWriter - { - public EvaluationTraceWriter(ITraceWriter trace, ISecretMasker secretMasker) - { - ArgumentUtility.CheckForNull(secretMasker, nameof(secretMasker)); - m_trace = trace; - m_secretMasker = secretMasker; - } - - public void Info(String message) - { - if (m_trace != null) - { - message = m_secretMasker.MaskSecrets(message); - m_trace.Info(message); - } - } - - public void Verbose(String message) - { - if (m_trace != null) - { - message = m_secretMasker.MaskSecrets(message); - m_trace.Verbose(message); - } - } - - private readonly ISecretMasker m_secretMasker; - private readonly ITraceWriter m_trace; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionConstants.cs b/src/Sdk/DTExpressions/Expressions/ExpressionConstants.cs deleted file mode 100644 index 54f7b7d3e..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionConstants.cs +++ /dev/null @@ -1,52 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Expressions -{ - internal static class ExpressionConstants - { - static ExpressionConstants() - { - AddFunction("and", 2, Int32.MaxValue); - AddFunction("coalesce", 2, Int32.MaxValue); - AddFunction("contains", 2, 2); - AddFunction("containsValue", 2, 2); - AddFunction("endsWith", 2, 2); - AddFunction("eq", 2, 2); - AddFunction("format", 1, Byte.MaxValue); - AddFunction("gt", 2, 2); - AddFunction("ge", 2, 2); - AddFunction("lt", 2, 2); - AddFunction("join", 2, 2); - AddFunction("le", 2, 2); - AddFunction("in", 2, Int32.MaxValue); - AddFunction("not", 1, 1); - AddFunction("ne", 2, 2); - AddFunction("notIn", 2, Int32.MaxValue); - AddFunction("or", 2, Int32.MaxValue); - AddFunction("startsWith", 2, 2); - AddFunction("xor", 2, 2); - } - - private static void AddFunction(String name, Int32 minParameters, Int32 maxParameters) - where T : FunctionNode, new() - { - WellKnownFunctions.Add(name, new FunctionInfo(name, minParameters, maxParameters)); - } - - internal static readonly String DateTimeFormat = @"yyyy\-MM\-dd\ HH\:mm\:sszzz"; - internal static readonly Int32 MaxDepth = 50; - internal static readonly Int32 MaxLength = 21000; // Under 85,000 large object heap threshold, even if .NET switches to UTF-32 - internal static readonly String NumberFormat = "0.#######"; - internal static readonly Dictionary WellKnownFunctions = new Dictionary(StringComparer.OrdinalIgnoreCase); - - // Punctuation - internal const Char StartIndex = '['; - internal const Char StartParameter = '('; - internal const Char EndIndex = ']'; - internal const Char EndParameter = ')'; - internal const Char Separator = ','; - internal const Char Dereference = '.'; - internal const Char Wildcard = '*'; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionException.cs b/src/Sdk/DTExpressions/Expressions/ExpressionException.cs deleted file mode 100644 index ef2623cd6..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionException.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using GitHub.DistributedTask.Logging; - -namespace GitHub.DistributedTask.Expressions -{ - public class ExpressionException : Exception - { - internal ExpressionException(ISecretMasker secretMasker, String message) - { - if (secretMasker != null) - { - message = secretMasker.MaskSecrets(message); - } - - m_message = message; - } - - public override String Message => m_message; - - private readonly String m_message; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionNode.cs b/src/Sdk/DTExpressions/Expressions/ExpressionNode.cs deleted file mode 100644 index e08b8d90e..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionNode.cs +++ /dev/null @@ -1,494 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Reflection; -using GitHub.DistributedTask.Logging; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class ExpressionNode : IExpressionNode - { - internal ContainerNode Container { get; set; } - - internal Int32 Level { get; private set; } - - /// - /// The name is used for tracing. Normally the parser will set the name. However if a node - /// is added manually, then the name may not be set and will fallback to the type name. - /// - protected internal String Name - { - get - { - return !String.IsNullOrEmpty(m_name) ? m_name : this.GetType().Name; - } - - set - { - m_name = value; - } - } - - /// - /// Indicates whether the evalation result should be stored on the context and used - /// when the realized result is traced. - /// - protected abstract Boolean TraceFullyRealized { get; } - - internal abstract String ConvertToExpression(); - - internal abstract String ConvertToRealizedExpression(EvaluationContext context); - - /// - /// Evaluates the node - /// - protected virtual Object EvaluateCore(EvaluationContext context) - { - throw new InvalidOperationException($"Method {nameof(EvaluateCore)} not implemented"); - } - - /// - /// Evaluates the node - /// - /// The current expression context - /// - /// Helps determine how much memory is being consumed across the evaluation of the expression. - /// - protected virtual Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - return EvaluateCore(context); - } - - /// - /// INode entry point. - /// - public T Evaluate( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options = null) - { - if (Container != null) - { - // Do not localize. This is an SDK consumer error. - throw new NotSupportedException($"Expected {nameof(IExpressionNode)}.{nameof(Evaluate)} to be called on root node only."); - } - - ISecretMasker originalSecretMasker = secretMasker; - try - { - secretMasker = secretMasker?.Clone() ?? new SecretMasker(); - trace = new EvaluationTraceWriter(trace, secretMasker); - var context = new EvaluationContext(trace, secretMasker, state, options, this); - trace.Info($"Evaluating: {ConvertToExpression()}"); - - // String - if (typeof(T).Equals(typeof(String))) - { - String stringResult = EvaluateString(context); - TraceTreeResult(context, stringResult, ValueKind.String); - return (T)(Object)stringResult; - } - // Boolean - else if (typeof(T).Equals(typeof(Boolean))) - { - Boolean booleanResult = EvaluateBoolean(context); - TraceTreeResult(context, booleanResult, ValueKind.Boolean); - return (T)(Object)booleanResult; - } - // Version - else if (typeof(T).Equals(typeof(Version))) - { - Version versionResult = EvaluateVersion(context); - TraceTreeResult(context, versionResult, ValueKind.Version); - return (T)(Object)versionResult; - } - // DateTime types - else if (typeof(T).Equals(typeof(DateTimeOffset))) - { - DateTimeOffset dateTimeResult = EvaluateDateTime(context); - TraceTreeResult(context, dateTimeResult, ValueKind.DateTime); - return (T)(Object)dateTimeResult; - } - else if (typeof(T).Equals(typeof(DateTime))) - { - DateTimeOffset dateTimeResult = EvaluateDateTime(context); - TraceTreeResult(context, dateTimeResult, ValueKind.DateTime); - return (T)(Object)dateTimeResult.UtcDateTime; - } - - TypeInfo typeInfo = typeof(T).GetTypeInfo(); - if (typeInfo.IsPrimitive) - { - // Decimal - if (typeof(T).Equals(typeof(Decimal))) - { - Decimal decimalResult = EvaluateNumber(context); - TraceTreeResult(context, decimalResult, ValueKind.Number); - return (T)(Object)decimalResult; - } - // Other numeric types - else if (typeof(T).Equals(typeof(Byte)) || - typeof(T).Equals(typeof(SByte)) || - typeof(T).Equals(typeof(Int16)) || - typeof(T).Equals(typeof(UInt16)) || - typeof(T).Equals(typeof(Int32)) || - typeof(T).Equals(typeof(UInt32)) || - typeof(T).Equals(typeof(Int64)) || - typeof(T).Equals(typeof(UInt64)) || - typeof(T).Equals(typeof(Single)) || - typeof(T).Equals(typeof(Double))) - { - Decimal decimalResult = EvaluateNumber(context); - trace.Verbose($"Converting expression result to type {typeof(T).Name}"); - try - { - T numericResult = (T)Convert.ChangeType(decimalResult, typeof(T)); - - // Note, the value is converted back to decimal before tracing, in order to leverage the same - // util-formatting method used in other places. - TraceTreeResult(context, Convert.ToDecimal((Object)numericResult), ValueKind.Number); - - return numericResult; - } - catch (Exception exception) - { - context.Trace.Verbose($"Failed to convert the result number into the type {typeof(T).Name}. {exception.Message}"); - throw new TypeCastException( - secretMasker, - value: decimalResult, - fromKind: ValueKind.Number, - toType: typeof(T), - error: exception.Message); - } - } - } - - // Generic evaluate - EvaluationResult result = Evaluate(context); - TraceTreeResult(context, result.Value, result.Kind); - - // JToken - if (typeof(T).Equals(typeof(JToken))) - { - if (result.Value is null) - { - return default; - } - else if (result.Value is JToken) - { - return (T)result.Value; - } - else - { - return (T)(Object)JToken.FromObject(result.Value, JsonUtility.CreateJsonSerializer()); - } - } - // Object or Array - else if (result.Kind == ValueKind.Object || result.Kind == ValueKind.Array) - { - Type resultType = result.Value.GetType(); - context.Trace.Verbose($"Result type: {resultType.Name}"); - if (typeInfo.IsAssignableFrom(resultType.GetTypeInfo())) - { - return (T)result.Value; - } - else - { - context.Trace.Verbose($"Unable to assign result to the type {typeof(T).Name}"); - throw new TypeCastException(fromType: resultType, toType: typeof(T)); - } - } - // Null - else if (result.Kind == ValueKind.Null) - { - return default; - } - // String - else if (result.Kind == ValueKind.String) - { - // Treat empty string as null - String stringResult = result.Value as String; - if (String.IsNullOrEmpty(stringResult)) - { - return default; - } - - // Otherwise deserialize - try - { - return JsonUtility.FromString(stringResult); - } - catch (Exception exception) when (exception is JsonReaderException || exception is JsonSerializationException) - { - context.Trace.Verbose($"Failed to json-deserialize the result string into the type {typeof(T).Name}. {exception.Message}"); - throw new TypeCastException( - context.SecretMasker, - value: stringResult, - fromKind: ValueKind.String, - toType: typeof(T), - error: exception.Message); - } - } - else - { - context.Trace.Verbose($"Unable to convert from kind {result.Kind} to the type {typeof(T).Name}"); - throw new TypeCastException( - context.SecretMasker, - value: result.Value, - fromKind: result.Kind, - toType: typeof(T)); - } - } - finally - { - if (secretMasker != null && secretMasker != originalSecretMasker) - { - (secretMasker as IDisposable)?.Dispose(); - secretMasker = null; - } - } - } - - /// - /// INode entry point. - /// - public Object Evaluate( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options = null) - { - return Evaluate(trace, secretMasker, state, options, out _, out _); - } - - /// - /// INode entry point. - /// - public Boolean EvaluateBoolean( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state) - { - return Evaluate(trace, secretMasker, state); - } - - /// - /// INode entry point. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public EvaluationResult EvaluateResult( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options) - { - var val = Evaluate(trace, secretMasker, state, options, out ValueKind kind, out Object raw); - return new EvaluationResult(null, 0, val, kind, raw, omitTracing: true); - } - - /// - /// This function is intended only for ExpressionNode authors to call. The EvaluationContext - /// caches result-state specific to the evaluation instance. - /// - public EvaluationResult Evaluate(EvaluationContext context) - { - // Evaluate - Level = Container == null ? 0 : Container.Level + 1; - TraceVerbose(context, Level, $"Evaluating {Name}:"); - var coreResult = EvaluateCore(context, out ResultMemory coreMemory); - - if (coreMemory == null) - { - coreMemory = new ResultMemory(); - } - - // Convert to canonical value - var val = ExpressionUtil.ConvertToCanonicalValue(context.Options, coreResult, out ValueKind kind, out Object raw, out ResultMemory conversionMemory); - - // The depth can be safely trimmed when the total size of the core result is known, - // or when the total size of the core result can easily be determined. - var trimDepth = coreMemory.IsTotal || (Object.ReferenceEquals(raw, null) && s_simpleKinds.Contains(kind)); - - // Account for the memory overhead of the core result - var coreBytes = coreMemory.Bytes ?? EvaluationMemory.CalculateBytes(raw ?? val); - context.Memory.AddAmount(Level, coreBytes, trimDepth); - - // Account for the memory overhead of the conversion result - if (!Object.ReferenceEquals(raw, null)) - { - if (conversionMemory == null) - { - conversionMemory = new ResultMemory(); - } - - var conversionBytes = conversionMemory.Bytes ?? EvaluationMemory.CalculateBytes(val); - context.Memory.AddAmount(Level, conversionBytes); - } - - var result = new EvaluationResult(context, Level, val, kind, raw); - - // Store the trace result - if (this.TraceFullyRealized) - { - context.SetTraceResult(this, result); - } - - return result; - } - - /// - /// This function is intended only for ExpressionNode authors to call during evaluation. - /// The EvaluationContext caches result-state specific to the evaluation instance. - /// - public Boolean EvaluateBoolean(EvaluationContext context) - { - return Evaluate(context).ConvertToBoolean(context); - } - - /// - /// This function is intended only for ExpressionNode authors to call during evaluation. - /// The EvaluationContext caches result-state specific to the evaluation instance. - /// - public DateTimeOffset EvaluateDateTime(EvaluationContext context) - { - return Evaluate(context).ConvertToDateTime(context); - } - - /// - /// This function is intended only for ExpressionNode authors to call during evaluation. - /// The EvaluationContext caches result-state specific to the evaluation instance. - /// - public Decimal EvaluateNumber(EvaluationContext context) - { - return Evaluate(context).ConvertToNumber(context); - } - - /// - /// This function is intended only for ExpressionNode authors to call during evaluation. - /// The EvaluationContext caches result-state specific to the evaluation instance. - /// - public String EvaluateString(EvaluationContext context) - { - return Evaluate(context).ConvertToString(context); - } - - /// - /// This function is intended only for ExpressionNode authors to call during evaluation. - /// The EvaluationContext caches result-state specific to the evaluation instance. - /// - public Version EvaluateVersion(EvaluationContext context) - { - return Evaluate(context).ConvertToVersion(context); - } - - public virtual IEnumerable GetParameters() where T : IExpressionNode - { - return new T[0]; - } - - protected MemoryCounter CreateMemoryCounter(EvaluationContext context) - { - return new MemoryCounter(this, context.Options.MaxMemory); - } - - private Object Evaluate( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options, - out ValueKind kind, - out Object raw) - { - if (Container != null) - { - // Do not localize. This is an SDK consumer error. - throw new NotSupportedException($"Expected {nameof(IExpressionNode)}.{nameof(Evaluate)} to be called on root node only."); - } - - ISecretMasker originalSecretMasker = secretMasker; - try - { - // Evaluate - secretMasker = secretMasker?.Clone() ?? new SecretMasker(); - trace = new EvaluationTraceWriter(trace, secretMasker); - var context = new EvaluationContext(trace, secretMasker, state, options, this); - trace.Info($"Evaluating: {ConvertToExpression()}"); - EvaluationResult result = Evaluate(context); - - // Trace the result - TraceTreeResult(context, result.Value, result.Kind); - - kind = result.Kind; - raw = result.Raw; - return result.Value; - } - finally - { - if (secretMasker != null && secretMasker != originalSecretMasker) - { - (secretMasker as IDisposable)?.Dispose(); - secretMasker = null; - } - } - } - - private void TraceTreeResult( - EvaluationContext context, - Object result, - ValueKind kind) - { - // Get the realized expression - String realizedExpression = ConvertToRealizedExpression(context); - - // Format the result - String traceValue = ExpressionUtil.FormatValue(context.SecretMasker, result, kind); - - // Only trace the realized expression if it is meaningfully different - if (!String.Equals(realizedExpression, traceValue, StringComparison.Ordinal)) - { - if (kind == ValueKind.Number && - String.Equals(realizedExpression, $"'{traceValue}'", StringComparison.Ordinal)) - { - // Don't bother tracing the realized expression when the result is a number and the - // realized expresion is a precisely matching string. - } - else - { - context.Trace.Info($"Expanded: {realizedExpression}"); - } - } - - // Always trace the result - context.Trace.Info($"Result: {traceValue}"); - } - - private static void TraceVerbose( - EvaluationContext context, - Int32 level, - String message) - { - context.Trace.Verbose(String.Empty.PadLeft(level * 2, '.') + (message ?? String.Empty)); - } - - private static readonly ValueKind[] s_simpleKinds = new[] - { - ValueKind.Boolean, - ValueKind.DateTime, - ValueKind.Null, - ValueKind.Number, - ValueKind.String, - ValueKind.Version, - }; - - private String m_name; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionParser.cs b/src/Sdk/DTExpressions/Expressions/ExpressionParser.cs deleted file mode 100644 index 9e562f388..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionParser.cs +++ /dev/null @@ -1,547 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ExpressionParser - { - public ExpressionParser(): this(null) - { - } - - public ExpressionParser(ExpressionParserOptions options) - { - m_parserOptions = options ?? new ExpressionParserOptions(); - } - - public IExpressionNode CreateTree( - String expression, - ITraceWriter trace, - IEnumerable namedValues, - IEnumerable functions) - { - var context = new ParseContext(expression, trace, namedValues, functions, allowUnknownKeywords: false, allowKeywordHyphens: m_parserOptions.AllowHyphens); - context.Trace.Info($"Parsing expression: <{expression}>"); - return CreateTree(context); - } - - public void ValidateSyntax( - String expression, - ITraceWriter trace) - { - var context = new ParseContext(expression, trace, namedValues: null, functions: null, allowUnknownKeywords: true, allowKeywordHyphens: m_parserOptions.AllowHyphens); - context.Trace.Info($"Validating expression syntax: <{expression}>"); - CreateTree(context); - } - - private static IExpressionNode CreateTree(ParseContext context) - { - while (TryGetNextToken(context)) - { - switch (context.Token.Kind) - { - // Punctuation - case TokenKind.StartIndex: - HandleStartIndex(context); - break; - case TokenKind.EndIndex: - HandleEndIndex(context); - break; - case TokenKind.EndParameter: - HandleEndParameter(context); - break; - case TokenKind.Separator: - HandleSeparator(context); - break; - case TokenKind.Dereference: - HandleDereference(context); - break; - case TokenKind.Wildcard: - HandleWildcard(context); - break; - - // Functions - case TokenKind.WellKnownFunction: - case TokenKind.ExtensionFunction: - HandleFunction(context); - break; - - // Leaf values - case TokenKind.Boolean: - case TokenKind.Number: - case TokenKind.Version: - case TokenKind.String: - case TokenKind.ExtensionNamedValue: - HandleValue(context); - break; - - // Unknown keyword - case TokenKind.UnknownKeyword: - HandleUnknownKeyword(context); - break; - - // Malformed - case TokenKind.Unrecognized: - throw new ParseException(ParseExceptionKind.UnrecognizedValue, context.Token, context.Expression); - - // Unexpected - case TokenKind.PropertyName: // PropertyName should never reach here (HandleDereference reads next token). - case TokenKind.StartParameter: // StartParameter is only expected by HandleFunction. - default: - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // Validate depth. - if (context.Containers.Count >= ExpressionConstants.MaxDepth) - { - throw new ParseException(ParseExceptionKind.ExceededMaxDepth, token: null, expression: context.Expression); - } - } - - // Validate all containers were closed. - if (context.Containers.Count > 0) - { - ContainerInfo container = context.Containers.Peek(); - if (container.Node is FunctionNode) - { - throw new ParseException(ParseExceptionKind.UnclosedFunction, container.Token, context.Expression); - } - else - { - throw new ParseException(ParseExceptionKind.UnclosedIndexer, container.Token, context.Expression); - } - } - - return context.Root; - } - - private static bool TryGetNextToken(ParseContext context) - { - context.LastToken = context.Token; - if (context.Lexer.TryGetNextToken(ref context.Token)) - { - // Adjust indent level. - int indentLevel = context.Containers.Count; - if (indentLevel > 0) - { - switch (context.Token.Kind) - { - case TokenKind.StartParameter: - case TokenKind.EndParameter: - case TokenKind.EndIndex: - indentLevel--; - break; - } - } - - String indent = String.Empty.PadRight(indentLevel * 2, '.'); - switch (context.Token.Kind) - { - // Literal values - case TokenKind.Boolean: - context.Trace.Verbose($"{indent}{ExpressionUtil.FormatValue(null, context.Token.ParsedValue, ValueKind.Boolean)}"); - break; - case TokenKind.Number: - context.Trace.Verbose($"{indent}{ExpressionUtil.FormatValue(null, context.Token.ParsedValue, ValueKind.Number)}"); - break; - case TokenKind.Version: - context.Trace.Verbose($"{indent}{ExpressionUtil.FormatValue(null, context.Token.ParsedValue, ValueKind.Version)}"); - break; - case TokenKind.String: - context.Trace.Verbose($"{indent}{ExpressionUtil.FormatValue(null, context.Token.ParsedValue, ValueKind.String)}"); - break; - // Property or unrecognized - case TokenKind.PropertyName: - case TokenKind.Unrecognized: - context.Trace.Verbose($"{indent}{context.Token.Kind} {ExpressionUtil.FormatValue(null, context.Token.RawValue, ValueKind.String)}"); - break; - // Function or punctuation - case TokenKind.WellKnownFunction: - case TokenKind.ExtensionFunction: - case TokenKind.ExtensionNamedValue: - case TokenKind.Wildcard: - case TokenKind.UnknownKeyword: - case TokenKind.StartIndex: - case TokenKind.StartParameter: - case TokenKind.EndIndex: - case TokenKind.EndParameter: - case TokenKind.Separator: - case TokenKind.Dereference: - context.Trace.Verbose($"{indent}{context.Token.RawValue}"); - break; - default: // Should never reach here. - throw new NotSupportedException($"Unexpected token kind: {context.Token.Kind}"); - } - - return true; - } - - return false; - } - - private static void HandleStartIndex(ParseContext context) - { - // Validate follows ")", "]", "*", or a property name. - if (context.LastToken == null || - (context.LastToken.Kind != TokenKind.EndParameter && context.LastToken.Kind != TokenKind.EndIndex && context.LastToken.Kind != TokenKind.PropertyName && context.LastToken.Kind != TokenKind.ExtensionNamedValue && context.LastToken.Kind != TokenKind.UnknownKeyword && context.LastToken.Kind != TokenKind.Wildcard)) - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // Wrap the object being indexed into. - var indexer = new IndexerNode(); - ExpressionNode obj = null; - if (context.Containers.Count > 0) - { - ContainerNode container = context.Containers.Peek().Node; - Int32 objIndex = container.Parameters.Count - 1; - obj = container.Parameters[objIndex]; - container.ReplaceParameter(objIndex, indexer); - } - else - { - obj = context.Root; - context.Root = indexer; - } - - indexer.AddParameter(obj); - - // Update the container stack. - context.Containers.Push(new ContainerInfo() { Node = indexer, Token = context.Token }); - } - - private static void HandleDereference(ParseContext context) - { - // Validate follows ")", "]", "*", or a property name. - if (context.LastToken == null || - (context.LastToken.Kind != TokenKind.EndParameter && context.LastToken.Kind != TokenKind.EndIndex && context.LastToken.Kind != TokenKind.PropertyName && context.LastToken.Kind != TokenKind.ExtensionNamedValue && context.LastToken.Kind != TokenKind.UnknownKeyword && context.LastToken.Kind != TokenKind.Wildcard)) - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // Wrap the object being indexed into. - var indexer = new IndexerNode(); - ExpressionNode obj = null; - if (context.Containers.Count > 0) - { - ContainerNode container = context.Containers.Peek().Node; - Int32 objIndex = container.Parameters.Count - 1; - obj = container.Parameters[objIndex]; - container.ReplaceParameter(objIndex, indexer); - } - else - { - obj = context.Root; - context.Root = indexer; - } - - indexer.AddParameter(obj); - - // Validate a token follows. - if (!TryGetNextToken(context)) - { - throw new ParseException(ParseExceptionKind.ExpectedPropertyName, context.LastToken, context.Expression); - } - - if (context.Token.Kind == TokenKind.PropertyName) - { - indexer.AddParameter(new LiteralValueNode(context.Token.RawValue)); - } - else if (context.Token.Kind == TokenKind.Wildcard) - { - // For a wildcard we add a third parameter, a boolean set to true, so that we know it's a wildcard. - indexer.AddParameter(new LiteralValueNode(context.Token.RawValue)); - indexer.AddParameter(new LiteralValueNode(true)); - } - else - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - } - - private static void HandleWildcard(ParseContext context) - { - // Validate follows "[". - if (context.LastToken == null || - context.LastToken.Kind != TokenKind.StartIndex) - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // When we have a wildcard, we add the wildcard and also third boolean parameter set to true. - // This lets us differentiate downstream from '*'. - context.Containers.Peek().Node.AddParameter(new LiteralValueNode(context.Token.RawValue)); - context.Containers.Peek().Node.AddParameter(new LiteralValueNode(true)); - } - - private static void HandleEndParameter(ParseContext context) - { - ContainerInfo container = context.Containers.Count > 0 ? context.Containers.Peek() : null; // Validate: - if (container == null || // 1) Container is not null - !(container.Node is FunctionNode) || // 2) Container is a function - container.Node.Parameters.Count < GetMinParamCount(context, container.Token) || // 3) Not below min param threshold - container.Node.Parameters.Count > GetMaxParamCount(context, container.Token) || // 4) Not above max param threshold - context.LastToken.Kind == TokenKind.Separator) // 5) Last token is not a separator - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - context.Containers.Pop(); - } - - private static void HandleEndIndex(ParseContext context) - { - IndexerNode indexer = context.Containers.Count > 0 ? context.Containers.Peek().Node as IndexerNode : null; - // // Validate: - if (indexer == null || // 1) Container is an indexer - !(indexer.Parameters.Count == 2 || indexer.Parameters.Count == 3)) // 2) Can be 2 or 3 parameters. It's 3 parameters when we are using a filtered array since we - // set a boolean along with the wildcard. - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - context.Containers.Pop(); - } - - private static void HandleUnknownKeyword(ParseContext context) - { - // Validate. - if (!context.AllowUnknownKeywords) - { - throw new ParseException(ParseExceptionKind.UnrecognizedValue, context.Token, context.Expression); - } - - // Try handle function. - if (HandleFunction(context, bestEffort: true)) - { - return; - } - - // Handle named value. - HandleValue(context); - } - - private static void HandleValue(ParseContext context) - { - // Validate either A) is the first token OR B) follows "[" "(" or ",". - if (context.LastToken != null && - context.LastToken.Kind != TokenKind.StartIndex && - context.LastToken.Kind != TokenKind.StartParameter && - context.LastToken.Kind != TokenKind.Separator) - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // Create the node. - ExpressionNode node; - switch (context.Token.Kind) - { - case TokenKind.ExtensionNamedValue: - String name = context.Token.RawValue; - node = context.ExtensionNamedValues[name].CreateNode(); - node.Name = name; - break; - case TokenKind.UnknownKeyword: - node = new UnknownNamedValueNode(); - node.Name = context.Token.RawValue; - break; - default: - node = new LiteralValueNode(context.Token.ParsedValue); - break; - } - - // Update the tree. - if (context.Root == null) - { - context.Root = node; - } - else - { - context.Containers.Peek().Node.AddParameter(node); - } - } - - private static void HandleSeparator(ParseContext context) - { - ContainerInfo container = context.Containers.Count > 0 ? context.Containers.Peek() : null; // Validate: - if (container == null || // 1) Container is not null - !(container.Node is FunctionNode) || // 2) Container is a function - container.Node.Parameters.Count < 1 || // 3) At least one parameter - container.Node.Parameters.Count >= GetMaxParamCount(context, container.Token) ||// 4) Under max parameters threshold - context.LastToken.Kind == TokenKind.Separator) // 5) Last token is not a separator - { - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - } - - private static Boolean HandleFunction( - ParseContext context, - Boolean bestEffort = false) - { - // Validate either A) is first token OR B) follows "," or "[" or "(". - if (context.LastToken != null && - (context.LastToken.Kind != TokenKind.Separator && - context.LastToken.Kind != TokenKind.StartIndex && - context.LastToken.Kind != TokenKind.StartParameter)) - { - if (bestEffort) - { - return false; - } - - throw new ParseException(ParseExceptionKind.UnexpectedSymbol, context.Token, context.Expression); - } - - // Validate '(' follows. - if (bestEffort) - { - Token nextToken = null; - if (!context.Lexer.TryPeekNextToken(ref nextToken) || nextToken.Kind != TokenKind.StartParameter) - { - return false; - } - - TryGetNextToken(context); - } - else if (!TryGetNextToken(context) || context.Token.Kind != TokenKind.StartParameter) - { - throw new ParseException(ParseExceptionKind.ExpectedStartParameter, context.LastToken, context.Expression); - } - - // Create the node. - FunctionNode node; - String name = context.LastToken.RawValue; - switch (context.LastToken.Kind) - { - case TokenKind.WellKnownFunction: - node = ExpressionConstants.WellKnownFunctions[name].CreateNode(); - node.Name = name; - break; - case TokenKind.ExtensionFunction: - node = context.ExtensionFunctions[name].CreateNode(); - node.Name = name; - break; - case TokenKind.UnknownKeyword: - node = new UnknownFunctionNode(); - node.Name = name; - break; - default: - // Should never reach here. - throw new NotSupportedException($"Unexpected function token name: '{context.LastToken.Kind}'"); - } - - // Update the tree. - if (context.Root == null) - { - context.Root = node; - } - else - { - context.Containers.Peek().Node.AddParameter(node); - } - - // Update the container stack. - context.Containers.Push(new ContainerInfo() { Node = node, Token = context.LastToken }); - return true; - } - - private static int GetMinParamCount( - ParseContext context, - Token token) - { - switch (token.Kind) - { - case TokenKind.WellKnownFunction: - return ExpressionConstants.WellKnownFunctions[token.RawValue].MinParameters; - case TokenKind.ExtensionFunction: - return context.ExtensionFunctions[token.RawValue].MinParameters; - case TokenKind.UnknownKeyword: - return 0; - default: // Should never reach here. - throw new NotSupportedException($"Unexpected token kind '{token.Kind}'. Unable to determine min param count."); - } - } - - private static Int32 GetMaxParamCount( - ParseContext context, - Token token) - { - switch (token.Kind) - { - case TokenKind.WellKnownFunction: - return ExpressionConstants.WellKnownFunctions[token.RawValue].MaxParameters; - case TokenKind.ExtensionFunction: - return context.ExtensionFunctions[token.RawValue].MaxParameters; - case TokenKind.UnknownKeyword: - return Int32.MaxValue; - default: // Should never reach here. - throw new NotSupportedException($"Unexpected token kind '{token.Kind}'. Unable to determine max param count."); - } - } - - private ExpressionParserOptions m_parserOptions; - - private sealed class ContainerInfo - { - public ContainerNode Node { get; set; } - - public Token Token { get; set; } - } - - private sealed class ParseContext - { - public readonly Boolean AllowUnknownKeywords; - public readonly Stack Containers = new Stack(); - public readonly String Expression; - public readonly Dictionary ExtensionFunctions = new Dictionary(StringComparer.OrdinalIgnoreCase); - public readonly Dictionary ExtensionNamedValues = new Dictionary(StringComparer.OrdinalIgnoreCase); - public readonly LexicalAnalyzer Lexer; - public readonly ITraceWriter Trace; - public Token Token; - public Token LastToken; - public ExpressionNode Root; - - public ParseContext( - String expression, - ITraceWriter trace, - IEnumerable namedValues, - IEnumerable functions, - Boolean allowUnknownKeywords = false, - Boolean allowKeywordHyphens = false) - { - Expression = expression ?? String.Empty; - if (Expression.Length > ExpressionConstants.MaxLength) - { - throw new ParseException(ParseExceptionKind.ExceededMaxLength, token: null, expression: Expression); - } - - Trace = trace ?? new NoOperationTraceWriter(); - foreach (INamedValueInfo namedValueInfo in (namedValues ?? new INamedValueInfo[0])) - { - ExtensionNamedValues.Add(namedValueInfo.Name, namedValueInfo); - } - - foreach (IFunctionInfo functionInfo in (functions ?? new IFunctionInfo[0])) - { - ExtensionFunctions.Add(functionInfo.Name, functionInfo); - } - - AllowUnknownKeywords = allowUnknownKeywords; - Lexer = new LexicalAnalyzer(Expression, namedValues: ExtensionNamedValues.Keys, functions: ExtensionFunctions.Keys, allowKeywordHyphens); - } - - private class NoOperationTraceWriter : ITraceWriter - { - public void Info(String message) - { - } - - public void Verbose(String message) - { - } - } - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionParserOptions.cs b/src/Sdk/DTExpressions/Expressions/ExpressionParserOptions.cs deleted file mode 100644 index 49e267e82..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionParserOptions.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public sealed class ExpressionParserOptions - { - public Boolean AllowHyphens - { - get; - set; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ExpressionUtil.cs b/src/Sdk/DTExpressions/Expressions/ExpressionUtil.cs deleted file mode 100644 index ffb8219d5..000000000 --- a/src/Sdk/DTExpressions/Expressions/ExpressionUtil.cs +++ /dev/null @@ -1,211 +0,0 @@ -using System; -using System.ComponentModel; -using System.Globalization; -using System.Reflection; -using GitHub.DistributedTask.Logging; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - internal static class ExpressionUtil - { - internal static Object ConvertToCanonicalValue( - EvaluationOptions options, - Object val, - out ValueKind kind, - out Object raw, - out ResultMemory conversionResultMemory) - { - // Apply converter - if (options?.Converters?.Count > 0 && - !Object.ReferenceEquals(val, null) && - options.Converters.TryGetValue(val.GetType(), out Converter convert)) - { - raw = val; - var conversionResult = convert(val); - val = conversionResult.Result; - conversionResultMemory = conversionResult.ResultMemory; - } - else - { - raw = null; - conversionResultMemory = null; - } - - if (Object.ReferenceEquals(val, null)) - { - kind = ValueKind.Null; - return null; - } - else if (val is IString str) - { - kind = ValueKind.String; - return str.GetString(); - } - else if (val is IBoolean booleanValue) - { - kind = ValueKind.Boolean; - return booleanValue.GetBoolean(); - } - else if (val is INumber num) - { - kind = ValueKind.Number; - return num.GetNumber(); - } - else if (val is JToken) - { - var jtoken = val as JToken; - switch (jtoken.Type) - { - case JTokenType.Array: - kind = ValueKind.Array; - return jtoken; - case JTokenType.Boolean: - kind = ValueKind.Boolean; - return jtoken.ToObject(); - case JTokenType.Float: - case JTokenType.Integer: - kind = ValueKind.Number; - // todo: test the extents of the conversion - return jtoken.ToObject(); - case JTokenType.Null: - kind = ValueKind.Null; - return null; - case JTokenType.Object: - kind = ValueKind.Object; - return jtoken; - case JTokenType.String: - kind = ValueKind.String; - return jtoken.ToObject(); - } - } - else if (val is String) - { - kind = ValueKind.String; - return val; - } - else if (val is Version) - { - kind = ValueKind.Version; - return val; - } - else if (!val.GetType().GetTypeInfo().IsClass) - { - if (val is Boolean) - { - kind = ValueKind.Boolean; - return val; - } - else if (val is DateTimeOffset) - { - kind = ValueKind.DateTime; - return val; - } - else if (val is DateTime dateTime) - { - kind = ValueKind.DateTime; - switch (dateTime.Kind) - { - // When Local: convert to preferred time zone - case DateTimeKind.Local: - var targetTimeZone = options?.TimeZone ?? TimeZoneInfo.Local; - var localDateTimeOffset = new DateTimeOffset(dateTime); - return TimeZoneInfo.ConvertTime(localDateTimeOffset, targetTimeZone); - // When Unspecified: assume preferred time zone - case DateTimeKind.Unspecified: - var timeZone = options?.TimeZone ?? TimeZoneInfo.Local; - var offset = timeZone.GetUtcOffset(dateTime); - return new DateTimeOffset(dateTime, offset); - // When UTC: keep UTC - case DateTimeKind.Utc: - return new DateTimeOffset(dateTime); - default: - throw new NotSupportedException($"Unexpected DateTimeKind '{dateTime.Kind}'"); // Should never happen - } - } - else if (val is Decimal || val is Byte || val is SByte || val is Int16 || val is UInt16 || val is Int32 || val is UInt32 || val is Int64 || val is UInt64 || val is Single || val is Double) - { - kind = ValueKind.Number; - return Convert.ToDecimal(val); - } - else if (val is Enum) - { - var strVal = String.Format(CultureInfo.InvariantCulture, "{0:G}", val); - if (Decimal.TryParse(strVal, NumberStyles.AllowLeadingSign, CultureInfo.InvariantCulture, out Decimal decVal)) - { - kind = ValueKind.Number; - return decVal; - } - - kind = ValueKind.String; - return strVal; - } - } - - kind = ValueKind.Object; - return val; - } - - internal static String FormatValue( - ISecretMasker secretMasker, - EvaluationResult evaluationResult) - { - return FormatValue(secretMasker, evaluationResult.Value, evaluationResult.Kind); - } - - internal static String FormatValue( - ISecretMasker secretMasker, - Object value, - ValueKind kind) - { - switch (kind) - { - case ValueKind.Boolean: - return ((Boolean)value).ToString(); - - case ValueKind.DateTime: - var strDateTime = "(DateTime)" + ((DateTimeOffset)value).ToString(ExpressionConstants.DateTimeFormat, CultureInfo.InvariantCulture); - return secretMasker != null ? secretMasker.MaskSecrets(strDateTime) : strDateTime; - - case ValueKind.Number: - var strNumber = ((Decimal)value).ToString(ExpressionConstants.NumberFormat, CultureInfo.InvariantCulture); - return secretMasker != null ? secretMasker.MaskSecrets(strNumber) : strNumber; - - case ValueKind.String: - // Mask secrets before string-escaping. - var strValue = secretMasker != null ? secretMasker.MaskSecrets(value as String) : value as String; - return $"'{StringEscape(strValue)}'"; - - case ValueKind.Version: - String strVersion = secretMasker != null ? secretMasker.MaskSecrets(value.ToString()) : value.ToString(); - return $"v{strVersion}"; - - case ValueKind.Array: - case ValueKind.Null: - case ValueKind.Object: - return kind.ToString(); - - default: // Should never reach here. - throw new NotSupportedException($"Unable to convert to realized expression. Unexpected value kind: {kind}"); - } - } - - internal static Char SafeCharAt( - String str, - Int32 index) - { - if (str.Length > index) - { - return str[index]; - } - - return '\0'; - } - - internal static String StringEscape(String value) - { - return String.IsNullOrEmpty(value) ? String.Empty : value.Replace("'", "''"); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/FormatNode.cs b/src/Sdk/DTExpressions/Expressions/FormatNode.cs deleted file mode 100644 index 19325f4ae..000000000 --- a/src/Sdk/DTExpressions/Expressions/FormatNode.cs +++ /dev/null @@ -1,394 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Linq; -using System.Text; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class FormatNode : FunctionNode - { - protected sealed override Object EvaluateCore(EvaluationContext context) - { - var format = Parameters[0].EvaluateString(context); - var index = 0; - var result = new FormatResultBuilder(this, context, CreateMemoryCounter(context)); - while (index < format.Length) - { - var lbrace = format.IndexOf('{', index); - var rbrace = format.IndexOf('}', index); - - // Left brace - if (lbrace >= 0 && (rbrace < 0 || rbrace > lbrace)) - { - // Escaped left brace - if (ExpressionUtil.SafeCharAt(format, lbrace + 1) == '{') - { - result.Append(format.Substring(index, lbrace - index + 1)); - index = lbrace + 2; - } - // Left brace, number, optional format specifiers, right brace - else if (rbrace > lbrace + 1 && - ReadArgIndex(format, lbrace + 1, out Byte argIndex, out Int32 endArgIndex) && - ReadFormatSpecifiers(format, endArgIndex + 1, out String formatSpecifiers, out rbrace)) - { - // Check parameter count - if (argIndex > Parameters.Count - 2) - { - throw new FormatException(ExpressionResources.InvalidFormatArgIndex(format)); - } - - // Append the portion before the left brace - if (lbrace > index) - { - result.Append(format.Substring(index, lbrace - index)); - } - - // Append the arg - result.Append(argIndex, formatSpecifiers); - index = rbrace + 1; - } - else - { - throw new FormatException(ExpressionResources.InvalidFormatString(format)); - } - } - // Right brace - else if (rbrace >= 0) - { - // Escaped right brace - if (ExpressionUtil.SafeCharAt(format, rbrace + 1) == '}') - { - result.Append(format.Substring(index, rbrace - index + 1)); - index = rbrace + 2; - } - else - { - throw new FormatException(ExpressionResources.InvalidFormatString(format)); - } - } - // Last segment - else - { - result.Append(format.Substring(index)); - break; - } - } - - return result.ToString(); - } - - private Boolean ReadArgIndex( - String str, - Int32 startIndex, - out Byte result, - out Int32 endIndex) - { - // Count the number of digits - var length = 0; - while (Char.IsDigit(ExpressionUtil.SafeCharAt(str, startIndex + length))) - { - length++; - } - - // Validate at least one digit - if (length < 1) - { - result = default; - endIndex = default; - return false; - } - - // Parse the number - endIndex = startIndex + length - 1; - return Byte.TryParse(str.Substring(startIndex, length), NumberStyles.None, CultureInfo.InvariantCulture, out result); - } - - private Boolean ReadFormatSpecifiers( - String str, - Int32 startIndex, - out String result, - out Int32 rbrace) - { - // No format specifiers - var c = ExpressionUtil.SafeCharAt(str, startIndex); - if (c == '}') - { - result = String.Empty; - rbrace = startIndex; - return true; - } - - // Validate starts with ":" - if (c != ':') - { - result = default; - rbrace = default; - return false; - } - - // Read the specifiers - var specifiers = new StringBuilder(); - var index = startIndex + 1; - while (true) - { - // Validate not the end of the string - if (index >= str.Length) - { - result = default; - rbrace = default; - return false; - } - - c = str[index]; - - // Not right-brace - if (c != '}') - { - specifiers.Append(c); - index++; - } - // Escaped right-brace - else if (ExpressionUtil.SafeCharAt(str, index + 1) == '}') - { - specifiers.Append('}'); - index += 2; - } - // Closing right-brace - else - { - result = specifiers.ToString(); - rbrace = index; - return true; - } - } - } - - private sealed class FormatResultBuilder - { - internal FormatResultBuilder( - FormatNode node, - EvaluationContext context, - MemoryCounter counter) - { - m_node = node; - m_context = context; - m_counter = counter; - m_cache = new ArgValue[node.Parameters.Count - 1]; - } - - // Build the final string. This is when lazy segments are evaluated. - public override String ToString() - { - return String.Join( - String.Empty, - m_segments.Select(obj => - { - if (obj is Lazy lazy) - { - return lazy.Value; - } - else - { - return obj as String; - } - })); - } - - // Append a static value - internal void Append(String value) - { - if (value?.Length > 0) - { - // Track memory - m_counter.Add(value); - - // Append the segment - m_segments.Add(value); - } - } - - // Append an argument - internal void Append( - Int32 argIndex, - String formatSpecifiers) - { - // Delay execution until the final ToString - m_segments.Add(new Lazy(() => - { - String result; - - // Get the arg from the cache - var argValue = m_cache[argIndex]; - - // Evaluate the arg and cache the result - if (argValue == null) - { - // The evaluation result is required when format specifiers are used. Otherwise the string - // result is required. Go ahead and store both values. Since ConvertToString produces tracing, - // we need to run that now so the tracing appears in order in the log. - var evaluationResult = m_node.Parameters[argIndex + 1].Evaluate(m_context); - var stringResult = evaluationResult.ConvertToString(m_context); - argValue = new ArgValue(evaluationResult, stringResult); - m_cache[argIndex] = argValue; - } - - // No format specifiers - if (String.IsNullOrEmpty(formatSpecifiers)) - { - result = argValue.StringResult; - } - // DateTime - else if (argValue.EvaluationResult.Kind == ValueKind.DateTime) - { - result = FormatDateTime((DateTimeOffset)argValue.EvaluationResult.Value, formatSpecifiers); - } - // Invalid - else - { - throw new FormatException(ExpressionResources.InvalidFormatSpecifiers(formatSpecifiers, argValue.EvaluationResult.Kind)); - } - - // Track memory - if (!String.IsNullOrEmpty(result)) - { - m_counter.Add(result); - } - - return result; - })); - } - - private String FormatDateTime( - DateTimeOffset dateTime, - String specifiers) - { - var result = new StringBuilder(); - var i = 0; - while (true) - { - // Get the next specifier - var specifier = GetNextSpecifier(specifiers, ref i); - - // Check end of string - if (String.IsNullOrEmpty(specifier)) - { - break; - } - - // Append the value - switch (specifier) - { - case "yyyy": - case "yy": - case "MM": - case "dd": - case "HH": - case "mm": - case "ss": - case "ff": - case "fff": - case "ffff": - case "fffff": - case "ffffff": - case "fffffff": - case "zzz": - result.Append(dateTime.ToString(specifier)); - break; - - // .Net requires a leading % for some specifiers - case "M": - case "d": - case "H": - case "m": - case "s": - case "f": - case "K": - result.Append(dateTime.ToString("%" + specifier)); - break; - - default: - // Escaped character - if (specifier[0] == '\\') - { - result.Append(specifier[1]); - } - else if (specifier[0] == ' ') - { - result.Append(specifier); - } - // Unexpected - else - { - throw new FormatException(ExpressionResources.InvalidFormatSpecifiers(specifiers, ValueKind.DateTime)); - } - break; - } - } - - return result.ToString(); - } - - private String GetNextSpecifier( - String specifiers, - ref Int32 index) - { - // End of string - if (index >= specifiers.Length) - { - return String.Empty; - } - - // Get the first char - var startIndex = index; - var c = specifiers[index++]; - - // Escaped - if (c == '\\') - { - // End of string - if (index >= specifiers.Length) - { - throw new FormatException(ExpressionResources.InvalidFormatSpecifiers(specifiers, ValueKind.DateTime)); - } - - index++; - } - // Find consecutive matches - else - { - while (index < specifiers.Length && specifiers[index] == c) - { - index++; - } - } - - return specifiers.Substring(startIndex, index - startIndex); - } - - private readonly ArgValue[] m_cache; - private readonly EvaluationContext m_context; - private readonly MemoryCounter m_counter; - private readonly FormatNode m_node; - private readonly List m_segments = new List(); - } - - /// - /// Stores an EvaluateResult and the value converted to a String. - /// - private sealed class ArgValue - { - public ArgValue( - EvaluationResult evaluationResult, - String stringResult) - { - EvaluationResult = evaluationResult; - StringResult = stringResult; - } - - public EvaluationResult EvaluationResult { get; } - - public String StringResult { get; } - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/FunctionInfo.cs b/src/Sdk/DTExpressions/Expressions/FunctionInfo.cs deleted file mode 100644 index 6852ea977..000000000 --- a/src/Sdk/DTExpressions/Expressions/FunctionInfo.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public class FunctionInfo : IFunctionInfo - where T : FunctionNode, new() - { - public FunctionInfo(String name, Int32 minParameters, Int32 maxParameters) - { - Name = name; - MinParameters = minParameters; - MaxParameters = maxParameters; - } - - public String Name { get; } - - public Int32 MinParameters { get; } - - public Int32 MaxParameters { get; } - - public FunctionNode CreateNode() - { - return new T(); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/FunctionNode.cs b/src/Sdk/DTExpressions/Expressions/FunctionNode.cs deleted file mode 100644 index 6722f36a3..000000000 --- a/src/Sdk/DTExpressions/Expressions/FunctionNode.cs +++ /dev/null @@ -1,45 +0,0 @@ -using System; -using System.ComponentModel; -using System.Globalization; -using System.Linq; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class FunctionNode : ContainerNode - { - /// - /// Generally this should not be overridden. True indicates the result of the node is traced as part of the "expanded" - /// (i.e. "realized") trace information. Otherwise the node expression is printed, and parameters to the node may or - /// may not be fully realized - depending on each respective parameter's trace-fully-realized setting. - /// - /// The purpose is so the end user can understand how their expression expanded at run time. For example, consider - /// the expression: eq(variables.publish, 'true'). The runtime-expanded expression may be: eq('true', 'true') - /// - protected override Boolean TraceFullyRealized => true; - - internal sealed override String ConvertToExpression() - { - return String.Format( - CultureInfo.InvariantCulture, - "{0}({1})", - Name, - String.Join(", ", Parameters.Select(x => x.ConvertToExpression()))); - } - - internal sealed override String ConvertToRealizedExpression(EvaluationContext context) - { - // Check if the result was stored - if (context.TryGetTraceResult(this, out String result)) - { - return result; - } - - return String.Format( - CultureInfo.InvariantCulture, - "{0}({1})", - Name, - String.Join(", ", Parameters.Select(x => x.ConvertToRealizedExpression(context)))); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/GreaterThanNode.cs b/src/Sdk/DTExpressions/Expressions/GreaterThanNode.cs deleted file mode 100644 index 2c101b766..000000000 --- a/src/Sdk/DTExpressions/Expressions/GreaterThanNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class GreaterThanNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].Evaluate(context).CompareTo(context, Parameters[1].Evaluate(context)) > 0; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/GreaterThanOrEqualNode.cs b/src/Sdk/DTExpressions/Expressions/GreaterThanOrEqualNode.cs deleted file mode 100644 index 85116ed67..000000000 --- a/src/Sdk/DTExpressions/Expressions/GreaterThanOrEqualNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class GreaterThanOrEqualNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].Evaluate(context).CompareTo(context, Parameters[1].Evaluate(context)) >= 0; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IBoolean.cs b/src/Sdk/DTExpressions/Expressions/IBoolean.cs deleted file mode 100644 index b5a1fec8b..000000000 --- a/src/Sdk/DTExpressions/Expressions/IBoolean.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IBoolean - { - Boolean GetBoolean(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IExpressionNode.cs b/src/Sdk/DTExpressions/Expressions/IExpressionNode.cs deleted file mode 100644 index 52c0d9a9a..000000000 --- a/src/Sdk/DTExpressions/Expressions/IExpressionNode.cs +++ /dev/null @@ -1,70 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Logging; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IExpressionNode - { - /// - /// Evaluates the expression and attempts to cast or deserialize the result to the specified - /// type. The specified type can either be simple type or a JSON-serializable class. Allowed - /// simple types are: Boolean, String, Version, Byte, SByte, Int16, UInt16, Int32, UInt32, - /// Int64, UInt64, Single, Double, or Decimal. When a JSON-serializable class is specified, the - /// following rules are applied: If the type of the evaluation result object, is assignable to - /// the specified type, then the result will be cast and returned. If the evaluation result - /// object is a String, it will be deserialized as the specified type. If the evaluation result - /// object is null, null will be returned. - /// - /// Optional trace writer - /// Optional secret masker - /// State object for custom evaluation function nodes and custom named-value nodes - T Evaluate( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options = null); - - /// - /// Evaluates the expression and returns the result. - /// - /// Optional trace writer - /// Optional secret masker - /// State object for custom evaluation function nodes and custom named-value nodes - Object Evaluate( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options = null); - - /// - /// Evaluates the expression and casts the result to a Boolean. - /// - /// Optional trace writer - /// Optional secret masker - /// State object for custom evaluation function nodes and custom named-value nodes - Boolean EvaluateBoolean( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state); - - IEnumerable GetParameters() where T : IExpressionNode; - - /// - /// Evaluates the expression and returns the result, wrapped in the SDK helper - /// for converting, comparing, and traversing objects. - /// - /// Optional trace writer - /// Optional secret masker - /// State object for custom evaluation function nodes and custom named-value nodes - /// Evaluation options - [EditorBrowsable(EditorBrowsableState.Never)] - EvaluationResult EvaluateResult( - ITraceWriter trace, - ISecretMasker secretMasker, - Object state, - EvaluationOptions options); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IFunctionInfo.cs b/src/Sdk/DTExpressions/Expressions/IFunctionInfo.cs deleted file mode 100644 index 0aad42a8c..000000000 --- a/src/Sdk/DTExpressions/Expressions/IFunctionInfo.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public interface IFunctionInfo - { - String Name { get; } - Int32 MinParameters { get; } - Int32 MaxParameters { get; } - FunctionNode CreateNode(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/INamedValueInfo.cs b/src/Sdk/DTExpressions/Expressions/INamedValueInfo.cs deleted file mode 100644 index 94dfcd3c6..000000000 --- a/src/Sdk/DTExpressions/Expressions/INamedValueInfo.cs +++ /dev/null @@ -1,10 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public interface INamedValueInfo - { - String Name { get; } - NamedValueNode CreateNode(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/INumber.cs b/src/Sdk/DTExpressions/Expressions/INumber.cs deleted file mode 100644 index 7baa37529..000000000 --- a/src/Sdk/DTExpressions/Expressions/INumber.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface INumber - { - Decimal GetNumber(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IReadOnlyArray.cs b/src/Sdk/DTExpressions/Expressions/IReadOnlyArray.cs deleted file mode 100644 index 686e8bc26..000000000 --- a/src/Sdk/DTExpressions/Expressions/IReadOnlyArray.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IReadOnlyArray : IReadOnlyList - { - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IReadOnlyObject.cs b/src/Sdk/DTExpressions/Expressions/IReadOnlyObject.cs deleted file mode 100644 index 757a17c12..000000000 --- a/src/Sdk/DTExpressions/Expressions/IReadOnlyObject.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IReadOnlyObject : IReadOnlyDictionary - { - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IString.cs b/src/Sdk/DTExpressions/Expressions/IString.cs deleted file mode 100644 index c7d677ce6..000000000 --- a/src/Sdk/DTExpressions/Expressions/IString.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IString - { - String GetString(); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ITraceWriter.cs b/src/Sdk/DTExpressions/Expressions/ITraceWriter.cs deleted file mode 100644 index c1b7fa1f7..000000000 --- a/src/Sdk/DTExpressions/Expressions/ITraceWriter.cs +++ /dev/null @@ -1,10 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public interface ITraceWriter - { - void Info(String message); - void Verbose(String message); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/InNode.cs b/src/Sdk/DTExpressions/Expressions/InNode.cs deleted file mode 100644 index 7807e1942..000000000 --- a/src/Sdk/DTExpressions/Expressions/InNode.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class InNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - EvaluationResult left = Parameters[0].Evaluate(context); - for (Int32 i = 1; i < Parameters.Count; i++) - { - EvaluationResult right = Parameters[i].Evaluate(context); - if (left.Equals(context, right)) - { - return true; - } - } - - return false; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/IndexerNode.cs b/src/Sdk/DTExpressions/Expressions/IndexerNode.cs deleted file mode 100644 index 37d818104..000000000 --- a/src/Sdk/DTExpressions/Expressions/IndexerNode.cs +++ /dev/null @@ -1,452 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Globalization; -using System.Reflection; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using Newtonsoft.Json.Serialization; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class IndexerNode : ContainerNode - { - internal IndexerNode() - { - Name = "indexer"; - } - - protected sealed override Boolean TraceFullyRealized => true; - - internal sealed override String ConvertToExpression() - { - return String.Format( - CultureInfo.InvariantCulture, - "{0}[{1}]", - Parameters[0].ConvertToExpression(), - Parameters[1].ConvertToExpression()); - } - - internal sealed override String ConvertToRealizedExpression(EvaluationContext context) - { - // Check if the result was stored - if (context.TryGetTraceResult(this, out String result)) - { - return result; - } - - return ConvertToExpression(); - } - - protected sealed override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - EvaluationResult firstParameter = Parameters[0].Evaluate(context); - - if (context.Options.UseCollectionInterfaces) - { - if (!firstParameter.TryGetCollectionInterface(out Object collection)) - { - // Even if we can't get the collection interface, return empty filtered array if it is a wildcard. - if (Parameters.Count > 2) - { - resultMemory = null; - return new FilteredArray(); - } - - resultMemory = null; - return null; - } - - // Handle operating on a filtered array - if (collection is FilteredArray filteredArray) - { - return HandleFilteredArray(context, filteredArray, out resultMemory); - } - // Handle operating on an object - else if (collection is IReadOnlyObject obj) - { - return HandleObject(context, obj, out resultMemory); - } - // Handle operating on an array - else if (collection is IReadOnlyArray array) - { - return HandleArray(context, array, out resultMemory); - } - - resultMemory = null; - return null; - } - else - { - Object result = null; - - if (firstParameter.Kind == ValueKind.Array && firstParameter.Value is JArray) - { - var jarray = firstParameter.Value as JArray; - EvaluationResult index = Parameters[1].Evaluate(context); - if (index.Kind == ValueKind.Number) - { - Decimal d = (Decimal)index.Value; - if (d >= 0m && d < (Decimal)jarray.Count && d == Math.Floor(d)) - { - result = jarray[(Int32)d]; - } - } - else if (index.Kind == ValueKind.String && !String.IsNullOrEmpty(index.Value as String)) - { - Decimal d; - if (index.TryConvertToNumber(context, out d)) - { - if (d >= 0m && d < (Decimal)jarray.Count && d == Math.Floor(d)) - { - result = jarray[(Int32)d]; - } - } - } - } - else if (firstParameter.Kind == ValueKind.Object) - { - if (firstParameter.Value is JObject) - { - var jobject = firstParameter.Value as JObject; - EvaluationResult index = Parameters[1].Evaluate(context); - String s; - if (index.TryConvertToString(context, out s)) - { - result = jobject[s]; - } - } - else if (firstParameter.Value is IDictionary) - { - var dictionary = firstParameter.Value as IDictionary; - EvaluationResult index = Parameters[1].Evaluate(context); - if (index.TryConvertToString(context, out String key)) - { - if (!dictionary.TryGetValue(key, out String resultString)) - { - result = null; - } - else - { - result = resultString; - } - } - } - else if (firstParameter.Value is IDictionary) - { - var dictionary = firstParameter.Value as IDictionary; - EvaluationResult index = Parameters[1].Evaluate(context); - String s; - if (index.TryConvertToString(context, out s)) - { - if (!dictionary.TryGetValue(s, out result)) - { - result = null; - } - } - } - else if (firstParameter.Value is IReadOnlyDictionary) - { - var dictionary = firstParameter.Value as IReadOnlyDictionary; - EvaluationResult index = Parameters[1].Evaluate(context); - if (index.TryConvertToString(context, out String key)) - { - if (!dictionary.TryGetValue(key, out String resultString)) - { - result = null; - } - else - { - result = resultString; - } - } - } - else if (firstParameter.Value is IReadOnlyDictionary) - { - var dictionary = firstParameter.Value as IReadOnlyDictionary; - EvaluationResult index = Parameters[1].Evaluate(context); - String s; - if (index.TryConvertToString(context, out s)) - { - if (!dictionary.TryGetValue(s, out result)) - { - result = null; - } - } - } - else - { - var contract = s_serializer.Value.ContractResolver.ResolveContract(firstParameter.Value.GetType()); - var objectContract = contract as JsonObjectContract; - if (objectContract != null) - { - EvaluationResult index = Parameters[1].Evaluate(context); - if (index.TryConvertToString(context, out String key)) - { - var property = objectContract.Properties.GetClosestMatchProperty(key); - if (property != null) - { - result = objectContract.Properties[property.PropertyName].ValueProvider.GetValue(firstParameter.Value); - } - } - } - else - { - var dictionaryContract = contract as JsonDictionaryContract; - if (dictionaryContract != null && dictionaryContract.DictionaryKeyType == typeof(String)) - { - EvaluationResult index = Parameters[1].Evaluate(context); - if (index.TryConvertToString(context, out String key)) - { - var genericMethod = s_tryGetValueTemplate.Value.MakeGenericMethod(dictionaryContract.DictionaryValueType); - resultMemory = null; - return genericMethod.Invoke(null, new[] { firstParameter.Value, key }); - } - } - } - } - } - - resultMemory = null; - return result; - } - } - - private Object HandleFilteredArray( - EvaluationContext context, - FilteredArray filteredArray, - out ResultMemory resultMemory) - { - EvaluationResult indexResult = Parameters[1].Evaluate(context); - var indexHelper = new IndexHelper(indexResult, context); - - Boolean isFilter; - if (Parameters.Count > 2) - { - isFilter = true; - - if (!String.Equals(indexHelper.StringIndex, ExpressionConstants.Wildcard.ToString(), StringComparison.Ordinal)) - { - throw new InvalidOperationException($"Unexpected filter '{indexHelper.StringIndex}'"); - } - } - else - { - isFilter = false; - } - - var result = new FilteredArray(); - var counter = new MemoryCounter(this, context.Options.MaxMemory); - - foreach (var item in filteredArray) - { - // Leverage the expression SDK to traverse the object - var itemResult = EvaluationResult.CreateIntermediateResult(context, item, out _); - if (itemResult.TryGetCollectionInterface(out Object nestedCollection)) - { - // Apply the index to a child object - if (nestedCollection is IReadOnlyObject nestedObject) - { - if (isFilter) - { - foreach (var val in nestedObject.Values) - { - result.Add(val); - counter.Add(IntPtr.Size); - } - } - else if (indexHelper.HasStringIndex) - { - if (nestedObject.TryGetValue(indexHelper.StringIndex, out Object nestedObjectValue)) - { - result.Add(nestedObjectValue); - counter.Add(IntPtr.Size); - } - } - } - // Apply the index to a child array - else if (nestedCollection is IReadOnlyArray nestedArray) - { - if (isFilter) - { - foreach (var val in nestedArray) - { - result.Add(val); - counter.Add(IntPtr.Size); - } - } - else if (indexHelper.HasIntegerIndex && - indexHelper.IntegerIndex < nestedArray.Count) - { - result.Add(nestedArray[indexHelper.IntegerIndex]); - counter.Add(IntPtr.Size); - } - } - } - } - - resultMemory = new ResultMemory { Bytes = counter.CurrentBytes }; - return result; - } - - private Object HandleObject( - EvaluationContext context, - IReadOnlyObject obj, - out ResultMemory resultMemory) - { - EvaluationResult indexResult = Parameters[1].Evaluate(context); - var indexHelper = new IndexHelper(indexResult, context); - - if (indexHelper.HasStringIndex) - { - Boolean isFilter = Parameters.Count > 2; - - if (isFilter) - { - var filteredArray = new FilteredArray(); - var counter = new MemoryCounter(this, context.Options.MaxMemory); - - foreach (var val in obj.Values) - { - filteredArray.Add(val); - counter.Add(IntPtr.Size); - } - - resultMemory = new ResultMemory { Bytes = counter.CurrentBytes }; - return filteredArray; - } - else if (obj.TryGetValue(indexHelper.StringIndex, out Object result)) - { - resultMemory = null; - return result; - } - } - - resultMemory = null; - return null; - } - - private Object HandleArray( - EvaluationContext context, - IReadOnlyArray array, - out ResultMemory resultMemory) - { - // Similar to as above but for an array - EvaluationResult indexResult = Parameters[1].Evaluate(context); - var indexHelper = new IndexHelper(indexResult, context); - - // When we are operating on a array and it has three parameters, with the second being a string * and the third being a true boolean, it's a filtered array. - if (Parameters.Count > 2) - { - var filtered = new FilteredArray(); - var counter = new MemoryCounter(this, context.Options.MaxMemory); - - foreach (var x in array) - { - filtered.Add(x); - counter.Add(IntPtr.Size); - } - - resultMemory = new ResultMemory { Bytes = counter.CurrentBytes }; - return filtered; - } - - if (indexHelper.HasIntegerIndex && indexHelper.IntegerIndex < array.Count) - { - resultMemory = null; - return array[indexHelper.IntegerIndex]; - } - - resultMemory = null; - return null; - } - - // todo: remove with feature flag cleanup for "UseCollectionInterfaces" - private static Object TryGetValue( - IDictionary dictionary, - String key) - { - TValue value; - if (!dictionary.TryGetValue(key, out value)) - { - return null; - } - - return value; - } - - private class FilteredArray : IReadOnlyArray - { - public FilteredArray() - { - m_list = new List(); - } - - public void Add(Object o) - { - m_list.Add(o); - } - - public Int32 Count => m_list.Count; - - public Object this[Int32 index] => m_list[index]; - - public IEnumerator GetEnumerator() => m_list.GetEnumerator(); - - IEnumerator IEnumerable.GetEnumerator() => m_list.GetEnumerator(); - - private readonly IList m_list; - } - - private class IndexHelper - { - public Boolean HasIntegerIndex => m_integerIndex.Value.Item1; - public Int32 IntegerIndex => m_integerIndex.Value.Item2; - - public Boolean HasStringIndex => m_stringIndex.Value.Item1; - public String StringIndex => m_stringIndex.Value.Item2; - - public IndexHelper( - EvaluationResult result, - EvaluationContext context) - { - m_result = result; - m_context = context; - - m_integerIndex = new Lazy>(() => - { - if (m_result.TryConvertToNumber(m_context, out Decimal decimalIndex) && - decimalIndex >= 0m) - { - return new Tuple(true, (Int32)Math.Floor(decimalIndex)); - } - - return new Tuple(false, default(Int32)); - }); - - m_stringIndex = new Lazy>(() => - { - if (m_result.TryConvertToString(m_context, out String stringIndex)) - { - return new Tuple(true, stringIndex); - } - - return new Tuple(false, null); - }); - } - - private Lazy> m_integerIndex; - private Lazy> m_stringIndex; - - private readonly EvaluationResult m_result; - private readonly EvaluationContext m_context; - } - - // todo: remove these properties with feature flag cleanup for "UseCollectionInterfaces" - private static Lazy s_serializer = new Lazy(() => JsonUtility.CreateJsonSerializer()); - private static Lazy s_tryGetValueTemplate = new Lazy(() => typeof(IndexerNode).GetTypeInfo().GetMethod(nameof(TryGetValue), BindingFlags.NonPublic | BindingFlags.Static)); - } -} diff --git a/src/Sdk/DTExpressions/Expressions/JoinNode.cs b/src/Sdk/DTExpressions/Expressions/JoinNode.cs deleted file mode 100644 index cdef727d7..000000000 --- a/src/Sdk/DTExpressions/Expressions/JoinNode.cs +++ /dev/null @@ -1,69 +0,0 @@ -using System; -using System.Text; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class JoinNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => true; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - var items = Parameters[1].Evaluate(context); - - if (items.TryGetCollectionInterface(out var collection) && collection is IReadOnlyArray array) - { - if (array.Count > 0) - { - var result = new StringBuilder(); - var memory = new MemoryCounter(this, context.Options.MaxMemory); - - // Append the first item - var item = array[0]; - var itemResult = EvaluationResult.CreateIntermediateResult(context, item, out _); - if (itemResult.TryConvertToString(context, out String itemString)) - { - memory.Add(itemString); - result.Append(itemString); - } - - // More items? - if (array.Count > 1) - { - var separator = Parameters[0].EvaluateString(context); - - for (var i = 1; i < array.Count; i++) - { - // Append the separator - memory.Add(separator); - result.Append(separator); - - // Append the next item - var nextItem = array[i]; - var nextItemResult = EvaluationResult.CreateIntermediateResult(context, nextItem, out _); - if (nextItemResult.TryConvertToString(context, out String nextItemString)) - { - memory.Add(nextItemString); - result.Append(nextItemString); - } - } - } - - return result.ToString(); - } - else - { - return String.Empty; - } - } - else if (items.TryConvertToString(context, out String str)) - { - return str; - } - else - { - return String.Empty; - } - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/LessThanNode.cs b/src/Sdk/DTExpressions/Expressions/LessThanNode.cs deleted file mode 100644 index 08018719e..000000000 --- a/src/Sdk/DTExpressions/Expressions/LessThanNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class LessThanNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].Evaluate(context).CompareTo(context, Parameters[1].Evaluate(context)) < 0; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/LessThanOrEqualNode.cs b/src/Sdk/DTExpressions/Expressions/LessThanOrEqualNode.cs deleted file mode 100644 index 39367fc22..000000000 --- a/src/Sdk/DTExpressions/Expressions/LessThanOrEqualNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class LessThanOrEqualNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].Evaluate(context).CompareTo(context, Parameters[1].Evaluate(context)) <= 0; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/LexicalAnalyzer.cs b/src/Sdk/DTExpressions/Expressions/LexicalAnalyzer.cs deleted file mode 100644 index a688aac49..000000000 --- a/src/Sdk/DTExpressions/Expressions/LexicalAnalyzer.cs +++ /dev/null @@ -1,293 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Text; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class LexicalAnalyzer - { - public LexicalAnalyzer(String expression, IEnumerable namedValues, IEnumerable functions, Boolean allowKeywordHyphens) - { - m_expression = expression; - m_extensionNamedValues = new HashSet(namedValues ?? new String[0], StringComparer.OrdinalIgnoreCase); - m_extensionFunctions = new HashSet(functions ?? new String[0], StringComparer.OrdinalIgnoreCase); - m_allowKeyHyphens = allowKeywordHyphens; - } - - public Boolean TryGetNextToken(ref Token token) - { - // Skip whitespace. - while (m_index < m_expression.Length && Char.IsWhiteSpace(m_expression[m_index])) - { - m_index++; - } - - // Test end of string. - if (m_index >= m_expression.Length) - { - token = null; - return false; - } - - // Read the first character to determine the type of token. - Char c = m_expression[m_index]; - switch (c) - { - case ExpressionConstants.StartIndex: - token = new Token(TokenKind.StartIndex, c, m_index++); - break; - case ExpressionConstants.StartParameter: - token = new Token(TokenKind.StartParameter, c, m_index++); - break; - case ExpressionConstants.EndIndex: - token = new Token(TokenKind.EndIndex, c, m_index++); - break; - case ExpressionConstants.EndParameter: - token = new Token(TokenKind.EndParameter, c, m_index++); - break; - case ExpressionConstants.Separator: - token = new Token(TokenKind.Separator, c, m_index++); - break; - case ExpressionConstants.Wildcard: - token = new Token(TokenKind.Wildcard, c, m_index++); - break; - case '\'': - token = ReadStringToken(); - break; - default: - if (c == '.') - { - if (m_lastToken == null || - m_lastToken.Kind == TokenKind.Separator || - m_lastToken.Kind == TokenKind.StartIndex || - m_lastToken.Kind == TokenKind.StartParameter) - { - token = ReadNumberOrVersionToken(); - } - else - { - token = new Token(TokenKind.Dereference, c, m_index++); - } - } - else if (c == '-' || (c >= '0' && c <= '9')) - { - token = ReadNumberOrVersionToken(); - } - else - { - token = ReadKeywordToken(m_allowKeyHyphens); - } - - break; - } - - m_lastToken = token; - return true; - } - - public Boolean TryPeekNextToken(ref Token token) - { - // Record the state. - Int32 index = m_index; - Token lastToken = m_lastToken; - - // Get next token. - Boolean result = TryGetNextToken(ref token); - - // Restore the state. - m_index = index; - m_lastToken = lastToken; - - return result; - } - - private Token ReadNumberOrVersionToken() - { - Int32 startIndex = m_index; - Int32 periods = 0; - do - { - if (m_expression[m_index] == '.') - { - periods++; - } - - m_index++; - } - while (m_index < m_expression.Length && (!TestWhitespaceOrPunctuation(m_expression[m_index]) || m_expression[m_index] == '.')); - - Int32 length = m_index - startIndex; - String str = m_expression.Substring(startIndex, length); - if (periods >= 2) - { - Version version; - if (Version.TryParse(str, out version)) - { - return new Token(TokenKind.Version, str, startIndex, version); - } - } - else - { - // Note, NumberStyles.AllowThousands cannot be allowed since comma has special meaning as a token separator. - Decimal d; - if (Decimal.TryParse( - str, - NumberStyles.AllowDecimalPoint | NumberStyles.AllowLeadingSign, - CultureInfo.InvariantCulture, - out d)) - { - return new Token(TokenKind.Number, str, startIndex, d); - } - } - - return new Token(TokenKind.Unrecognized, str, startIndex); - } - - private Token ReadKeywordToken(bool allowHyphen) - { - // Read to the end of the keyword. - Int32 startIndex = m_index; - m_index++; // Skip the first char. It is already known to be the start of the keyword. - while (m_index < m_expression.Length && !TestWhitespaceOrPunctuation(m_expression[m_index])) - { - m_index++; - } - - // Test if valid keyword character sequence. - Int32 length = m_index - startIndex; - String str = m_expression.Substring(startIndex, length); - if (TestKeyword(str, allowHyphen)) - { - // Test if follows property dereference operator. - if (m_lastToken != null && m_lastToken.Kind == TokenKind.Dereference) - { - return new Token(TokenKind.PropertyName, str, startIndex); - } - - // Boolean - if (str.Equals(Boolean.TrueString, StringComparison.OrdinalIgnoreCase)) - { - return new Token(TokenKind.Boolean, str, startIndex, true); - } - else if (str.Equals(Boolean.FalseString, StringComparison.OrdinalIgnoreCase)) - { - return new Token(TokenKind.Boolean, str, startIndex, false); - } - // Well-known function - else if (ExpressionConstants.WellKnownFunctions.ContainsKey(str)) - { - return new Token(TokenKind.WellKnownFunction, str, startIndex); - } - // Extension value - else if (m_extensionNamedValues.Contains(str)) - { - return new Token(TokenKind.ExtensionNamedValue, str, startIndex); - } - // Extension function - else if (m_extensionFunctions.Contains(str)) - { - return new Token(TokenKind.ExtensionFunction, str, startIndex); - } - } - - // Unknown keyword - return new Token(TokenKind.UnknownKeyword, str, startIndex); - } - - private Token ReadStringToken() - { - Int32 startIndex = m_index; - Char c; - Boolean closed = false; - var str = new StringBuilder(); - m_index++; // Skip the leading single-quote. - while (m_index < m_expression.Length) - { - c = m_expression[m_index++]; - if (c == '\'') - { - // End of string. - if (m_index >= m_expression.Length || m_expression[m_index] != '\'') - { - closed = true; - break; - } - - // Escaped single quote. - m_index++; - } - - str.Append(c); - } - - Int32 length = m_index - startIndex; - String rawValue = m_expression.Substring(startIndex, length); - if (closed) - { - return new Token(TokenKind.String, rawValue, startIndex, str.ToString()); - } - - return new Token(TokenKind.Unrecognized, rawValue, startIndex); - } - - private static Boolean TestKeyword(String str, bool allowHyphen) - { - if (String.IsNullOrEmpty(str)) - { - return false; - } - - Char first = str[0]; - if ((first >= 'a' && first <= 'z') || - (first >= 'A' && first <= 'Z') || - first == '_') - { - for (Int32 i = 1 ; i < str.Length ; i++) - { - Char c = str[i]; - if ((c >= 'a' && c <= 'z') || - (c >= 'A' && c <= 'Z') || - (c >= '0' && c <= '9') || - c == '_' || (allowHyphen && c == '-')) - { - // OK - } - else - { - return false; - } - } - - return true; - } - else - { - return false; - } - } - - private static Boolean TestWhitespaceOrPunctuation(Char c) - { - switch (c) - { - case ExpressionConstants.StartIndex: - case ExpressionConstants.StartParameter: - case ExpressionConstants.EndIndex: - case ExpressionConstants.EndParameter: - case ExpressionConstants.Separator: - case ExpressionConstants.Dereference: - return true; - default: - return char.IsWhiteSpace(c); - } - } - - private readonly String m_expression; // Raw expression string. - private readonly HashSet m_extensionFunctions; - private readonly HashSet m_extensionNamedValues; - private Int32 m_index; // Index of raw condition string. - private Token m_lastToken; - private readonly Boolean m_allowKeyHyphens; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/LiteralValueNode.cs b/src/Sdk/DTExpressions/Expressions/LiteralValueNode.cs deleted file mode 100644 index 2639cdbcc..000000000 --- a/src/Sdk/DTExpressions/Expressions/LiteralValueNode.cs +++ /dev/null @@ -1,47 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class LiteralValueNode : ExpressionNode - { - public LiteralValueNode(Object val) - { - ValueKind kind; - - // Note, it is OK to pass null EvaluationOptions here since the parser does not support - // localized values. For example, if parsing local date-times were supported, then we - // would need to know the account's time zone at parse time. This is an OK limitation, - // since we can defer this type of problem to runtime, for example by adding a parseDate function. - Value = ExpressionUtil.ConvertToCanonicalValue(null, val, out kind, out _, out _); - - Kind = kind; - Name = kind.ToString(); - } - - public ValueKind Kind { get; } - - public Object Value { get; } - - // Prevent the value from being stored on the evaluation context. - // This avoids unneccessarily duplicating the value in memory. - protected sealed override Boolean TraceFullyRealized => false; - - internal sealed override String ConvertToExpression() - { - return ExpressionUtil.FormatValue(null, Value, Kind); - } - - internal sealed override String ConvertToRealizedExpression(EvaluationContext context) - { - return ExpressionUtil.FormatValue(null, Value, Kind); - } - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Value; - } - } - -} diff --git a/src/Sdk/DTExpressions/Expressions/MemoryCounter.cs b/src/Sdk/DTExpressions/Expressions/MemoryCounter.cs deleted file mode 100644 index 305b8b856..000000000 --- a/src/Sdk/DTExpressions/Expressions/MemoryCounter.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.ComponentModel; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Expressions -{ - /// - /// Helper class for ExpressionNode authors. This class helps calculate memory overhead for a result object. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class MemoryCounter - { - internal MemoryCounter( - ExpressionNode node, - Int32? maxBytes) - { - m_node = node; - m_maxBytes = (maxBytes ?? 0) > 0 ? maxBytes.Value : Int32.MaxValue; - } - - public Int32 CurrentBytes => m_currentBytes; - - public void Add(Int32 amount) - { - if (!TryAdd(amount)) - { - throw new InvalidOperationException(ExpressionResources.ExceededAllowedMemory(m_node?.ConvertToExpression())); - } - } - - public void Add(String value) - { - Add(CalculateSize(value)); - } - - public void Add( - JToken value, - Boolean traverse) - { - // This measurement doesn't have to be perfect - // https://codeblog.jonskeet.uk/2011/04/05/of-memory-and-strings/ - - if (value is null) - { - Add(MinObjectSize); - } - - if (!traverse) - { - switch (value.Type) - { - case JTokenType.Bytes: - case JTokenType.String: - case JTokenType.Uri: - Add(value.ToObject()); - return; - - case JTokenType.Property: - var property = value as JProperty; - Add(property.Name); - return; - - default: - Add(MinObjectSize); - return; - } - } - - do - { - // Descend as much as possible - while (true) - { - // Add bytes - Add(value, false); - - // Descend - if (value.HasValues) - { - value = value.First; - } - // No more descendants - else - { - break; - } - } - - // Next sibling or ancestor sibling - do - { - var sibling = value.Next; - - // Sibling found - if (sibling != null) - { - value = sibling; - break; - } - - // Ascend - value = value.Parent; - - } while (value != null); - - } while (value != null); - } - - public void AddMinObjectSize() - { - Add(MinObjectSize); - } - - public void Remove(String value) - { - m_currentBytes -= CalculateSize(value); - } - - public static Int32 CalculateSize(String value) - { - // This measurement doesn't have to be perfect. - // https://codeblog.jonskeet.uk/2011/04/05/of-memory-and-strings/ - - Int32 bytes; - checked - { - bytes = StringBaseOverhead + ((value?.Length ?? 0) * 2); - } - return bytes; - } - - internal Boolean TryAdd(Int32 amount) - { - try - { - checked - { - amount += m_currentBytes; - } - - if (amount > m_maxBytes) - { - return false; - } - - m_currentBytes = amount; - return true; - } - catch (OverflowException) - { - return false; - } - } - - internal Boolean TryAdd(String value) - { - return TryAdd(CalculateSize(value)); - } - - internal const Int32 MinObjectSize = 24; - internal const Int32 StringBaseOverhead = 26; - private readonly Int32 m_maxBytes; - private readonly ExpressionNode m_node; - private Int32 m_currentBytes; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/NamedValueInfo.cs b/src/Sdk/DTExpressions/Expressions/NamedValueInfo.cs deleted file mode 100644 index 1c7484438..000000000 --- a/src/Sdk/DTExpressions/Expressions/NamedValueInfo.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public class NamedValueInfo : INamedValueInfo - where T : NamedValueNode, new() - { - public NamedValueInfo(String name) - { - Name = name; - } - - public String Name { get; } - - public NamedValueNode CreateNode() - { - return new T(); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/NamedValueNode.cs b/src/Sdk/DTExpressions/Expressions/NamedValueNode.cs deleted file mode 100644 index 9dfab2a88..000000000 --- a/src/Sdk/DTExpressions/Expressions/NamedValueNode.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class NamedValueNode : ExpressionNode - { - internal sealed override string ConvertToExpression() => Name; - - protected sealed override Boolean TraceFullyRealized => true; - - internal sealed override String ConvertToRealizedExpression(EvaluationContext context) - { - // Check if the result was stored - if (context.TryGetTraceResult(this, out String result)) - { - return result; - } - - return Name; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/NotEqualNode.cs b/src/Sdk/DTExpressions/Expressions/NotEqualNode.cs deleted file mode 100644 index 4a54e6215..000000000 --- a/src/Sdk/DTExpressions/Expressions/NotEqualNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class NotEqualNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return !Parameters[0].Evaluate(context).Equals(context, Parameters[1].Evaluate(context)); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/NotInNode.cs b/src/Sdk/DTExpressions/Expressions/NotInNode.cs deleted file mode 100644 index c7b1a5a08..000000000 --- a/src/Sdk/DTExpressions/Expressions/NotInNode.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class NotInNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - EvaluationResult left = Parameters[0].Evaluate(context); - for (Int32 i = 1; i < Parameters.Count; i++) - { - EvaluationResult right = Parameters[i].Evaluate(context); - if (left.Equals(context, right)) - { - return false; - } - } - - return true; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/NotNode.cs b/src/Sdk/DTExpressions/Expressions/NotNode.cs deleted file mode 100644 index b27ef2fc4..000000000 --- a/src/Sdk/DTExpressions/Expressions/NotNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class NotNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return !Parameters[0].EvaluateBoolean(context); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/OrNode.cs b/src/Sdk/DTExpressions/Expressions/OrNode.cs deleted file mode 100644 index 513a2e5e5..000000000 --- a/src/Sdk/DTExpressions/Expressions/OrNode.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class OrNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - foreach (ExpressionNode parameter in Parameters) - { - if (parameter.EvaluateBoolean(context)) - { - return true; - } - } - - return false; - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ParseException.cs b/src/Sdk/DTExpressions/Expressions/ParseException.cs deleted file mode 100644 index 489c0d873..000000000 --- a/src/Sdk/DTExpressions/Expressions/ParseException.cs +++ /dev/null @@ -1,65 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - public sealed class ParseException : ExpressionException - { - internal ParseException(ParseExceptionKind kind, Token token, String expression) - : base(secretMasker: null, message: String.Empty) - { - Expression = expression; - Kind = kind; - RawToken = token?.RawValue; - TokenIndex = token?.Index ?? 0; - String description; - switch (kind) - { - case ParseExceptionKind.ExceededMaxDepth: - description = ExpressionResources.ExceededMaxExpressionDepth(ExpressionConstants.MaxDepth); - break; - case ParseExceptionKind.ExceededMaxLength: - description = ExpressionResources.ExceededMaxExpressionLength(ExpressionConstants.MaxLength); - break; - case ParseExceptionKind.ExpectedPropertyName: - description = ExpressionResources.ExpectedPropertyName(); - break; - case ParseExceptionKind.ExpectedStartParameter: - description = ExpressionResources.ExpectedStartParameter(); - break; - case ParseExceptionKind.UnclosedFunction: - description = ExpressionResources.UnclosedFunction(); - break; - case ParseExceptionKind.UnclosedIndexer: - description = ExpressionResources.UnclosedIndexer(); - break; - case ParseExceptionKind.UnexpectedSymbol: - description = ExpressionResources.UnexpectedSymbol(); - break; - case ParseExceptionKind.UnrecognizedValue: - description = ExpressionResources.UnrecognizedValue(); - break; - default: // Should never reach here. - throw new Exception($"Unexpected parse exception kind '{kind}'."); - } - - if (token == null) - { - Message = ExpressionResources.ParseErrorWithFwlink(description); - } - else - { - Message = ExpressionResources.ParseErrorWithTokenInfo(description, RawToken, TokenIndex + 1, Expression); - } - } - - internal String Expression { get; } - - internal ParseExceptionKind Kind { get; } - - internal String RawToken { get; } - - internal Int32 TokenIndex { get; } - - public sealed override String Message { get; } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ParseExceptionKind.cs b/src/Sdk/DTExpressions/Expressions/ParseExceptionKind.cs deleted file mode 100644 index cddebfed2..000000000 --- a/src/Sdk/DTExpressions/Expressions/ParseExceptionKind.cs +++ /dev/null @@ -1,14 +0,0 @@ -namespace GitHub.DistributedTask.Expressions -{ - internal enum ParseExceptionKind - { - ExceededMaxDepth, - ExceededMaxLength, - ExpectedPropertyName, - ExpectedStartParameter, - UnclosedFunction, - UnclosedIndexer, - UnexpectedSymbol, - UnrecognizedValue, - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ResultMemory.cs b/src/Sdk/DTExpressions/Expressions/ResultMemory.cs deleted file mode 100644 index 762980b11..000000000 --- a/src/Sdk/DTExpressions/Expressions/ResultMemory.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class ResultMemory - { - /// - /// Only set a non-null value when both of the following conditions are met: - /// 1) The result is a complex object. In other words, the result is - /// not a simple type: string, boolean, number, version, datetime, or null. - /// 2) The result is a newly created object. - /// - /// - /// For example, consider a function jsonParse() which takes a string parameter, - /// and returns a JToken object. The JToken object is newly created and a rough - /// measurement should be returned for the number of bytes it consumes in memory. - /// - /// - /// - /// For another example, consider a function which returns a sub-object from a - /// complex parameter value. From the perspective of an individual function, - /// the size of the complex parameter value is unknown. In this situation, set the - /// value to IntPtr.Size. - /// - /// - /// - /// When you are unsure, set the value to null. Null indicates the overhead of a - /// new pointer should be accounted for. - /// - /// - public Int32? Bytes { get; set; } - - /// - /// Indicates whether represents the total size of the result. - /// True indicates the accounting-overhead of downstream parameters can be discarded. - /// - /// For , this value is currently ignored. - /// - /// - /// For example, consider a funciton jsonParse() which takes a string paramter, - /// and returns a JToken object. The JToken object is newly created and a rough - /// measurement should be returned for the amount of bytes it consumes in memory. - /// Set the to true, since new object contains no references - /// to previously allocated memory. - /// - /// - /// - /// For another example, consider a function which wraps a complex parameter result. - /// should be set to the amount of newly allocated memory. - /// However since the object references previously allocated memory, set - /// to false. - /// - /// - public Boolean IsTotal { get; set; } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/StartsWithNode.cs b/src/Sdk/DTExpressions/Expressions/StartsWithNode.cs deleted file mode 100644 index 9c5e04bb2..000000000 --- a/src/Sdk/DTExpressions/Expressions/StartsWithNode.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class StartsWithNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - String left = Parameters[0].EvaluateString(context) ?? String.Empty; - String right = Parameters[1].EvaluateString(context) ?? String.Empty; - return left.StartsWith(right, StringComparison.OrdinalIgnoreCase); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/Token.cs b/src/Sdk/DTExpressions/Expressions/Token.cs deleted file mode 100644 index c1788a04d..000000000 --- a/src/Sdk/DTExpressions/Expressions/Token.cs +++ /dev/null @@ -1,28 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class Token - { - public Token(TokenKind kind, Char rawValue, Int32 index, Object parsedValue = null) - : this(kind, rawValue.ToString(), index, parsedValue) - { - } - - public Token(TokenKind kind, String rawValue, Int32 index, Object parsedValue = null) - { - Kind = kind; - RawValue = rawValue; - Index = index; - ParsedValue = parsedValue; - } - - public TokenKind Kind { get; } - - public String RawValue { get; } - - public Int32 Index { get; } - - public Object ParsedValue { get; } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/TokenKind.cs b/src/Sdk/DTExpressions/Expressions/TokenKind.cs deleted file mode 100644 index 97cbf20d4..000000000 --- a/src/Sdk/DTExpressions/Expressions/TokenKind.cs +++ /dev/null @@ -1,29 +0,0 @@ -namespace GitHub.DistributedTask.Expressions -{ - internal enum TokenKind - { - // Punctuation - StartIndex, - StartParameter, - EndIndex, - EndParameter, - Separator, - Dereference, - Wildcard, - - // Values - Boolean, - Number, - Version, - String, - PropertyName, - - // Functions and named-values - WellKnownFunction, - ExtensionFunction, - ExtensionNamedValue, - UnknownKeyword, - - Unrecognized, - } -} diff --git a/src/Sdk/DTExpressions/Expressions/TypeCastException.cs b/src/Sdk/DTExpressions/Expressions/TypeCastException.cs deleted file mode 100644 index 59ad6afaa..000000000 --- a/src/Sdk/DTExpressions/Expressions/TypeCastException.cs +++ /dev/null @@ -1,67 +0,0 @@ -using System; -using GitHub.DistributedTask.Logging; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class TypeCastException : ExpressionException - { - internal TypeCastException(Type fromType, Type toType) - : base(null, String.Empty) - { - FromType = fromType; - ToType = toType; - m_message = ExpressionResources.TypeCastErrorNoValue(fromType.Name, toType.Name); - } - - internal TypeCastException(ISecretMasker secretMasker, Object value, ValueKind fromKind, ValueKind toKind) - : base(null, String.Empty) - { - Value = value; - FromKind = fromKind; - ToKind = toKind; - m_message = ExpressionResources.TypeCastError( - fromKind, // from kind - toKind, // to kind - ExpressionUtil.FormatValue(secretMasker, value, fromKind)); // value - } - - internal TypeCastException(ISecretMasker secretMasker, Object value, ValueKind fromKind, Type toType) - : base(null, String.Empty) - { - Value = value; - FromKind = fromKind; - ToType = toType; - m_message = ExpressionResources.TypeCastError( - fromKind, // from kind - toType, // to type - ExpressionUtil.FormatValue(secretMasker, value, fromKind)); // value - } - - internal TypeCastException(ISecretMasker secretMasker, Object value, ValueKind fromKind, Type toType, String error) - : base(null, String.Empty) - { - Value = value; - FromKind = fromKind; - ToType = toType; - m_message = ExpressionResources.TypeCastErrorWithError( - fromKind, // from kind - toType, // to type - ExpressionUtil.FormatValue(secretMasker, value, fromKind), // value - secretMasker != null ? secretMasker.MaskSecrets(error) : error); // error - } - - public override String Message => m_message; - - internal Object Value { get; } - - internal ValueKind? FromKind { get; } - - internal Type FromType { get; } - - internal ValueKind? ToKind { get; } - - internal Type ToType { get; } - - private readonly String m_message; - } -} diff --git a/src/Sdk/DTExpressions/Expressions/UnknownFunctionNode.cs b/src/Sdk/DTExpressions/Expressions/UnknownFunctionNode.cs deleted file mode 100644 index 6f22f1874..000000000 --- a/src/Sdk/DTExpressions/Expressions/UnknownFunctionNode.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class UnknownFunctionNode : FunctionNode - { - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // Should never reach here. - throw new NotSupportedException("Unknown function node is not supported during evaluation."); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/UnknownNamedValueNode.cs b/src/Sdk/DTExpressions/Expressions/UnknownNamedValueNode.cs deleted file mode 100644 index a6dedc643..000000000 --- a/src/Sdk/DTExpressions/Expressions/UnknownNamedValueNode.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class UnknownNamedValueNode : NamedValueNode - { - protected sealed override object EvaluateCore(EvaluationContext evaluationContext) - { - // Should never reach here. - throw new NotSupportedException("Unknown function node is not supported during evaluation."); - } - } -} diff --git a/src/Sdk/DTExpressions/Expressions/ValueKind.cs b/src/Sdk/DTExpressions/Expressions/ValueKind.cs deleted file mode 100644 index ea3dc8477..000000000 --- a/src/Sdk/DTExpressions/Expressions/ValueKind.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System.ComponentModel; - -namespace GitHub.DistributedTask.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public enum ValueKind - { - Array, - Boolean, - DateTime, - Null, - Number, - Object, - String, - Version, - } -} diff --git a/src/Sdk/DTExpressions/Expressions/XOrNode.cs b/src/Sdk/DTExpressions/Expressions/XOrNode.cs deleted file mode 100644 index e00837482..000000000 --- a/src/Sdk/DTExpressions/Expressions/XOrNode.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Expressions -{ - internal sealed class XorNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - return Parameters[0].EvaluateBoolean(context) ^ Parameters[1].EvaluateBoolean(context); - } - } -} diff --git a/src/Sdk/DTGenerated/Generated/TaskAgentHttpClientBase.cs b/src/Sdk/DTGenerated/Generated/TaskAgentHttpClientBase.cs index 408b407a3..cc92e4ff2 100644 --- a/src/Sdk/DTGenerated/Generated/TaskAgentHttpClientBase.cs +++ b/src/Sdk/DTGenerated/Generated/TaskAgentHttpClientBase.cs @@ -33,7 +33,7 @@ using GitHub.Services.WebApi; namespace GitHub.DistributedTask.WebApi { [ResourceArea(TaskResourceIds.AreaId)] - public abstract class TaskAgentHttpClientBase : TaskAgentHttpClientCompatBase + public abstract class TaskAgentHttpClientBase : VssHttpClientBase { public TaskAgentHttpClientBase(Uri baseUrl, VssCredentials credentials) : base(baseUrl, credentials) @@ -60,184 +60,6 @@ namespace GitHub.DistributedTask.WebApi { } - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task AddAgentCloudAsync( - TaskAgentCloud agentCloud, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("bfa72b3d-0fc6-43fb-932b-a7f6559f93b9"); - HttpContent content = new ObjectContent(agentCloud, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task DeleteAgentCloudAsync( - int agentCloudId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("bfa72b3d-0fc6-43fb-932b-a7f6559f93b9"); - object routeValues = new { agentCloudId = agentCloudId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task GetAgentCloudAsync( - int agentCloudId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("bfa72b3d-0fc6-43fb-932b-a7f6559f93b9"); - object routeValues = new { agentCloudId = agentCloudId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentCloudsAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("bfa72b3d-0fc6-43fb-932b-a7f6559f93b9"); - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get agent cloud types. - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentCloudTypesAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("5932e193-f376-469d-9c3e-e5588ce12cb5"); - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForQueueAsync( - int queueId, - int top, - string continuationToken = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5f81ffb-f396-498d-85b1-5ada145e648a"); - object routeValues = new { queueId = queueId }; - - List> queryParams = new List>(); - queryParams.Add("$top", top.ToString(CultureInfo.InvariantCulture)); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task QueueAgentRequestAsync( - int queueId, - TaskAgentJobRequest request, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f5f81ffb-f396-498d-85b1-5ada145e648a"); - object routeValues = new { queueId = queueId }; - HttpContent content = new ObjectContent(request, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - /// /// [Preview API] Adds an agent to a pool. You probably don't want to call this endpoint directly. Instead, [configure an agent](https://docs.microsoft.com/azure/devops/pipelines/agents/agents) using the agent download package. /// @@ -471,1685 +293,6 @@ namespace GitHub.DistributedTask.WebApi content: content); } - /// - /// [Preview API] Returns list of azure subscriptions - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetAzureManagementGroupsAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("39fe3bf2-7ee0-4198-a469-4a29929afa9c"); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Returns list of azure subscriptions - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetAzureSubscriptionsAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("bcd6189c-0303-471f-a8e1-acb22b74d700"); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] GET a PAT token for managing (configuring, removing, tagging) deployment targets in a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group in which deployment targets are managed. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GenerateDeploymentGroupAccessTokenAsync( - string project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("3d197ba2-c3e9-4253-882f-0ee2440f8174"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] GET a PAT token for managing (configuring, removing, tagging) deployment targets in a deployment group. - /// - /// Project ID - /// ID of the deployment group in which deployment targets are managed. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GenerateDeploymentGroupAccessTokenAsync( - Guid project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("3d197ba2-c3e9-4253-882f-0ee2440f8174"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Create a deployment group. - /// - /// Project ID or project name - /// Deployment group to create. - /// - /// The cancellation token to cancel operation. - public virtual Task AddDeploymentGroupAsync( - string project, - DeploymentGroupCreateParameter deploymentGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(deploymentGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a deployment group. - /// - /// Project ID - /// Deployment group to create. - /// - /// The cancellation token to cancel operation. - public virtual Task AddDeploymentGroupAsync( - Guid project, - DeploymentGroupCreateParameter deploymentGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(deploymentGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group to be deleted. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteDeploymentGroupAsync( - string project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete a deployment group. - /// - /// Project ID - /// ID of the deployment group to be deleted. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteDeploymentGroupAsync( - Guid project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get a deployment group by its ID. - /// - /// Project ID or project name - /// ID of the deployment group. - /// Get the deployment group only if this action can be performed on it. - /// Include these additional details in the returned object. - /// - /// The cancellation token to cancel operation. - public virtual Task GetDeploymentGroupAsync( - string project, - int deploymentGroupId, - DeploymentGroupActionFilter? actionFilter = null, - DeploymentGroupExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a deployment group by its ID. - /// - /// Project ID - /// ID of the deployment group. - /// Get the deployment group only if this action can be performed on it. - /// Include these additional details in the returned object. - /// - /// The cancellation token to cancel operation. - public virtual Task GetDeploymentGroupAsync( - Guid project, - int deploymentGroupId, - DeploymentGroupActionFilter? actionFilter = null, - DeploymentGroupExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment groups by name or IDs. - /// - /// Project ID or project name - /// Name of the deployment group. - /// Get only deployment groups on which this action can be performed. - /// Include these additional details in the returned objects. - /// Get deployment groups with names greater than this continuationToken lexicographically. - /// Maximum number of deployment groups to return. Default is **1000**. - /// Comma separated list of IDs of the deployment groups. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentGroupsAsync( - string project, - string name = null, - DeploymentGroupActionFilter? actionFilter = null, - DeploymentGroupExpands? expand = null, - string continuationToken = null, - int? top = null, - IEnumerable ids = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (name != null) - { - queryParams.Add("name", name); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (ids != null && ids.Any()) - { - queryParams.Add("ids", string.Join(",", ids)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment groups by name or IDs. - /// - /// Project ID - /// Name of the deployment group. - /// Get only deployment groups on which this action can be performed. - /// Include these additional details in the returned objects. - /// Get deployment groups with names greater than this continuationToken lexicographically. - /// Maximum number of deployment groups to return. Default is **1000**. - /// Comma separated list of IDs of the deployment groups. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentGroupsAsync( - Guid project, - string name = null, - DeploymentGroupActionFilter? actionFilter = null, - DeploymentGroupExpands? expand = null, - string continuationToken = null, - int? top = null, - IEnumerable ids = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (name != null) - { - queryParams.Add("name", name); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (ids != null && ids.Any()) - { - queryParams.Add("ids", string.Join(",", ids)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Update a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group. - /// Deployment group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateDeploymentGroupAsync( - string project, - int deploymentGroupId, - DeploymentGroupUpdateParameter deploymentGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(deploymentGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a deployment group. - /// - /// Project ID - /// ID of the deployment group. - /// Deployment group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateDeploymentGroupAsync( - Guid project, - int deploymentGroupId, - DeploymentGroupUpdateParameter deploymentGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("083c4d89-ab35-45af-aa11-7cf66895c53e"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(deploymentGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Get a list of deployment group metrics. - /// - /// Project ID or project name - /// Name of the deployment group. - /// Get metrics for deployment groups with names greater than this continuationToken lexicographically. - /// Maximum number of deployment group metrics to return. Default is **50**. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentGroupsMetricsAsync( - string project, - string deploymentGroupName = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("281c6308-427a-49e1-b83a-dac0f4862189"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (deploymentGroupName != null) - { - queryParams.Add("deploymentGroupName", deploymentGroupName); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment group metrics. - /// - /// Project ID - /// Name of the deployment group. - /// Get metrics for deployment groups with names greater than this continuationToken lexicographically. - /// Maximum number of deployment group metrics to return. Default is **50**. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentGroupsMetricsAsync( - Guid project, - string deploymentGroupName = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("281c6308-427a-49e1-b83a-dac0f4862189"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (deploymentGroupName != null) - { - queryParams.Add("deploymentGroupName", deploymentGroupName); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentMachineAsync( - string project, - int deploymentGroupId, - int machineId, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a3540e5b-f0dc-4668-963b-b752459be545"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - queryParams.Add("machineId", machineId.ToString(CultureInfo.InvariantCulture)); - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - int machineId, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a3540e5b-f0dc-4668-963b-b752459be545"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - queryParams.Add("machineId", machineId.ToString(CultureInfo.InvariantCulture)); - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentMachinesAsync( - string project, - int deploymentGroupId, - IEnumerable machineIds = null, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a3540e5b-f0dc-4668-963b-b752459be545"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (machineIds != null && machineIds.Any()) - { - queryParams.Add("machineIds", string.Join(",", machineIds)); - } - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentMachinesAsync( - Guid project, - int deploymentGroupId, - IEnumerable machineIds = null, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a3540e5b-f0dc-4668-963b-b752459be545"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (machineIds != null && machineIds.Any()) - { - queryParams.Add("machineIds", string.Join(",", machineIds)); - } - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task RefreshDeploymentMachinesAsync( - string project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("91006ac4-0f68-4d82-a2bc-540676bd73ce"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task RefreshDeploymentMachinesAsync( - Guid project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("91006ac4-0f68-4d82-a2bc-540676bd73ce"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] GET a PAT token for managing (configuring, removing, tagging) deployment agents in a deployment pool. - /// - /// ID of the deployment pool in which deployment agents are managed. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GenerateDeploymentPoolAccessTokenAsync( - int poolId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("e077ee4a-399b-420b-841f-c43fbc058e0b"); - object routeValues = new { poolId = poolId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment pool summaries. - /// - /// Name of the deployment pool. - /// Include these additional details in the returned objects. - /// List of deployment pool ids. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentPoolsSummaryAsync( - string poolName = null, - DeploymentPoolSummaryExpands? expands = null, - IEnumerable poolIds = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6525d6c6-258f-40e0-a1a9-8a24a3957625"); - - List> queryParams = new List>(); - if (poolName != null) - { - queryParams.Add("poolName", poolName); - } - if (expands != null) - { - queryParams.Add("expands", expands.Value.ToString()); - } - if (poolIds != null && poolIds.Any()) - { - queryParams.Add("poolIds", string.Join(",", poolIds)); - } - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get agent requests for a deployment target. - /// - /// Project ID or project name - /// ID of the deployment group to which the target belongs. - /// ID of the deployment target. - /// Maximum number of completed requests to return. Default is **50** - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentTargetAsync( - string project, - int deploymentGroupId, - int targetId, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2fac0be3-8c8f-4473-ab93-c1389b08a2c9"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - queryParams.Add("targetId", targetId.ToString(CultureInfo.InvariantCulture)); - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get agent requests for a deployment target. - /// - /// Project ID - /// ID of the deployment group to which the target belongs. - /// ID of the deployment target. - /// Maximum number of completed requests to return. Default is **50** - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - int targetId, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2fac0be3-8c8f-4473-ab93-c1389b08a2c9"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - queryParams.Add("targetId", targetId.ToString(CultureInfo.InvariantCulture)); - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get agent requests for a list deployment targets. - /// - /// Project ID or project name - /// ID of the deployment group to which the targets belong. - /// Comma separated list of IDs of the deployment targets. - /// Id of owner of agent job request. - /// Datetime to return request after this time. - /// Maximum number of completed requests to return for each target. Default is **50** - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentTargetsAsync( - string project, - int deploymentGroupId, - IEnumerable targetIds = null, - int? ownerId = null, - DateTime? completedOn = null, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2fac0be3-8c8f-4473-ab93-c1389b08a2c9"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (targetIds != null && targetIds.Any()) - { - queryParams.Add("targetIds", string.Join(",", targetIds)); - } - if (ownerId != null) - { - queryParams.Add("ownerId", ownerId.Value.ToString(CultureInfo.InvariantCulture)); - } - if (completedOn != null) - { - AddDateTimeToQueryParams(queryParams, "completedOn", completedOn.Value); - } - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get agent requests for a list deployment targets. - /// - /// Project ID - /// ID of the deployment group to which the targets belong. - /// Comma separated list of IDs of the deployment targets. - /// Id of owner of agent job request. - /// Datetime to return request after this time. - /// Maximum number of completed requests to return for each target. Default is **50** - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForDeploymentTargetsAsync( - Guid project, - int deploymentGroupId, - IEnumerable targetIds = null, - int? ownerId = null, - DateTime? completedOn = null, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2fac0be3-8c8f-4473-ab93-c1389b08a2c9"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (targetIds != null && targetIds.Any()) - { - queryParams.Add("targetIds", string.Join(",", targetIds)); - } - if (ownerId != null) - { - queryParams.Add("ownerId", ownerId.Value.ToString(CultureInfo.InvariantCulture)); - } - if (completedOn != null) - { - AddDateTimeToQueryParams(queryParams, "completedOn", completedOn.Value); - } - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Upgrade the deployment targets in a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task RefreshDeploymentTargetsAsync( - string project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("1c1a817f-f23d-41c6-bf8d-14b638f64152"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Upgrade the deployment targets in a deployment group. - /// - /// Project ID - /// ID of the deployment group. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task RefreshDeploymentTargetsAsync( - Guid project, - int deploymentGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("1c1a817f-f23d-41c6-bf8d-14b638f64152"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Proxy for a GET request defined by an 'endpoint'. The request is authorized using a service connection. The response is filtered using an XPath/Json based selector. - /// - /// Describes the URL to fetch. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> QueryEndpointAsync( - TaskDefinitionEndpoint endpoint, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f223b809-8c33-4b7d-b53f-07232569b5d6"); - HttpContent content = new ObjectContent(endpoint, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Get environment deployment execution history - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetEnvironmentDeploymentExecutionRecordsAsync( - string project, - int environmentId, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("51bb5d21-4305-4ea6-9dbb-b7488af73334"); - object routeValues = new { project = project, environmentId = environmentId }; - - List> queryParams = new List>(); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get environment deployment execution history - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetEnvironmentDeploymentExecutionRecordsAsync( - Guid project, - int environmentId, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("51bb5d21-4305-4ea6-9dbb-b7488af73334"); - object routeValues = new { project = project, environmentId = environmentId }; - - List> queryParams = new List>(); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Create an environment. - /// - /// Project ID or project name - /// Environment to create. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddEnvironmentAsync( - string project, - EnvironmentCreateParameter environmentCreateParameter, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(environmentCreateParameter, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create an environment. - /// - /// Project ID - /// Environment to create. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddEnvironmentAsync( - Guid project, - EnvironmentCreateParameter environmentCreateParameter, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(environmentCreateParameter, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete the specified environment. - /// - /// Project ID or project name - /// ID of the environment. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteEnvironmentAsync( - string project, - int environmentId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete the specified environment. - /// - /// Project ID - /// ID of the environment. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteEnvironmentAsync( - Guid project, - int environmentId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get an environment by its ID. - /// - /// Project ID or project name - /// ID of the environment. - /// Include these additional details in the returned objects. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetEnvironmentByIdAsync( - string project, - int environmentId, - EnvironmentExpands? expands = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - - List> queryParams = new List>(); - if (expands != null) - { - queryParams.Add("expands", expands.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get an environment by its ID. - /// - /// Project ID - /// ID of the environment. - /// Include these additional details in the returned objects. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetEnvironmentByIdAsync( - Guid project, - int environmentId, - EnvironmentExpands? expands = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - - List> queryParams = new List>(); - if (expands != null) - { - queryParams.Add("expands", expands.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get all environments. - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetEnvironmentsAsync( - string project, - string name = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (name != null) - { - queryParams.Add("name", name); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get all environments. - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetEnvironmentsAsync( - Guid project, - string name = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (name != null) - { - queryParams.Add("name", name); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Update the specified environment. - /// - /// Project ID or project name - /// ID of the environment. - /// Environment data to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateEnvironmentAsync( - string project, - int environmentId, - EnvironmentUpdateParameter environmentUpdateParameter, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(environmentUpdateParameter, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update the specified environment. - /// - /// Project ID - /// ID of the environment. - /// Environment data to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateEnvironmentAsync( - Guid project, - int environmentId, - EnvironmentUpdateParameter environmentUpdateParameter, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("8572b1fc-2482-47fa-8f74-7e3ed53ee54b"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(environmentUpdateParameter, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetTaskHubLicenseDetailsAsync( - string hubName, - bool? includeEnterpriseUsersCount = null, - bool? includeHostedAgentMinutesCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f9f0f436-b8a1-4475-9041-1ccdbf8f0128"); - object routeValues = new { hubName = hubName }; - - List> queryParams = new List>(); - if (includeEnterpriseUsersCount != null) - { - queryParams.Add("includeEnterpriseUsersCount", includeEnterpriseUsersCount.Value.ToString()); - } - if (includeHostedAgentMinutesCount != null) - { - queryParams.Add("includeHostedAgentMinutesCount", includeHostedAgentMinutesCount.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 3), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateTaskHubLicenseDetailsAsync( - string hubName, - TaskHubLicenseDetails taskHubLicenseDetails, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("f9f0f436-b8a1-4475-9041-1ccdbf8f0128"); - object routeValues = new { hubName = hubName }; - HttpContent content = new ObjectContent(taskHubLicenseDetails, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 3), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetTaskIconAsync( - Guid taskId, - string versionString, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("63463108-174d-49d4-b8cb-235eea42a5e1"); - object routeValues = new { taskId = taskId, versionString = versionString }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task ValidateInputsAsync( - InputValidationRequest inputValidationRequest, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("58475b1e-adaf-4155-9bc1-e04bf1fff4c2"); - HttpContent content = new ObjectContent(inputValidationRequest, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - /// /// [Preview API] /// @@ -2228,186 +371,6 @@ namespace GitHub.DistributedTask.WebApi cancellationToken: cancellationToken); } - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsAsync( - int poolId, - int top, - string continuationToken = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("fc825784-c92a-4299-9221-998a02d1b54f"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - queryParams.Add("$top", top.ToString(CultureInfo.InvariantCulture)); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForAgentAsync( - int poolId, - int agentId, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("fc825784-c92a-4299-9221-998a02d1b54f"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - queryParams.Add("agentId", agentId.ToString(CultureInfo.InvariantCulture)); - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForAgentsAsync( - int poolId, - IEnumerable agentIds = null, - int? completedRequestCount = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("fc825784-c92a-4299-9221-998a02d1b54f"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - if (agentIds != null && agentIds.Any()) - { - queryParams.Add("agentIds", string.Join(",", agentIds)); - } - if (completedRequestCount != null) - { - queryParams.Add("completedRequestCount", completedRequestCount.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentRequestsForPlanAsync( - int poolId, - Guid planId, - Guid? jobId = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("fc825784-c92a-4299-9221-998a02d1b54f"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - queryParams.Add("planId", planId.ToString()); - if (jobId != null) - { - queryParams.Add("jobId", jobId.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task QueueAgentRequestByPoolAsync( - int poolId, - TaskAgentJobRequest request, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("fc825784-c92a-4299-9221-998a02d1b54f"); - object routeValues = new { poolId = poolId }; - HttpContent content = new ObjectContent(request, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - /// /// [Preview API] /// @@ -2445,1536 +408,6 @@ namespace GitHub.DistributedTask.WebApi content: content); } - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddKubernetesResourceAsync( - string project, - int environmentId, - KubernetesResourceCreateParameters createParameters, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(createParameters, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddKubernetesResourceAsync( - Guid project, - int environmentId, - KubernetesResourceCreateParameters createParameters, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(createParameters, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteKubernetesResourceAsync( - string project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteKubernetesResourceAsync( - Guid project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetKubernetesResourceAsync( - string project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetKubernetesResourceAsync( - Guid project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("73fba52f-15ab-42b3-a538-ce67a9223a04"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GenerateDeploymentMachineGroupAccessTokenAsync( - string project, - int machineGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f8c7c0de-ac0d-469b-9cb1-c21f72d67693"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GenerateDeploymentMachineGroupAccessTokenAsync( - Guid project, - int machineGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f8c7c0de-ac0d-469b-9cb1-c21f72d67693"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentMachineGroupAsync( - string project, - DeploymentMachineGroup machineGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(machineGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentMachineGroupAsync( - Guid project, - DeploymentMachineGroup machineGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(machineGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteDeploymentMachineGroupAsync( - string project, - int machineGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteDeploymentMachineGroupAsync( - Guid project, - int machineGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetDeploymentMachineGroupAsync( - string project, - int machineGroupId, - MachineGroupActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetDeploymentMachineGroupAsync( - Guid project, - int machineGroupId, - MachineGroupActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachineGroupsAsync( - string project, - string machineGroupName = null, - MachineGroupActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (machineGroupName != null) - { - queryParams.Add("machineGroupName", machineGroupName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachineGroupsAsync( - Guid project, - string machineGroupName = null, - MachineGroupActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (machineGroupName != null) - { - queryParams.Add("machineGroupName", machineGroupName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentMachineGroupAsync( - string project, - int machineGroupId, - DeploymentMachineGroup machineGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - HttpContent content = new ObjectContent(machineGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentMachineGroupAsync( - Guid project, - int machineGroupId, - DeploymentMachineGroup machineGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("d4adf50f-80c6-4ac8-9ca1-6e4e544286e9"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - HttpContent content = new ObjectContent(machineGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachineGroupMachinesAsync( - string project, - int machineGroupId, - IEnumerable tagFilters = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("966c3874-c347-4b18-a90c-d509116717fd"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - List> queryParams = new List>(); - if (tagFilters != null && tagFilters.Any()) - { - queryParams.Add("tagFilters", string.Join(",", tagFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachineGroupMachinesAsync( - Guid project, - int machineGroupId, - IEnumerable tagFilters = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("966c3874-c347-4b18-a90c-d509116717fd"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - - List> queryParams = new List>(); - if (tagFilters != null && tagFilters.Any()) - { - queryParams.Add("tagFilters", string.Join(",", tagFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateDeploymentMachineGroupMachinesAsync( - string project, - int machineGroupId, - IEnumerable deploymentMachines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("966c3874-c347-4b18-a90c-d509116717fd"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - HttpContent content = new ObjectContent>(deploymentMachines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateDeploymentMachineGroupMachinesAsync( - Guid project, - int machineGroupId, - IEnumerable deploymentMachines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("966c3874-c347-4b18-a90c-d509116717fd"); - object routeValues = new { project = project, machineGroupId = machineGroupId }; - HttpContent content = new ObjectContent>(deploymentMachines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentMachineAsync( - string project, - int deploymentGroupId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteDeploymentMachineAsync( - string project, - int deploymentGroupId, - int machineId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - int machineId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetDeploymentMachineAsync( - string project, - int deploymentGroupId, - int machineId, - DeploymentMachineExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - - List> queryParams = new List>(); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - int machineId, - DeploymentMachineExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - - List> queryParams = new List>(); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachinesAsync( - string project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - DeploymentMachineExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetDeploymentMachinesAsync( - Guid project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - DeploymentMachineExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task ReplaceDeploymentMachineAsync( - string project, - int deploymentGroupId, - int machineId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task ReplaceDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - int machineId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentMachineAsync( - string project, - int deploymentGroupId, - int machineId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentMachineAsync( - Guid project, - int deploymentGroupId, - int machineId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, machineId = machineId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateDeploymentMachinesAsync( - string project, - int deploymentGroupId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateDeploymentMachinesAsync( - Guid project, - int deploymentGroupId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6f6d406f-cfe6-409c-9327-7009928077e7"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task CreateAgentPoolMaintenanceDefinitionAsync( - int poolId, - TaskAgentPoolMaintenanceDefinition definition, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("80572e16-58f0-4419-ac07-d19fde32195c"); - object routeValues = new { poolId = poolId }; - HttpContent content = new ObjectContent(definition, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteAgentPoolMaintenanceDefinitionAsync( - int poolId, - int definitionId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("80572e16-58f0-4419-ac07-d19fde32195c"); - object routeValues = new { poolId = poolId, definitionId = definitionId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetAgentPoolMaintenanceDefinitionAsync( - int poolId, - int definitionId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("80572e16-58f0-4419-ac07-d19fde32195c"); - object routeValues = new { poolId = poolId, definitionId = definitionId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentPoolMaintenanceDefinitionsAsync( - int poolId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("80572e16-58f0-4419-ac07-d19fde32195c"); - object routeValues = new { poolId = poolId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateAgentPoolMaintenanceDefinitionAsync( - int poolId, - int definitionId, - TaskAgentPoolMaintenanceDefinition definition, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("80572e16-58f0-4419-ac07-d19fde32195c"); - object routeValues = new { poolId = poolId, definitionId = definitionId }; - HttpContent content = new ObjectContent(definition, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteAgentPoolMaintenanceJobAsync( - int poolId, - int jobId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId, jobId = jobId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetAgentPoolMaintenanceJobAsync( - int poolId, - int jobId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId, jobId = jobId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task GetAgentPoolMaintenanceJobLogsAsync( - int poolId, - int jobId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId, jobId = jobId }; - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - mediaType: "application/zip", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetAgentPoolMaintenanceJobsAsync( - int poolId, - int? definitionId = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - if (definitionId != null) - { - queryParams.Add("definitionId", definitionId.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task QueueAgentPoolMaintenanceJobAsync( - int poolId, - TaskAgentPoolMaintenanceJob job, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId }; - HttpContent content = new ObjectContent(job, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateAgentPoolMaintenanceJobAsync( - int poolId, - int jobId, - TaskAgentPoolMaintenanceJob job, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("15e7ab6e-abce-4601-a6d8-e111fe148f46"); - object routeValues = new { poolId = poolId, jobId = jobId }; - HttpContent content = new ObjectContent(job, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - /// /// [Preview API] /// @@ -4213,135 +646,6 @@ namespace GitHub.DistributedTask.WebApi cancellationToken: cancellationToken); } - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task GetAgentPoolMetadataAsync( - int poolId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("0d62f887-9f53-48b9-9161-4c35d5735b0f"); - object routeValues = new { poolId = poolId }; - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - mediaType: "text/plain", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] Create an agent pool. - /// - /// Details about the new agent pool - /// - /// The cancellation token to cancel operation. - public virtual Task AddAgentPoolAsync( - TaskAgentPool pool, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("a8c47e17-4d56-4a56-92bb-de7ea7dc65be"); - HttpContent content = new ObjectContent(pool, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete an agent pool. - /// - /// ID of the agent pool to delete - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteAgentPoolAsync( - int poolId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("a8c47e17-4d56-4a56-92bb-de7ea7dc65be"); - object routeValues = new { poolId = poolId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get information about an agent pool. - /// - /// An agent pool ID - /// Agent pool properties (comma-separated) - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task GetAgentPoolAsync( - int poolId, - IEnumerable properties = null, - TaskAgentPoolActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a8c47e17-4d56-4a56-92bb-de7ea7dc65be"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - if (properties != null && properties.Any()) - { - queryParams.Add("properties", string.Join(",", properties)); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] Get a list of agent pools. /// @@ -4355,7 +659,6 @@ namespace GitHub.DistributedTask.WebApi string poolName = null, IEnumerable properties = null, TaskAgentPoolType? poolType = null, - TaskAgentPoolActionFilter? actionFilter = null, object userState = null, CancellationToken cancellationToken = default) { @@ -4375,10 +678,6 @@ namespace GitHub.DistributedTask.WebApi { queryParams.Add("poolType", poolType.Value.ToString()); } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } return SendAsync>( httpMethod, @@ -4389,1752 +688,6 @@ namespace GitHub.DistributedTask.WebApi cancellationToken: cancellationToken); } - /// - /// [Preview API] Get a list of agent pools. - /// - /// pool Ids to fetch - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentPoolsByIdsAsync( - IEnumerable poolIds, - TaskAgentPoolActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("a8c47e17-4d56-4a56-92bb-de7ea7dc65be"); - - List> queryParams = new List>(); - string poolIdsAsString = null; - if (poolIds != null) - { - poolIdsAsString = string.Join(",", poolIds); - } - queryParams.Add("poolIds", poolIdsAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Update properties on an agent pool - /// - /// The agent pool to update - /// Updated agent pool details - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateAgentPoolAsync( - int poolId, - TaskAgentPool pool, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("a8c47e17-4d56-4a56-92bb-de7ea7dc65be"); - object routeValues = new { poolId = poolId }; - HttpContent content = new ObjectContent(pool, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a new agent queue to connect a project to an agent pool. - /// - /// Details about the queue to create - /// Automatically authorize this queue when using YAML - /// - /// The cancellation token to cancel operation. - public virtual Task AddAgentQueueAsync( - TaskAgentQueue queue, - bool? authorizePipelines = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - HttpContent content = new ObjectContent(queue, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (authorizePipelines != null) - { - queryParams.Add("authorizePipelines", authorizePipelines.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a new agent queue to connect a project to an agent pool. - /// - /// Project ID or project name - /// Details about the queue to create - /// Automatically authorize this queue when using YAML - /// - /// The cancellation token to cancel operation. - public virtual Task AddAgentQueueAsync( - string project, - TaskAgentQueue queue, - bool? authorizePipelines = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(queue, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (authorizePipelines != null) - { - queryParams.Add("authorizePipelines", authorizePipelines.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a new agent queue to connect a project to an agent pool. - /// - /// Project ID - /// Details about the queue to create - /// Automatically authorize this queue when using YAML - /// - /// The cancellation token to cancel operation. - public virtual Task AddAgentQueueAsync( - Guid project, - TaskAgentQueue queue, - bool? authorizePipelines = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(queue, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (authorizePipelines != null) - { - queryParams.Add("authorizePipelines", authorizePipelines.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a new team project. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task CreateTeamProjectAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Create a new team project. - /// - /// Project ID or project name - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task CreateTeamProjectAsync( - string project, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Create a new team project. - /// - /// Project ID - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task CreateTeamProjectAsync( - Guid project, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Removes an agent queue from a project. - /// - /// The agent queue to remove - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteAgentQueueAsync( - int queueId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { queueId = queueId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Removes an agent queue from a project. - /// - /// Project ID or project name - /// The agent queue to remove - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteAgentQueueAsync( - string project, - int queueId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project, queueId = queueId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Removes an agent queue from a project. - /// - /// Project ID - /// The agent queue to remove - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteAgentQueueAsync( - Guid project, - int queueId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project, queueId = queueId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get information about an agent queue. - /// - /// Project ID or project name - /// The agent queue to get information about - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task GetAgentQueueAsync( - string project, - int queueId, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project, queueId = queueId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get information about an agent queue. - /// - /// Project ID - /// The agent queue to get information about - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task GetAgentQueueAsync( - Guid project, - int queueId, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project, queueId = queueId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get information about an agent queue. - /// - /// The agent queue to get information about - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task GetAgentQueueAsync( - int queueId, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { queueId = queueId }; - - List> queryParams = new List>(); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues. - /// - /// Project ID or project name - /// Filter on the agent queue name - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesAsync( - string project, - string queueName = null, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (queueName != null) - { - queryParams.Add("queueName", queueName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues. - /// - /// Project ID - /// Filter on the agent queue name - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesAsync( - Guid project, - string queueName = null, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (queueName != null) - { - queryParams.Add("queueName", queueName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues. - /// - /// Filter on the agent queue name - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesAsync( - string queueName = null, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - - List> queryParams = new List>(); - if (queueName != null) - { - queryParams.Add("queueName", queueName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their IDs - /// - /// Project ID or project name - /// A comma-separated list of agent queue IDs to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByIdsAsync( - string project, - IEnumerable queueIds, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string queueIdsAsString = null; - if (queueIds != null) - { - queueIdsAsString = string.Join(",", queueIds); - } - queryParams.Add("queueIds", queueIdsAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their IDs - /// - /// Project ID - /// A comma-separated list of agent queue IDs to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByIdsAsync( - Guid project, - IEnumerable queueIds, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string queueIdsAsString = null; - if (queueIds != null) - { - queueIdsAsString = string.Join(",", queueIds); - } - queryParams.Add("queueIds", queueIdsAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their IDs - /// - /// A comma-separated list of agent queue IDs to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByIdsAsync( - IEnumerable queueIds, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - - List> queryParams = new List>(); - string queueIdsAsString = null; - if (queueIds != null) - { - queueIdsAsString = string.Join(",", queueIds); - } - queryParams.Add("queueIds", queueIdsAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their names - /// - /// Project ID or project name - /// A comma-separated list of agent names to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByNamesAsync( - string project, - IEnumerable queueNames, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string queueNamesAsString = null; - if (queueNames != null) - { - queueNamesAsString = string.Join(",", queueNames); - } - queryParams.Add("queueNames", queueNamesAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their names - /// - /// Project ID - /// A comma-separated list of agent names to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByNamesAsync( - Guid project, - IEnumerable queueNames, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string queueNamesAsString = null; - if (queueNames != null) - { - queueNamesAsString = string.Join(",", queueNames); - } - queryParams.Add("queueNames", queueNamesAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agent queues by their names - /// - /// A comma-separated list of agent names to retrieve - /// Filter by whether the calling user has use or manage permissions - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentQueuesByNamesAsync( - IEnumerable queueNames, - TaskAgentQueueActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("900fa995-c559-4923-aae7-f8424fe4fbea"); - - List> queryParams = new List>(); - string queueNamesAsString = null; - if (queueNames != null) - { - queueNamesAsString = string.Join(",", queueNames); - } - queryParams.Add("queueNames", queueNamesAsString); - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAgentCloudRequestsAsync( - int agentCloudId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("20189bd7-5134-49c2-b8e9-f9e856eea2b2"); - object routeValues = new { agentCloudId = agentCloudId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetResourceLimitsAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("1f1f0557-c445-42a6-b4a0-0df605a3a0f8"); - - return SendAsync>( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetResourceUsageAsync( - string parallelismTag = null, - bool? poolIsHosted = null, - bool? includeRunningRequests = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("eae1d376-a8b1-4475-9041-1dfdbe8f0143"); - - List> queryParams = new List>(); - if (parallelismTag != null) - { - queryParams.Add("parallelismTag", parallelismTag); - } - if (poolIsHosted != null) - { - queryParams.Add("poolIsHosted", poolIsHosted.Value.ToString()); - } - if (includeRunningRequests != null) - { - queryParams.Add("includeRunningRequests", includeRunningRequests.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 2), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetTaskGroupHistoryAsync( - string project, - Guid taskGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("100cc92a-b255-47fa-9ab3-e44a2985a3ac"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetTaskGroupHistoryAsync( - Guid project, - Guid taskGroupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("100cc92a-b255-47fa-9ab3-e44a2985a3ac"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Delete a secure file - /// - /// Project ID or project name - /// The unique secure file Id - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteSecureFileAsync( - string project, - Guid secureFileId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete a secure file - /// - /// Project ID - /// The unique secure file Id - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteSecureFileAsync( - Guid project, - Guid secureFileId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Download a secure file by Id - /// - /// Project ID or project name - /// The unique secure file Id - /// A valid download ticket - /// If download is true, the file is sent as attachement in the response body. If download is false, the response body contains the file stream. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DownloadSecureFileAsync( - string project, - Guid secureFileId, - string ticket, - bool? download = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - List> queryParams = new List>(); - queryParams.Add("ticket", ticket); - if (download != null) - { - queryParams.Add("download", download.Value.ToString()); - } - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - queryParameters: queryParams, - mediaType: "application/octet-stream", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] Download a secure file by Id - /// - /// Project ID - /// The unique secure file Id - /// A valid download ticket - /// If download is true, the file is sent as attachement in the response body. If download is false, the response body contains the file stream. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DownloadSecureFileAsync( - Guid project, - Guid secureFileId, - string ticket, - bool? download = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - List> queryParams = new List>(); - queryParams.Add("ticket", ticket); - if (download != null) - { - queryParams.Add("download", download.Value.ToString()); - } - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - queryParameters: queryParams, - mediaType: "application/octet-stream", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] Get a secure file - /// - /// Project ID or project name - /// The unique secure file Id - /// If includeDownloadTicket is true and the caller has permissions, a download ticket is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetSecureFileAsync( - string project, - Guid secureFileId, - bool? includeDownloadTicket = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - List> queryParams = new List>(); - if (includeDownloadTicket != null) - { - queryParams.Add("includeDownloadTicket", includeDownloadTicket.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a secure file - /// - /// Project ID - /// The unique secure file Id - /// If includeDownloadTicket is true and the caller has permissions, a download ticket is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetSecureFileAsync( - Guid project, - Guid secureFileId, - bool? includeDownloadTicket = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - - List> queryParams = new List>(); - if (includeDownloadTicket != null) - { - queryParams.Add("includeDownloadTicket", includeDownloadTicket.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID or project name - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// Filter by secure file permissions for View, Manage or Use action. Defaults to View. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesAsync( - string project, - string namePattern = null, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (namePattern != null) - { - queryParams.Add("namePattern", namePattern); - } - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// Filter by secure file permissions for View, Manage or Use action. Defaults to View. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesAsync( - Guid project, - string namePattern = null, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (namePattern != null) - { - queryParams.Add("namePattern", namePattern); - } - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID or project name - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesByIdsAsync( - string project, - IEnumerable secureFileIds, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string secureFileIdsAsString = null; - if (secureFileIds != null) - { - secureFileIdsAsString = string.Join(",", secureFileIds); - } - queryParams.Add("secureFileIds", secureFileIdsAsString); - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesByIdsAsync( - Guid project, - IEnumerable secureFileIds, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string secureFileIdsAsString = null; - if (secureFileIds != null) - { - secureFileIdsAsString = string.Join(",", secureFileIds); - } - queryParams.Add("secureFileIds", secureFileIdsAsString); - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID or project name - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesByNamesAsync( - string project, - IEnumerable secureFileNames, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string secureFileNamesAsString = null; - if (secureFileNames != null) - { - secureFileNamesAsString = string.Join(",", secureFileNames); - } - queryParams.Add("secureFileNames", secureFileNamesAsString); - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetSecureFilesByNamesAsync( - Guid project, - IEnumerable secureFileNames, - bool? includeDownloadTickets = null, - SecureFileActionFilter? actionFilter = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string secureFileNamesAsString = null; - if (secureFileNames != null) - { - secureFileNamesAsString = string.Join(",", secureFileNames); - } - queryParams.Add("secureFileNames", secureFileNamesAsString); - if (includeDownloadTickets != null) - { - queryParams.Add("includeDownloadTickets", includeDownloadTickets.Value.ToString()); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Query secure files using a name pattern and a condition on file properties. - /// - /// Project ID or project name - /// The main condition syntax is described [here](https://go.microsoft.com/fwlink/?linkid=842996). Use the *property('property-name')* function to access the value of the specified property of a secure file. It returns null if the property is not set. E.g. ``` and( eq( property('devices'), '2' ), in( property('provisioning profile type'), 'ad hoc', 'development' ) ) ``` - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> QuerySecureFilesByPropertiesAsync( - string project, - string condition, - string namePattern = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(condition, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (namePattern != null) - { - queryParams.Add("namePattern", namePattern); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Query secure files using a name pattern and a condition on file properties. - /// - /// Project ID - /// The main condition syntax is described [here](https://go.microsoft.com/fwlink/?linkid=842996). Use the *property('property-name')* function to access the value of the specified property of a secure file. It returns null if the property is not set. E.g. ``` and( eq( property('devices'), '2' ), in( property('provisioning profile type'), 'ad hoc', 'development' ) ) ``` - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> QuerySecureFilesByPropertiesAsync( - Guid project, - string condition, - string namePattern = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(condition, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (namePattern != null) - { - queryParams.Add("namePattern", namePattern); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update the name or properties of an existing secure file - /// - /// Project ID or project name - /// The unique secure file Id - /// The secure file with updated name and/or properties - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateSecureFileAsync( - string project, - Guid secureFileId, - SecureFile secureFile, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - HttpContent content = new ObjectContent(secureFile, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update the name or properties of an existing secure file - /// - /// Project ID - /// The unique secure file Id - /// The secure file with updated name and/or properties - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateSecureFileAsync( - Guid project, - Guid secureFileId, - SecureFile secureFile, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project, secureFileId = secureFileId }; - HttpContent content = new ObjectContent(secureFile, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update properties and/or names of a set of secure files. Files are identified by their IDs. Properties provided override the existing one entirely, i.e. do not merge. - /// - /// Project ID or project name - /// A list of secure file objects. Only three field must be populated Id, Name, and Properties. The rest of fields in the object are ignored. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateSecureFilesAsync( - string project, - IEnumerable secureFiles, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent>(secureFiles, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update properties and/or names of a set of secure files. Files are identified by their IDs. Properties provided override the existing one entirely, i.e. do not merge. - /// - /// Project ID - /// A list of secure file objects. Only three field must be populated Id, Name, and Properties. The rest of fields in the object are ignored. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateSecureFilesAsync( - Guid project, - IEnumerable secureFiles, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent>(secureFiles, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Upload a secure file, include the file stream in the request body - /// - /// Project ID or project name - /// Stream to upload - /// Name of the file to upload - /// If authorizePipelines is true, then the secure file is authorized for use by all pipelines in the project. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UploadSecureFileAsync( - string project, - Stream uploadStream, - string name, - bool? authorizePipelines = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new StreamContent(uploadStream); - content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); - - List> queryParams = new List>(); - queryParams.Add("name", name); - if (authorizePipelines != null) - { - queryParams.Add("authorizePipelines", authorizePipelines.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Upload a secure file, include the file stream in the request body - /// - /// Project ID - /// Stream to upload - /// Name of the file to upload - /// If authorizePipelines is true, then the secure file is authorized for use by all pipelines in the project. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UploadSecureFileAsync( - Guid project, - Stream uploadStream, - string name, - bool? authorizePipelines = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("adcfd8bc-b184-43ba-bd84-7c8c6a2ff421"); - object routeValues = new { project = project }; - HttpContent content = new StreamContent(uploadStream); - content.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); - - List> queryParams = new List>(); - queryParams.Add("name", name); - if (authorizePipelines != null) - { - queryParams.Add("authorizePipelines", authorizePipelines.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - /// /// [Preview API] /// @@ -6194,1502 +747,6 @@ namespace GitHub.DistributedTask.WebApi } } - /// - /// [Preview API] Register a deployment target to a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID or project name - /// ID of the deployment group to which the deployment target is registered. - /// Deployment target to register. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentTargetAsync( - string project, - int deploymentGroupId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Register a deployment target to a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID - /// ID of the deployment group to which the deployment target is registered. - /// Deployment target to register. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete a deployment target in a deployment group. This deletes the agent from associated deployment pool too. - /// - /// Project ID or project name - /// ID of the deployment group in which deployment target is deleted. - /// ID of the deployment target to delete. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteDeploymentTargetAsync( - string project, - int deploymentGroupId, - int targetId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete a deployment target in a deployment group. This deletes the agent from associated deployment pool too. - /// - /// Project ID - /// ID of the deployment group in which deployment target is deleted. - /// ID of the deployment target to delete. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - int targetId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get a deployment target by its ID in a deployment group - /// - /// Project ID or project name - /// ID of the deployment group to which deployment target belongs. - /// ID of the deployment target to return. - /// Include these additional details in the returned objects. - /// - /// The cancellation token to cancel operation. - public virtual Task GetDeploymentTargetAsync( - string project, - int deploymentGroupId, - int targetId, - DeploymentTargetExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - - List> queryParams = new List>(); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a deployment target by its ID in a deployment group - /// - /// Project ID - /// ID of the deployment group to which deployment target belongs. - /// ID of the deployment target to return. - /// Include these additional details in the returned objects. - /// - /// The cancellation token to cancel operation. - public virtual Task GetDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - int targetId, - DeploymentTargetExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - - List> queryParams = new List>(); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment targets in a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group. - /// Get only the deployment targets that contain all these comma separted list of tags. - /// Name pattern of the deployment targets to return. - /// When set to true, treats **name** as pattern. Else treats it as absolute match. Default is **false**. - /// Include these additional details in the returned objects. - /// Get only deployment targets that have this status. - /// Get only deployment targets that have this last job result. - /// Get deployment targets with names greater than this continuationToken lexicographically. - /// Maximum number of deployment targets to return. Default is **1000**. - /// Get only deployment targets that are enabled or disabled. Default is 'null' which returns all the targets. - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentTargetsAsync( - string project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - bool? partialNameMatch = null, - DeploymentTargetExpands? expand = null, - TaskAgentStatusFilter? agentStatus = null, - TaskAgentJobResultFilter? agentJobResult = null, - string continuationToken = null, - int? top = null, - bool? enabled = null, - IEnumerable propertyFilters = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (agentStatus != null) - { - queryParams.Add("agentStatus", agentStatus.Value.ToString()); - } - if (agentJobResult != null) - { - queryParams.Add("agentJobResult", agentJobResult.Value.ToString()); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (enabled != null) - { - queryParams.Add("enabled", enabled.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of deployment targets in a deployment group. - /// - /// Project ID - /// ID of the deployment group. - /// Get only the deployment targets that contain all these comma separted list of tags. - /// Name pattern of the deployment targets to return. - /// When set to true, treats **name** as pattern. Else treats it as absolute match. Default is **false**. - /// Include these additional details in the returned objects. - /// Get only deployment targets that have this status. - /// Get only deployment targets that have this last job result. - /// Get deployment targets with names greater than this continuationToken lexicographically. - /// Maximum number of deployment targets to return. Default is **1000**. - /// Get only deployment targets that are enabled or disabled. Default is 'null' which returns all the targets. - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentTargetsAsync( - Guid project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - bool? partialNameMatch = null, - DeploymentTargetExpands? expand = null, - TaskAgentStatusFilter? agentStatus = null, - TaskAgentJobResultFilter? agentJobResult = null, - string continuationToken = null, - int? top = null, - bool? enabled = null, - IEnumerable propertyFilters = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (agentStatus != null) - { - queryParams.Add("agentStatus", agentStatus.Value.ToString()); - } - if (agentJobResult != null) - { - queryParams.Add("agentJobResult", agentJobResult.Value.ToString()); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (enabled != null) - { - queryParams.Add("enabled", enabled.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Replace a deployment target in a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID or project name - /// ID of the deployment group in which deployment target is replaced. - /// ID of the deployment target to replace. - /// New deployment target. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task ReplaceDeploymentTargetAsync( - string project, - int deploymentGroupId, - int targetId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Replace a deployment target in a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID - /// ID of the deployment group in which deployment target is replaced. - /// ID of the deployment target to replace. - /// New deployment target. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task ReplaceDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - int targetId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a deployment target and its agent properties in a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID or project name - /// ID of the deployment group in which deployment target is updated. - /// ID of the deployment target to update. - /// Deployment target to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentTargetAsync( - string project, - int deploymentGroupId, - int targetId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a deployment target and its agent properties in a deployment group. Generally this is called by agent configuration tool. - /// - /// Project ID - /// ID of the deployment group in which deployment target is updated. - /// ID of the deployment target to update. - /// Deployment target to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateDeploymentTargetAsync( - Guid project, - int deploymentGroupId, - int targetId, - DeploymentMachine machine, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId, targetId = targetId }; - HttpContent content = new ObjectContent(machine, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update tags of a list of deployment targets in a deployment group. - /// - /// Project ID or project name - /// ID of the deployment group in which deployment targets are updated. - /// Deployment targets with tags to udpdate. - /// - /// The cancellation token to cancel operation. - public virtual Task> UpdateDeploymentTargetsAsync( - string project, - int deploymentGroupId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update tags of a list of deployment targets in a deployment group. - /// - /// Project ID - /// ID of the deployment group in which deployment targets are updated. - /// Deployment targets with tags to udpdate. - /// - /// The cancellation token to cancel operation. - public virtual Task> UpdateDeploymentTargetsAsync( - Guid project, - int deploymentGroupId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a task group. - /// - /// Project ID or project name - /// Task group object to create. - /// - /// The cancellation token to cancel operation. - public virtual Task AddTaskGroupAsync( - string project, - TaskGroupCreateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Create a task group. - /// - /// Project ID - /// Task group object to create. - /// - /// The cancellation token to cancel operation. - public virtual Task AddTaskGroupAsync( - Guid project, - TaskGroupCreateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete a task group. - /// - /// Project ID or project name - /// Id of the task group to be deleted. - /// Comments to delete. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteTaskGroupAsync( - string project, - Guid taskGroupId, - string comment = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (comment != null) - { - queryParams.Add("comment", comment); - } - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete a task group. - /// - /// Project ID - /// Id of the task group to be deleted. - /// Comments to delete. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteTaskGroupAsync( - Guid project, - Guid taskGroupId, - string comment = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (comment != null) - { - queryParams.Add("comment", comment); - } - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get task group. - /// - /// Project ID or project name - /// Id of the task group. - /// version specification of the task group. examples: 1, 1.0. - /// The properties that should be expanded. example $expand=Tasks will expand nested task groups. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetTaskGroupAsync( - string project, - Guid taskGroupId, - string versionSpec, - TaskGroupExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - queryParams.Add("versionSpec", versionSpec); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get task group. - /// - /// Project ID - /// Id of the task group. - /// version specification of the task group. examples: 1, 1.0. - /// The properties that should be expanded. example $expand=Tasks will expand nested task groups. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetTaskGroupAsync( - Guid project, - Guid taskGroupId, - string versionSpec, - TaskGroupExpands? expand = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - queryParams.Add("versionSpec", versionSpec); - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task GetTaskGroupRevisionAsync( - string project, - Guid taskGroupId, - int revision, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - queryParams.Add("revision", revision.ToString(CultureInfo.InvariantCulture)); - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - queryParameters: queryParams, - mediaType: "text/plain", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task GetTaskGroupRevisionAsync( - Guid project, - Guid taskGroupId, - int revision, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - queryParams.Add("revision", revision.ToString(CultureInfo.InvariantCulture)); - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - queryParameters: queryParams, - mediaType: "text/plain", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] List task groups. - /// - /// Project ID or project name - /// Id of the task group. - /// 'true' to recursively expand task groups. Default is 'false'. - /// Guid of the taskId to filter. - /// 'true'to include deleted task groups. Default is 'false'. - /// Number of task groups to get. - /// Gets the task groups after the continuation token provided. - /// Gets the results in the defined order. Default is 'CreatedOnDescending'. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - string project, - Guid? taskGroupId = null, - bool? expanded = null, - Guid? taskIdFilter = null, - bool? deleted = null, - int? top = null, - DateTime? continuationToken = null, - TaskGroupQueryOrder? queryOrder = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - if (taskIdFilter != null) - { - queryParams.Add("taskIdFilter", taskIdFilter.Value.ToString()); - } - if (deleted != null) - { - queryParams.Add("deleted", deleted.Value.ToString()); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (continuationToken != null) - { - AddDateTimeToQueryParams(queryParams, "continuationToken", continuationToken.Value); - } - if (queryOrder != null) - { - queryParams.Add("queryOrder", queryOrder.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] List task groups. - /// - /// Project ID - /// Id of the task group. - /// 'true' to recursively expand task groups. Default is 'false'. - /// Guid of the taskId to filter. - /// 'true'to include deleted task groups. Default is 'false'. - /// Number of task groups to get. - /// Gets the task groups after the continuation token provided. - /// Gets the results in the defined order. Default is 'CreatedOnDescending'. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - Guid project, - Guid? taskGroupId = null, - bool? expanded = null, - Guid? taskIdFilter = null, - bool? deleted = null, - int? top = null, - DateTime? continuationToken = null, - TaskGroupQueryOrder? queryOrder = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - if (taskIdFilter != null) - { - queryParams.Add("taskIdFilter", taskIdFilter.Value.ToString()); - } - if (deleted != null) - { - queryParams.Add("deleted", deleted.Value.ToString()); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (continuationToken != null) - { - AddDateTimeToQueryParams(queryParams, "continuationToken", continuationToken.Value); - } - if (queryOrder != null) - { - queryParams.Add("queryOrder", queryOrder.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> PublishPreviewTaskGroupAsync( - string project, - Guid taskGroupId, - TaskGroup taskGroup, - bool? disablePriorVersions = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (disablePriorVersions != null) - { - queryParams.Add("disablePriorVersions", disablePriorVersions.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> PublishPreviewTaskGroupAsync( - Guid project, - Guid taskGroupId, - TaskGroup taskGroup, - bool? disablePriorVersions = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - if (disablePriorVersions != null) - { - queryParams.Add("disablePriorVersions", disablePriorVersions.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> PublishTaskGroupAsync( - string project, - Guid parentTaskGroupId, - PublishTaskGroupMetadata taskGroupMetadata, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroupMetadata, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - queryParams.Add("parentTaskGroupId", parentTaskGroupId.ToString()); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> PublishTaskGroupAsync( - Guid project, - Guid parentTaskGroupId, - PublishTaskGroupMetadata taskGroupMetadata, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroupMetadata, new VssJsonMediaTypeFormatter(true)); - - List> queryParams = new List>(); - queryParams.Add("parentTaskGroupId", parentTaskGroupId.ToString()); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UndeleteTaskGroupAsync( - string project, - TaskGroup taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UndeleteTaskGroupAsync( - Guid project, - TaskGroup taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a task group. - /// - /// Project ID or project name - /// Task group to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("Use UpdateTaskGroup(Guid taskGroupId, [FromBody] TaskGroupUpdateParameter taskGroup) instead")] - public virtual Task UpdateTaskGroupAsync( - string project, - TaskGroupUpdateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a task group. - /// - /// Project ID - /// Task group to update. - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("Use UpdateTaskGroup(Guid taskGroupId, [FromBody] TaskGroupUpdateParameter taskGroup) instead")] - public virtual Task UpdateTaskGroupAsync( - Guid project, - TaskGroupUpdateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a task group. - /// - /// Project ID or project name - /// Id of the task group to update. - /// Task group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateTaskGroupAsync( - string project, - Guid taskGroupId, - TaskGroupUpdateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a task group. - /// - /// Project ID - /// Id of the task group to update. - /// Task group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateTaskGroupAsync( - Guid project, - Guid taskGroupId, - TaskGroupUpdateParameter taskGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - HttpContent content = new ObjectContent(taskGroup, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteTaskDefinitionAsync( - Guid taskId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("60aac929-f0cd-4bc8-9ce4-6b30e8f1b1bd"); - object routeValues = new { taskId = taskId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task GetTaskContentZipAsync( - Guid taskId, - string versionString, - IEnumerable visibility = null, - bool? scopeLocal = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("60aac929-f0cd-4bc8-9ce4-6b30e8f1b1bd"); - object routeValues = new { taskId = taskId, versionString = versionString }; - - List> queryParams = new List>(); - if (visibility != null) - { - AddIEnumerableAsQueryParams(queryParams, "visibility", visibility); - } - if (scopeLocal != null) - { - queryParams.Add("scopeLocal", scopeLocal.Value.ToString()); - } - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - queryParameters: queryParams, - mediaType: "application/zip", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetTaskDefinitionAsync( - Guid taskId, - string versionString, - IEnumerable visibility = null, - bool? scopeLocal = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("60aac929-f0cd-4bc8-9ce4-6b30e8f1b1bd"); - object routeValues = new { taskId = taskId, versionString = versionString }; - - List> queryParams = new List>(); - if (visibility != null) - { - AddIEnumerableAsQueryParams(queryParams, "visibility", visibility); - } - if (scopeLocal != null) - { - queryParams.Add("scopeLocal", scopeLocal.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetTaskDefinitionsAsync( - Guid? taskId = null, - IEnumerable visibility = null, - bool? scopeLocal = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("60aac929-f0cd-4bc8-9ce4-6b30e8f1b1bd"); - object routeValues = new { taskId = taskId }; - - List> queryParams = new List>(); - if (visibility != null) - { - AddIEnumerableAsQueryParams(queryParams, "visibility", visibility); - } - if (scopeLocal != null) - { - queryParams.Add("scopeLocal", scopeLocal.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] /// @@ -7722,1065 +779,5 @@ namespace GitHub.DistributedTask.WebApi userState: userState, cancellationToken: cancellationToken); } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateAgentUserCapabilitiesAsync( - int poolId, - int agentId, - IDictionary userCapabilities, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("30ba3ada-fedf-4da8-bbb5-dacf2f82e176"); - object routeValues = new { poolId = poolId, agentId = agentId }; - HttpContent content = new ObjectContent>(userCapabilities, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Add a variable group. - /// - /// Project ID or project name - /// Variable group to add. - /// - /// The cancellation token to cancel operation. - public virtual Task AddVariableGroupAsync( - string project, - VariableGroupParameters group, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(group, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Add a variable group. - /// - /// Project ID - /// Variable group to add. - /// - /// The cancellation token to cancel operation. - public virtual Task AddVariableGroupAsync( - Guid project, - VariableGroupParameters group, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - HttpContent content = new ObjectContent(group, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Delete a variable group - /// - /// Project ID or project name - /// Id of the variable group. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteVariableGroupAsync( - string project, - int groupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Delete a variable group - /// - /// Project ID - /// Id of the variable group. - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteVariableGroupAsync( - Guid project, - int groupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] Get a variable group. - /// - /// Project ID or project name - /// Id of the variable group. - /// - /// The cancellation token to cancel operation. - public virtual Task GetVariableGroupAsync( - string project, - int groupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a variable group. - /// - /// Project ID - /// Id of the variable group. - /// - /// The cancellation token to cancel operation. - public virtual Task GetVariableGroupAsync( - Guid project, - int groupId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get variable groups. - /// - /// Project ID or project name - /// Name of variable group. - /// Action filter for the variable group. It specifies the action which can be performed on the variable groups. - /// Number of variable groups to get. - /// Gets the variable groups after the continuation token provided. - /// Gets the results in the defined order. Default is 'IdDescending'. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetVariableGroupsAsync( - string project, - string groupName = null, - VariableGroupActionFilter? actionFilter = null, - int? top = null, - int? continuationToken = null, - VariableGroupQueryOrder? queryOrder = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (groupName != null) - { - queryParams.Add("groupName", groupName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken.Value.ToString(CultureInfo.InvariantCulture)); - } - if (queryOrder != null) - { - queryParams.Add("queryOrder", queryOrder.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get variable groups. - /// - /// Project ID - /// Name of variable group. - /// Action filter for the variable group. It specifies the action which can be performed on the variable groups. - /// Number of variable groups to get. - /// Gets the variable groups after the continuation token provided. - /// Gets the results in the defined order. Default is 'IdDescending'. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetVariableGroupsAsync( - Guid project, - string groupName = null, - VariableGroupActionFilter? actionFilter = null, - int? top = null, - int? continuationToken = null, - VariableGroupQueryOrder? queryOrder = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (groupName != null) - { - queryParams.Add("groupName", groupName); - } - if (actionFilter != null) - { - queryParams.Add("actionFilter", actionFilter.Value.ToString()); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken.Value.ToString(CultureInfo.InvariantCulture)); - } - if (queryOrder != null) - { - queryParams.Add("queryOrder", queryOrder.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get variable groups by ids. - /// - /// Project ID or project name - /// Comma separated list of Ids of variable groups. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetVariableGroupsByIdAsync( - string project, - IEnumerable groupIds, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string groupIdsAsString = null; - if (groupIds != null) - { - groupIdsAsString = string.Join(",", groupIds); - } - queryParams.Add("groupIds", groupIdsAsString); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get variable groups by ids. - /// - /// Project ID - /// Comma separated list of Ids of variable groups. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetVariableGroupsByIdAsync( - Guid project, - IEnumerable groupIds, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - string groupIdsAsString = null; - if (groupIds != null) - { - groupIdsAsString = string.Join(",", groupIds); - } - queryParams.Add("groupIds", groupIdsAsString); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Update a variable group. - /// - /// Project ID or project name - /// Id of the variable group to update. - /// Variable group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateVariableGroupAsync( - string project, - int groupId, - VariableGroupParameters group, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - HttpContent content = new ObjectContent(group, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] Update a variable group. - /// - /// Project ID - /// Id of the variable group to update. - /// Variable group to update. - /// - /// The cancellation token to cancel operation. - public virtual Task UpdateVariableGroupAsync( - Guid project, - int groupId, - VariableGroupParameters group, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PUT"); - Guid locationId = new Guid("f5b09dd5-9d54-45a1-8b5a-1c8287d634cc"); - object routeValues = new { project = project, groupId = groupId }; - HttpContent content = new ObjectContent(group, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> QuerySharedProjectsForVariableGroupAsync( - int groupId, - string project, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("74455598-def7-499a-b7a3-a41d1c8225f8"); - object routeValues = new { groupId = groupId }; - - List> queryParams = new List>(); - queryParams.Add("project", project); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task ShareVariableGroupWithProjectAsync( - int groupId, - string fromProject, - string withProject, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("74455598-def7-499a-b7a3-a41d1c8225f8"); - object routeValues = new { groupId = groupId }; - - List> queryParams = new List>(); - queryParams.Add("fromProject", fromProject); - queryParams.Add("withProject", withProject); - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddVirtualMachineGroupAsync( - string project, - int environmentId, - VirtualMachineGroupCreateParameters createParameters, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(createParameters, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AddVirtualMachineGroupAsync( - Guid project, - int environmentId, - VirtualMachineGroupCreateParameters createParameters, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(createParameters, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteVirtualMachineGroupAsync( - string project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual async Task DeleteVirtualMachineGroupAsync( - Guid project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetVirtualMachineGroupAsync( - string project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetVirtualMachineGroupAsync( - Guid project, - int environmentId, - int resourceId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateVirtualMachineGroupAsync( - string project, - int environmentId, - VirtualMachineGroup resource, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(resource, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task UpdateVirtualMachineGroupAsync( - Guid project, - int environmentId, - VirtualMachineGroup resource, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("9e597901-4af7-4cc3-8d92-47d54db8ebfb"); - object routeValues = new { project = project, environmentId = environmentId }; - HttpContent content = new ObjectContent(resource, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetVirtualMachinesAsync( - string project, - int environmentId, - int resourceId, - string continuationToken = null, - string name = null, - bool? partialNameMatch = null, - IEnumerable tags = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("48700676-2ba5-4282-8ec8-083280d169c7"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - List> queryParams = new List>(); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetVirtualMachinesAsync( - Guid project, - int environmentId, - int resourceId, - string continuationToken = null, - string name = null, - bool? partialNameMatch = null, - IEnumerable tags = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("48700676-2ba5-4282-8ec8-083280d169c7"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - - List> queryParams = new List>(); - if (continuationToken != null) - { - queryParams.Add("continuationToken", continuationToken); - } - if (name != null) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateVirtualMachinesAsync( - string project, - int environmentId, - int resourceId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("48700676-2ba5-4282-8ec8-083280d169c7"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> UpdateVirtualMachinesAsync( - Guid project, - int environmentId, - int resourceId, - IEnumerable machines, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("PATCH"); - Guid locationId = new Guid("48700676-2ba5-4282-8ec8-083280d169c7"); - object routeValues = new { project = project, environmentId = environmentId, resourceId = resourceId }; - HttpContent content = new ObjectContent>(machines, new VssJsonMediaTypeFormatter(true)); - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task AcquireAccessTokenAsync( - AadOauthTokenRequest authenticationRequest, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("9c63205e-3a0f-42a0-ad88-095200f13607"); - HttpContent content = new ObjectContent(authenticationRequest, new VssJsonMediaTypeFormatter(true)); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken, - content: content); - } - - /// - /// [Preview API] - /// - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("ServiceEndpoint APIs under distributedtask area is deprecated. Use the APIs under serviceendpoint area instead.")] - public virtual Task CreateAadOAuthRequestAsync( - string tenantId, - string redirectUri, - AadLoginPromptOption? promptOption = null, - string completeCallbackPayload = null, - bool? completeCallbackByAuthCode = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("POST"); - Guid locationId = new Guid("9c63205e-3a0f-42a0-ad88-095200f13607"); - - List> queryParams = new List>(); - queryParams.Add("tenantId", tenantId); - queryParams.Add("redirectUri", redirectUri); - if (promptOption != null) - { - queryParams.Add("promptOption", promptOption.Value.ToString()); - } - if (completeCallbackPayload != null) - { - queryParams.Add("completeCallbackPayload", completeCallbackPayload); - } - if (completeCallbackByAuthCode != null) - { - queryParams.Add("completeCallbackByAuthCode", completeCallbackByAuthCode.Value.ToString()); - } - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetVstsAadTenantIdAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("9c63205e-3a0f-42a0-ad88-095200f13607"); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// - /// The cancellation token to cancel operation. - public virtual Task GetYamlSchemaAsync( - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("1f9990b9-1dba-441f-9c2e-6485888c42b6"); - - return SendAsync( - httpMethod, - locationId, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } } } diff --git a/src/Sdk/DTGenerated/Generated/TaskHttpClientBase.cs b/src/Sdk/DTGenerated/Generated/TaskHttpClientBase.cs index 799566eab..867b4f927 100644 --- a/src/Sdk/DTGenerated/Generated/TaskHttpClientBase.cs +++ b/src/Sdk/DTGenerated/Generated/TaskHttpClientBase.cs @@ -59,36 +59,6 @@ namespace GitHub.DistributedTask.WebApi { } - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetPlanAttachmentsAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - string type, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("eb55e5d6-2f30-4295-b5ed-38da50b1fc52"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, type = type }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] /// @@ -130,126 +100,6 @@ namespace GitHub.DistributedTask.WebApi content: content); } - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task GetAttachmentAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - Guid timelineId, - Guid recordId, - string type, - string name, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("7898f959-9cdf-4096-b29e-7f293031629e"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, timelineId = timelineId, recordId = recordId, type = type, name = name }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual async Task GetAttachmentContentAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - Guid timelineId, - Guid recordId, - string type, - string name, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("7898f959-9cdf-4096-b29e-7f293031629e"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, timelineId = timelineId, recordId = recordId, type = type, name = name }; - HttpResponseMessage response; - using (HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("5.1-preview.1"), - mediaType: "application/octet-stream", - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - } - response.EnsureSuccessStatusCode(); - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - Stream responseStream = await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - return new GZipStream(responseStream, CompressionMode.Decompress); - } - else - { - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetAttachmentsAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - Guid timelineId, - Guid recordId, - string type, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("7898f959-9cdf-4096-b29e-7f293031629e"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, timelineId = timelineId, recordId = recordId, type = type }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] /// @@ -290,35 +140,6 @@ namespace GitHub.DistributedTask.WebApi } } - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetJobInstanceAsync( - Guid scopeIdentifier, - string hubName, - string orchestrationId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("0a1efd25-abda-43bd-9629-6c7bdd2e0d60"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, orchestrationId = orchestrationId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] /// @@ -386,245 +207,6 @@ namespace GitHub.DistributedTask.WebApi content: content); } - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetLogAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - int logId, - long? startLine = null, - long? endLine = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("46f5667d-263a-4684-91b1-dff7fdcf64e2"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, logId = logId }; - - List> queryParams = new List>(); - if (startLine != null) - { - queryParams.Add("startLine", startLine.Value.ToString(CultureInfo.InvariantCulture)); - } - if (endLine != null) - { - queryParams.Add("endLine", endLine.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetLogsAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("46f5667d-263a-4684-91b1-dff7fdcf64e2"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetPlanGroupsQueueMetricsAsync( - Guid scopeIdentifier, - string hubName, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("038fd4d5-cda7-44ca-92c0-935843fee1a7"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task> GetQueuedPlanGroupsAsync( - Guid scopeIdentifier, - string hubName, - PlanGroupStatus? statusFilter = null, - int? count = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("0dd73091-3e36-4f43-b443-1b76dd426d84"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName }; - - List> queryParams = new List>(); - if (statusFilter != null) - { - queryParams.Add("statusFilter", statusFilter.Value.ToString()); - } - if (count != null) - { - queryParams.Add("count", count.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetQueuedPlanGroupAsync( - Guid scopeIdentifier, - string hubName, - string planGroup, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("65fd0708-bc1e-447b-a731-0587c5464e5b"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planGroup = planGroup }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual Task GetPlanAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("5cecd946-d704-471e-a45f-3b4064fcfaba"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId }; - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetRecordsAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - Guid timelineId, - int? changeId = null, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("8893bc5b-35b2-4be7-83cb-99e683551db4"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, timelineId = timelineId }; - - List> queryParams = new List>(); - if (changeId != null) - { - queryParams.Add("changeId", changeId.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - /// /// [Preview API] /// @@ -691,39 +273,6 @@ namespace GitHub.DistributedTask.WebApi content: content); } - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteTimelineAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - Guid timelineId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("83597576-cc2c-453c-bea6-2882ae6a1653"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId, timelineId = timelineId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - /// /// [Preview API] /// @@ -768,33 +317,5 @@ namespace GitHub.DistributedTask.WebApi userState: userState, cancellationToken: cancellationToken); } - - /// - /// [Preview API] - /// - /// The project GUID to scope the request - /// The name of the server hub: "build" for the Build server or "rm" for the Release Management server - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTimelinesAsync( - Guid scopeIdentifier, - string hubName, - Guid planId, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("83597576-cc2c-453c-bea6-2882ae6a1653"); - object routeValues = new { scopeIdentifier = scopeIdentifier, hubName = hubName, planId = planId }; - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - userState: userState, - cancellationToken: cancellationToken); - } } } diff --git a/src/Sdk/DTLogging/Logging/ValueEncoders.cs b/src/Sdk/DTLogging/Logging/ValueEncoders.cs index 52aed6975..774787991 100644 --- a/src/Sdk/DTLogging/Logging/ValueEncoders.cs +++ b/src/Sdk/DTLogging/Logging/ValueEncoders.cs @@ -39,7 +39,7 @@ namespace GitHub.DistributedTask.Logging public static String ExpressionStringEscape(String value) { - return Expressions.ExpressionUtil.StringEscape(value); + return Expressions2.Sdk.ExpressionUtility.StringEscape(value); } public static String JsonStringEscape(String value) diff --git a/src/Sdk/DTPipelines/Pipelines/AgentJobRequestMessageUtil.cs b/src/Sdk/DTPipelines/Pipelines/AgentJobRequestMessageUtil.cs deleted file mode 100644 index a6d7fe489..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentJobRequestMessageUtil.cs +++ /dev/null @@ -1,769 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using System.Text.RegularExpressions; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class AgentJobRequestMessageUtil - { - // Legacy JobRequestMessage -> Pipeline JobRequestMessage - // Used by the agent when the latest version agent connect to old version TFS - // Used by the server when common method only take the new Message contact, like, telemetry logging - public static AgentJobRequestMessage Convert(WebApi.AgentJobRequestMessage message) - { - // construct steps - List jobSteps = new List(); - foreach (var task in message.Tasks) - { - TaskStep taskStep = new TaskStep(task); - jobSteps.Add(taskStep); - } - - Dictionary variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - HashSet maskHints = new HashSet(); - JobResources jobResources = new JobResources(); - WorkspaceOptions workspace = new WorkspaceOptions(); - message.Environment.Extract(variables, maskHints, jobResources); - - // convert repository endpoint into checkout task for Build - if (string.Equals(message.Plan.PlanType, "Build", StringComparison.OrdinalIgnoreCase)) - { - // repositoryId was added sometime after TFS2015, so we need to fall back to find endpoint using endpoint type. - var legacyRepoEndpoint = jobResources.Endpoints.FirstOrDefault(x => x.Data.ContainsKey("repositoryId")); - if (legacyRepoEndpoint == null) - { - legacyRepoEndpoint = jobResources.Endpoints.FirstOrDefault(x => x.Type == LegacyRepositoryTypes.Bitbucket || x.Type == LegacyRepositoryTypes.Git || x.Type == LegacyRepositoryTypes.TfsGit || x.Type == LegacyRepositoryTypes.GitHub || x.Type == LegacyRepositoryTypes.GitHubEnterprise || x.Type == LegacyRepositoryTypes.TfsVersionControl); - } - - // build retention job will not have a repo endpoint. - if (legacyRepoEndpoint != null) - { - // construct checkout task - var checkoutStep = new TaskStep(); - checkoutStep.Id = Guid.NewGuid(); - checkoutStep.DisplayName = PipelineConstants.CheckoutTask.FriendlyName; - checkoutStep.Name = "__system_checkout"; - checkoutStep.Reference = new TaskStepDefinitionReference() - { - Id = PipelineConstants.CheckoutTask.Id, - Name = PipelineConstants.CheckoutTask.Name, - Version = PipelineConstants.CheckoutTask.Version, - }; - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Repository] = "__legacy_repo_endpoint"; - - // construct self repository resource - var defaultRepo = new RepositoryResource(); - defaultRepo.Alias = "__legacy_repo_endpoint"; - defaultRepo.Properties.Set(RepositoryPropertyNames.Name, legacyRepoEndpoint.Name); - legacyRepoEndpoint.Data.TryGetValue("repositoryId", out string repositoryId); - if (!string.IsNullOrEmpty(repositoryId)) - { - defaultRepo.Id = repositoryId; - } - else - { - defaultRepo.Id = "__legacy_repo_endpoint"; - } - - defaultRepo.Endpoint = new ServiceEndpointReference() - { - Id = Guid.Empty, - Name = legacyRepoEndpoint.Name - }; - defaultRepo.Type = ConvertLegacySourceType(legacyRepoEndpoint.Type); - defaultRepo.Url = legacyRepoEndpoint.Url; - if (variables.TryGetValue("build.sourceVersion", out VariableValue sourceVersion) && !string.IsNullOrEmpty(sourceVersion?.Value)) - { - defaultRepo.Version = sourceVersion.Value; - } - if (variables.TryGetValue("build.sourceBranch", out VariableValue sourceBranch) && !string.IsNullOrEmpty(sourceBranch?.Value)) - { - defaultRepo.Properties.Set(RepositoryPropertyNames.Ref, sourceBranch.Value); - } - - VersionInfo versionInfo = null; - if (variables.TryGetValue("build.sourceVersionAuthor", out VariableValue sourceAuthor) && !string.IsNullOrEmpty(sourceAuthor?.Value)) - { - versionInfo = new VersionInfo(); - versionInfo.Author = sourceAuthor.Value; - } - if (variables.TryGetValue("build.sourceVersionMessage", out VariableValue sourceMessage) && !string.IsNullOrEmpty(sourceMessage?.Value)) - { - if (versionInfo == null) - { - versionInfo = new VersionInfo(); - } - versionInfo.Message = sourceMessage.Value; - } - if (versionInfo != null) - { - defaultRepo.Properties.Set(RepositoryPropertyNames.VersionInfo, versionInfo); - } - - if (defaultRepo.Type == RepositoryTypes.Tfvc) - { - if (variables.TryGetValue("build.sourceTfvcShelveset", out VariableValue shelveset) && !string.IsNullOrEmpty(shelveset?.Value)) - { - defaultRepo.Properties.Set(RepositoryPropertyNames.Shelveset, shelveset.Value); - } - - var legacyTfvcMappingJson = legacyRepoEndpoint.Data["tfvcWorkspaceMapping"]; - var legacyTfvcMapping = JsonUtility.FromString(legacyTfvcMappingJson); - if (legacyTfvcMapping != null) - { - IList tfvcMapping = new List(); - foreach (var mapping in legacyTfvcMapping.Mappings) - { - tfvcMapping.Add(new WorkspaceMapping() { ServerPath = mapping.ServerPath, LocalPath = mapping.LocalPath, Exclude = String.Equals(mapping.MappingType, "cloak", StringComparison.OrdinalIgnoreCase) }); - } - - defaultRepo.Properties.Set>(RepositoryPropertyNames.Mappings, tfvcMapping); - } - } - else if (defaultRepo.Type == RepositoryTypes.Svn) - { - var legacySvnMappingJson = legacyRepoEndpoint.Data["svnWorkspaceMapping"]; - var legacySvnMapping = JsonUtility.FromString(legacySvnMappingJson); - if (legacySvnMapping != null) - { - IList svnMapping = new List(); - foreach (var mapping in legacySvnMapping.Mappings) - { - svnMapping.Add(new WorkspaceMapping() { ServerPath = mapping.ServerPath, LocalPath = mapping.LocalPath, Depth = mapping.Depth, IgnoreExternals = mapping.IgnoreExternals, Revision = mapping.Revision }); - } - - defaultRepo.Properties.Set>(RepositoryPropertyNames.Mappings, svnMapping); - } - } - - legacyRepoEndpoint.Data.TryGetValue("clean", out string cleanString); - if (!string.IsNullOrEmpty(cleanString)) - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Clean] = cleanString; - } - else - { - // Checkout task has clean set tp false as default. - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Clean] = Boolean.FalseString; - } - - if (legacyRepoEndpoint.Data.TryGetValue("checkoutSubmodules", out string checkoutSubmodulesString) && - Boolean.TryParse(checkoutSubmodulesString, out Boolean checkoutSubmodules) && - checkoutSubmodules) - { - if (legacyRepoEndpoint.Data.TryGetValue("checkoutNestedSubmodules", out string nestedSubmodulesString) && - Boolean.TryParse(nestedSubmodulesString, out Boolean nestedSubmodules) && - nestedSubmodules) - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Submodules] = PipelineConstants.CheckoutTaskInputs.SubmodulesOptions.Recursive; - } - else - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Submodules] = PipelineConstants.CheckoutTaskInputs.SubmodulesOptions.True; - } - } - - if (legacyRepoEndpoint.Data.ContainsKey("fetchDepth")) - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.FetchDepth] = legacyRepoEndpoint.Data["fetchDepth"]; - } - - if (legacyRepoEndpoint.Data.ContainsKey("gitLfsSupport")) - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.Lfs] = legacyRepoEndpoint.Data["gitLfsSupport"]; - } - - if (VariableUtility.GetEnableAccessTokenType(variables) == EnableAccessTokenType.Variable) - { - checkoutStep.Inputs[PipelineConstants.CheckoutTaskInputs.PersistCredentials] = Boolean.TrueString; - } - - // construct worksapce option - if (Boolean.TryParse(cleanString, out Boolean clean) && clean) - { - if (legacyRepoEndpoint.Data.TryGetValue("cleanOptions", out string cleanOptionsString) && !string.IsNullOrEmpty(cleanOptionsString)) - { - if (string.Equals(cleanOptionsString, "1", StringComparison.OrdinalIgnoreCase)) //RepositoryCleanOptions.SourceAndOutputDir - { - workspace.Clean = PipelineConstants.WorkspaceCleanOptions.Outputs; - } - else if (string.Equals(cleanOptionsString, "2", StringComparison.OrdinalIgnoreCase)) //RepositoryCleanOptions.SourceDir - { - workspace.Clean = PipelineConstants.WorkspaceCleanOptions.Resources; - } - else if (string.Equals(cleanOptionsString, "3", StringComparison.OrdinalIgnoreCase)) //RepositoryCleanOptions.AllBuildDir - { - workspace.Clean = PipelineConstants.WorkspaceCleanOptions.All; - } - } - } - - // add checkout task when build.syncsources and skipSyncSource not set - variables.TryGetValue("build.syncSources", out VariableValue syncSourcesVariable); - legacyRepoEndpoint.Data.TryGetValue("skipSyncSource", out string skipSyncSource); - if (!string.IsNullOrEmpty(syncSourcesVariable?.Value) && Boolean.TryParse(syncSourcesVariable?.Value, out bool syncSource) && !syncSource) - { - checkoutStep.Condition = bool.FalseString; - } - else if (Boolean.TryParse(skipSyncSource, out bool skipSource) && skipSource) - { - checkoutStep.Condition = bool.FalseString; - } - - jobSteps.Insert(0, checkoutStep); - - // always add self repository to job resource - jobResources.Repositories.Add(defaultRepo); - } - } - - AgentJobRequestMessage agentRequestMessage = new AgentJobRequestMessage(message.Plan, message.Timeline, message.JobId, message.JobName, message.JobRefName, null, null, null, variables, maskHints.ToList(), jobResources, null, workspace, jobSteps, null) - { - RequestId = message.RequestId - }; - - return agentRequestMessage; - } - - // Pipeline JobRequestMessage -> Legacy JobRequestMessage - // Used by the server when the connected agent is old version and doesn't support new contract yet. - public static WebApi.AgentJobRequestMessage Convert(AgentJobRequestMessage message) - { - // Old agent can't handle container(s) - if (message.JobContainer != null) - { - throw new NotSupportedException("Job containers are not supported"); - } - if (message.JobServiceContainers != null) - { - throw new NotSupportedException("Job service containers are not supported"); - } - - // Old agent can't handle more than 1 repository - if (message.Resources.Repositories.Count > 1) - { - throw new NotSupportedException(string.Join(", ", message.Resources.Repositories.Select(x => x.Alias))); - } - - // Old agent can't handle more than 1 checkout task - if (message.Steps.Where(x => x.IsCheckoutTask()).Count() > 1) - { - throw new NotSupportedException(PipelineConstants.CheckoutTask.Id.ToString("D")); - } - - // construct tasks - List tasks = new List(); - foreach (var step in message.Steps) - { - // Pipeline builder should add min agent demand when steps contains group - if (step.Type != StepType.Task) - { - throw new NotSupportedException(step.Type.ToString()); - } - - // don't add checkout task, we need to convert the checkout task into endpoint - if (!step.IsCheckoutTask()) - { - TaskInstance task = (step as TaskStep).ToLegacyTaskInstance(); - tasks.Add(task); - } - } - - if (message.Resources != null) - { - foreach (var endpoint in message.Resources.Endpoints) - { - // Legacy message require all endpoint's name equals to endpoint's id - // Guid.Empty is for repository endpoints - if (!String.Equals(endpoint.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase) && - endpoint.Id != Guid.Empty) - { - endpoint.Name = endpoint.Id.ToString("D"); - } - } - - // Make sure we propagate download ticket into the mask hints - foreach (var secureFile in message.Resources.SecureFiles) - { - if (!String.IsNullOrEmpty(secureFile.Ticket)) - { - message.MaskHints.Add(new MaskHint() { Type = MaskType.Regex, Value = Regex.Escape(secureFile.Ticket) }); - } - } - } - - if (String.Equals(message.Plan.PlanType, "Build", StringComparison.OrdinalIgnoreCase)) - { - // create repository endpoint base on checkout task + repository resource + repository endpoint - // repoResource might be null when environment verion is still on 1 - var repoResource = message.Resources?.Repositories.SingleOrDefault(); - if (repoResource != null) - { - var legacyRepoEndpoint = new ServiceEndpoint(); - legacyRepoEndpoint.Name = repoResource.Properties.Get(RepositoryPropertyNames.Name); - legacyRepoEndpoint.Type = ConvertToLegacySourceType(repoResource.Type); - legacyRepoEndpoint.Url = repoResource.Url; - if (repoResource.Endpoint != null) - { - var referencedEndpoint = message.Resources.Endpoints.First(x => (x.Id == repoResource.Endpoint.Id && x.Id != Guid.Empty) || (String.Equals(x.Name, repoResource.Endpoint.Name?.Literal, StringComparison.OrdinalIgnoreCase) && x.Id == Guid.Empty && repoResource.Endpoint.Id == Guid.Empty)); - var endpointAuthCopy = referencedEndpoint.Authorization?.Clone(); - if (endpointAuthCopy != null) - { - if (endpointAuthCopy.Scheme == EndpointAuthorizationSchemes.Token) //InstallationToken (Tabby) or ApiToken (GithubEnterprise) - { - if (referencedEndpoint.Authorization.Parameters.TryGetValue(EndpointAuthorizationParameters.AccessToken, out string accessToken)) //Tabby - { - legacyRepoEndpoint.Authorization = new EndpointAuthorization() - { - Scheme = EndpointAuthorizationSchemes.UsernamePassword, - Parameters = - { - { EndpointAuthorizationParameters.Username, "x-access-token" }, - { EndpointAuthorizationParameters.Password, accessToken } - } - }; - } - else if (referencedEndpoint.Authorization.Parameters.TryGetValue(EndpointAuthorizationParameters.ApiToken, out string apiToken)) //GithubEnterprise - { - legacyRepoEndpoint.Authorization = new EndpointAuthorization() - { - Scheme = EndpointAuthorizationSchemes.UsernamePassword, - Parameters = - { - { EndpointAuthorizationParameters.Username, apiToken }, - { EndpointAuthorizationParameters.Password, "x-oauth-basic" } - } - }; - } - } - else if (endpointAuthCopy.Scheme == EndpointAuthorizationSchemes.PersonalAccessToken) // Github - { - if (referencedEndpoint.Authorization.Parameters.TryGetValue(EndpointAuthorizationParameters.AccessToken, out string accessToken)) //Tabby - { - legacyRepoEndpoint.Authorization = new EndpointAuthorization() - { - Scheme = EndpointAuthorizationSchemes.UsernamePassword, - Parameters = - { - { EndpointAuthorizationParameters.Username, "pat" }, - { EndpointAuthorizationParameters.Password, accessToken } - } - }; - } - } - else - { - legacyRepoEndpoint.Authorization = endpointAuthCopy; - } - } - - // there are 2 properties we put into the legacy repo endpoint directly from connect endpoint - if (referencedEndpoint.Data.TryGetValue("acceptUntrustedCerts", out String acceptUntrustedCerts)) - { - legacyRepoEndpoint.Data["acceptUntrustedCerts"] = acceptUntrustedCerts; - } - if (referencedEndpoint.Data.TryGetValue("realmName", out String realmName)) - { - legacyRepoEndpoint.Data["realmName"] = realmName; - } - } - legacyRepoEndpoint.Data["repositoryId"] = repoResource.Id; - - // default values in the old message format - legacyRepoEndpoint.Data["clean"] = Boolean.FalseString; - legacyRepoEndpoint.Data["checkoutSubmodules"] = Boolean.FalseString; - legacyRepoEndpoint.Data["checkoutNestedSubmodules"] = Boolean.FalseString; - legacyRepoEndpoint.Data["fetchDepth"] = "0"; - legacyRepoEndpoint.Data["gitLfsSupport"] = Boolean.FalseString; - legacyRepoEndpoint.Data["skipSyncSource"] = Boolean.FalseString; - legacyRepoEndpoint.Data["cleanOptions"] = "0"; - legacyRepoEndpoint.Data["rootFolder"] = null; // old tfvc repo endpoint has this set to $/foo, but it doesn't seems to be used at all. - - if (repoResource.Type == RepositoryTypes.Tfvc) - { - var tfvcMapping = repoResource.Properties.Get>(RepositoryPropertyNames.Mappings); - if (tfvcMapping != null) - { - LegacyBuildWorkspace legacyMapping = new LegacyBuildWorkspace(); - foreach (var mapping in tfvcMapping) - { - legacyMapping.Mappings.Add(new LegacyMappingDetails() { ServerPath = mapping.ServerPath, LocalPath = mapping.LocalPath, MappingType = mapping.Exclude ? "cloak" : "map" }); - } - - legacyRepoEndpoint.Data["tfvcWorkspaceMapping"] = JsonUtility.ToString(legacyMapping); - } - } - else if (repoResource.Type == RepositoryTypes.Svn) - { - var svnMapping = repoResource.Properties.Get>(RepositoryPropertyNames.Mappings); - if (svnMapping != null) - { - LegacySvnWorkspace legacyMapping = new LegacySvnWorkspace(); - foreach (var mapping in svnMapping) - { - legacyMapping.Mappings.Add(new LegacySvnMappingDetails() { ServerPath = mapping.ServerPath, LocalPath = mapping.LocalPath, Depth = mapping.Depth, IgnoreExternals = mapping.IgnoreExternals, Revision = mapping.Revision }); - } - - legacyRepoEndpoint.Data["svnWorkspaceMapping"] = JsonUtility.ToString(legacyMapping); - } - } - else if (repoResource.Type == RepositoryTypes.Git) - { - if (message.Variables.TryGetValue(WellKnownDistributedTaskVariables.ServerType, out VariableValue serverType) && String.Equals(serverType?.Value, "Hosted", StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["onpremtfsgit"] = Boolean.FalseString; - } - else - { - legacyRepoEndpoint.Data["onpremtfsgit"] = Boolean.TrueString; - } - } - - if (!message.Variables.ContainsKey("build.repository.id") || String.IsNullOrEmpty(message.Variables["build.repository.id"]?.Value)) - { - message.Variables["build.repository.id"] = repoResource.Id; - } - if (!message.Variables.ContainsKey("build.repository.name") || String.IsNullOrEmpty(message.Variables["build.repository.name"]?.Value)) - { - message.Variables["build.repository.name"] = repoResource.Properties.Get(RepositoryPropertyNames.Name); - } - if (!message.Variables.ContainsKey("build.repository.uri") || String.IsNullOrEmpty(message.Variables["build.repository.uri"]?.Value)) - { - message.Variables["build.repository.uri"] = repoResource.Url.AbsoluteUri; - } - - var versionInfo = repoResource.Properties.Get(RepositoryPropertyNames.VersionInfo); - if (!message.Variables.ContainsKey("build.sourceVersionAuthor") || String.IsNullOrEmpty(message.Variables["build.sourceVersionAuthor"]?.Value)) - { - message.Variables["build.sourceVersionAuthor"] = versionInfo?.Author; - } - if (!message.Variables.ContainsKey("build.sourceVersionMessage") || String.IsNullOrEmpty(message.Variables["build.sourceVersionMessage"]?.Value)) - { - message.Variables["build.sourceVersionMessage"] = versionInfo?.Message; - } - if (!message.Variables.ContainsKey("build.sourceVersion") || String.IsNullOrEmpty(message.Variables["build.sourceVersion"]?.Value)) - { - message.Variables["build.sourceVersion"] = repoResource.Version; - } - if (!message.Variables.ContainsKey("build.sourceBranch") || String.IsNullOrEmpty(message.Variables["build.sourceBranch"]?.Value)) - { - message.Variables["build.sourceBranch"] = repoResource.Properties.Get(RepositoryPropertyNames.Ref); - } - if (repoResource.Type == RepositoryTypes.Tfvc) - { - var shelveset = repoResource.Properties.Get(RepositoryPropertyNames.Shelveset); - if (!String.IsNullOrEmpty(shelveset) && (!message.Variables.ContainsKey("build.sourceTfvcShelveset") || String.IsNullOrEmpty(message.Variables["build.sourceTfvcShelveset"]?.Value))) - { - message.Variables["build.sourceTfvcShelveset"] = shelveset; - } - } - - TaskStep checkoutTask = message.Steps.FirstOrDefault(x => x.IsCheckoutTask()) as TaskStep; - if (checkoutTask != null) - { - if (checkoutTask.Inputs.TryGetValue(PipelineConstants.CheckoutTaskInputs.Clean, out string taskInputClean) && !string.IsNullOrEmpty(taskInputClean)) - { - legacyRepoEndpoint.Data["clean"] = taskInputClean; - } - else - { - legacyRepoEndpoint.Data["clean"] = Boolean.FalseString; - } - - if (checkoutTask.Inputs.TryGetValue(PipelineConstants.CheckoutTaskInputs.Submodules, out string taskInputSubmodules) && !string.IsNullOrEmpty(taskInputSubmodules)) - { - legacyRepoEndpoint.Data["checkoutSubmodules"] = Boolean.TrueString; - if (String.Equals(taskInputSubmodules, PipelineConstants.CheckoutTaskInputs.SubmodulesOptions.Recursive, StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["checkoutNestedSubmodules"] = Boolean.TrueString; - } - } - - if (checkoutTask.Inputs.TryGetValue(PipelineConstants.CheckoutTaskInputs.FetchDepth, out string taskInputFetchDepth) && !string.IsNullOrEmpty(taskInputFetchDepth)) - { - legacyRepoEndpoint.Data["fetchDepth"] = taskInputFetchDepth; - } - - if (checkoutTask.Inputs.TryGetValue(PipelineConstants.CheckoutTaskInputs.Lfs, out string taskInputfs) && !string.IsNullOrEmpty(taskInputfs)) - { - legacyRepoEndpoint.Data["gitLfsSupport"] = taskInputfs; - } - - // Skip sync sources - if (String.Equals(checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Repository], PipelineConstants.NoneAlias, StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["skipSyncSource"] = Boolean.TrueString; - } - else if (String.Equals(checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Repository], PipelineConstants.DesignerRepo, StringComparison.OrdinalIgnoreCase) && checkoutTask.Condition == Boolean.FalseString) - { - legacyRepoEndpoint.Data["skipSyncSource"] = Boolean.TrueString; - } - } - - // workspace clean options - legacyRepoEndpoint.Data["cleanOptions"] = "0"; // RepositoryCleanOptions.Source; - if (message.Workspace != null) - { - if (String.Equals(message.Workspace.Clean, PipelineConstants.WorkspaceCleanOptions.Outputs, StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["cleanOptions"] = "1"; // RepositoryCleanOptions.SourceAndOutputDir; - } - else if (String.Equals(message.Workspace.Clean, PipelineConstants.WorkspaceCleanOptions.Resources, StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["cleanOptions"] = "2"; //RepositoryCleanOptions.SourceDir; - } - else if (String.Equals(message.Workspace.Clean, PipelineConstants.WorkspaceCleanOptions.All, StringComparison.OrdinalIgnoreCase)) - { - legacyRepoEndpoint.Data["cleanOptions"] = "3"; // RepositoryCleanOptions.AllBuildDir; - } - } - - // add reposiotry endpoint to environment - message.Resources.Endpoints.Add(legacyRepoEndpoint); - } - } - - JobEnvironment environment = new JobEnvironment(message.Variables, message.MaskHints, message.Resources); - - WebApi.AgentJobRequestMessage legacyAgentRequestMessage = new WebApi.AgentJobRequestMessage(message.Plan, message.Timeline, message.JobId, message.JobDisplayName, message.JobName, environment, tasks) - { - RequestId = message.RequestId - }; - - return legacyAgentRequestMessage; - } - - private static string ConvertLegacySourceType(string legacySourceType) - { - if (String.Equals(legacySourceType, LegacyRepositoryTypes.Bitbucket, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.Bitbucket; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.Git, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.ExternalGit; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.TfsGit, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.Git; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.GitHub, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.GitHub; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.GitHubEnterprise, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.GitHubEnterprise; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.Svn, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.Svn; - } - else if (String.Equals(legacySourceType, LegacyRepositoryTypes.TfsVersionControl, StringComparison.OrdinalIgnoreCase)) - { - return RepositoryTypes.Tfvc; - } - else - { - throw new NotSupportedException(legacySourceType); - } - } - - private static string ConvertToLegacySourceType(string pipelineSourceType) - { - if (String.Equals(pipelineSourceType, RepositoryTypes.Bitbucket, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.Bitbucket; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.ExternalGit, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.Git; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.Git, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.TfsGit; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.GitHub, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.GitHub; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.GitHubEnterprise, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.GitHubEnterprise; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.Svn, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.Svn; - } - else if (String.Equals(pipelineSourceType, RepositoryTypes.Tfvc, StringComparison.OrdinalIgnoreCase)) - { - return LegacyRepositoryTypes.TfsVersionControl; - } - else - { - throw new NotSupportedException(pipelineSourceType); - } - } - - private static class LegacyRepositoryTypes // Copy from Build.Webapi - { - public const String TfsVersionControl = "TfsVersionControl"; - public const String TfsGit = "TfsGit"; - public const String Git = "Git"; - public const String GitHub = "GitHub"; - public const String GitHubEnterprise = "GitHubEnterprise"; - public const String Bitbucket = "Bitbucket"; - public const String Svn = "Svn"; - } - - /// - /// Represents an entry in a workspace mapping. - /// - [DataContract] - private class LegacyMappingDetails - { - /// - /// The server path. - /// - [DataMember(Name = "serverPath")] - public String ServerPath - { - get; - set; - } - - /// - /// The mapping type. - /// - [DataMember(Name = "mappingType")] - public String MappingType - { - get; - set; - } - - /// - /// The local path. - /// - [DataMember(Name = "localPath")] - public String LocalPath - { - get; - set; - } - } - - /// - /// Represents a workspace mapping. - /// - [DataContract] - private class LegacyBuildWorkspace - { - /// - /// The list of workspace mapping entries. - /// - public List Mappings - { - get - { - if (m_mappings == null) - { - m_mappings = new List(); - } - return m_mappings; - } - } - - [DataMember(Name = "mappings")] - private List m_mappings; - } - - /// - /// Represents a Subversion mapping entry. - /// - [DataContract] - private class LegacySvnMappingDetails - { - /// - /// The server path. - /// - [DataMember(Name = "serverPath")] - public String ServerPath - { - get; - set; - } - - /// - /// The local path. - /// - [DataMember(Name = "localPath")] - public String LocalPath - { - get; - set; - } - - /// - /// The revision. - /// - [DataMember(Name = "revision")] - public String Revision - { - get; - set; - } - - /// - /// The depth. - /// - [DataMember(Name = "depth")] - public Int32 Depth - { - get; - set; - } - - /// - /// Indicates whether to ignore externals. - /// - [DataMember(Name = "ignoreExternals")] - public bool IgnoreExternals - { - get; - set; - } - } - - /// - /// Represents a subversion workspace. - /// - [DataContract] - private class LegacySvnWorkspace - { - /// - /// The list of mappings. - /// - public List Mappings - { - get - { - if (m_Mappings == null) - { - m_Mappings = new List(); - } - return m_Mappings; - } - } - - [DataMember(Name = "mappings")] - private List m_Mappings; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentPoolReference.cs b/src/Sdk/DTPipelines/Pipelines/AgentPoolReference.cs deleted file mode 100644 index 9fd06febe..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentPoolReference.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class AgentPoolReference : ResourceReference - { - public AgentPoolReference() - { - } - - private AgentPoolReference(AgentPoolReference referenceToCopy) - : base(referenceToCopy) - { - this.Id = referenceToCopy.Id; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - public AgentPoolReference Clone() - { - return new AgentPoolReference(this); - } - - public override String ToString() - { - return base.ToString() ?? this.Id.ToString(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentPoolStore.cs b/src/Sdk/DTPipelines/Pipelines/AgentPoolStore.cs deleted file mode 100644 index e745c85ad..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentPoolStore.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class AgentPoolStore : IAgentPoolStore - { - public AgentPoolStore( - IList pools, - IAgentPoolResolver resolver = null) - { - this.Resolver = resolver; - Add(pools?.ToArray()); - } - - /// - /// Get the queue resolver configured for this store. - /// - public IAgentPoolResolver Resolver - { - get; - } - - public void Authorize(IList pools) - { - if (pools?.Count > 0) - { - foreach (var pool in pools) - { - var authorizedResource = this.Resolver?.Resolve(pool); - if (authorizedResource != null) - { - Add(authorizedResource); - } - } - } - } - - public IList GetAuthorizedReferences() - { - return m_resourcesById.Values.Select(x => new AgentPoolReference { Id = x.Id }).ToList(); - } - - public TaskAgentPool Get(AgentPoolReference reference) - { - if (reference == null) - { - return null; - } - - var referenceId = reference.Id; - var referenceName = reference.Name?.Literal; - if (reference.Id == 0 && String.IsNullOrEmpty(referenceName)) - { - return null; - } - - TaskAgentPool authorizedResource = null; - if (referenceId != 0) - { - if (m_resourcesById.TryGetValue(referenceId, out authorizedResource)) - { - return authorizedResource; - } - } - else if (!String.IsNullOrEmpty(referenceName)) - { - if (m_resourcesByName.TryGetValue(referenceName, out authorizedResource)) - { - return authorizedResource; - } - } - - // If we have an authorizer then attempt to authorize the reference for use - authorizedResource = this.Resolver?.Resolve(reference); - if (authorizedResource != null) - { - Add(authorizedResource); - } - - return authorizedResource; - } - - private void Add(params TaskAgentPool[] resources) - { - if (resources?.Length > 0) - { - foreach (var resource in resources) - { - // Track by ID - if (m_resourcesById.TryGetValue(resource.Id, out _)) - { - continue; - } - - m_resourcesById.Add(resource.Id, resource); - - // Track by name - if (m_resourcesByName.TryGetValue(resource.Name, out _)) - { - continue; - } - - m_resourcesByName.Add(resource.Name, resource); - } - } - } - - private readonly Dictionary m_resourcesById = new Dictionary(); - private readonly Dictionary m_resourcesByName = new Dictionary(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentPoolTarget.cs b/src/Sdk/DTPipelines/Pipelines/AgentPoolTarget.cs deleted file mode 100644 index 6e1125b4e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentPoolTarget.cs +++ /dev/null @@ -1,169 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class AgentPoolTarget : PhaseTarget - { - public AgentPoolTarget() - : base(PhaseTargetType.Pool) - { - } - - private AgentPoolTarget(AgentPoolTarget targetToClone) - : base(targetToClone) - { - this.Pool = targetToClone.Pool?.Clone(); - - - if (targetToClone.AgentSpecification != null) - { - this.AgentSpecification = new JObject(targetToClone.AgentSpecification); - } - - if (targetToClone.m_agentIds?.Count > 0) - { - this.m_agentIds = targetToClone.m_agentIds; - } - } - - /// - /// Gets or sets the target pool from which agents will be selected. - /// - [DataMember(EmitDefaultValue = false)] - public AgentPoolReference Pool - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public JObject AgentSpecification - { - get; - set; - } - - /// - /// Gets agent Ids filter on which deployment should be done. - /// - public List AgentIds - { - get - { - if (m_agentIds == null) - { - m_agentIds = new List(); - } - return m_agentIds; - } - } - - public override PhaseTarget Clone() - { - return new AgentPoolTarget(this); - } - - public override Boolean IsValid(TaskDefinition task) - { - ArgumentUtility.CheckForNull(task, nameof(task)); - return task.RunsOn.Contains(TaskRunsOnConstants.RunsOnAgent, StringComparer.OrdinalIgnoreCase); - } - - internal override void Validate( - IPipelineContext context, - BuildOptions buildOptions, - ValidationResult result, - IList steps, - ISet taskDemands) - { - // validate pool - Int32 poolId = 0; - String poolName = null; - var pool = this.Pool; - if (pool != null) - { - poolId = pool.Id; - poolName = pool.Name?.GetValue(context)?.Value; - } - - if (poolId == 0 && String.IsNullOrEmpty(poolName) && buildOptions.ValidateResources) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotDefined())); - } - else - { - // we have a valid queue. record the reference - result.AddPoolReference(poolId, poolName); - - // Attempt to resolve the queue using any identifier specified. We will look up by either ID - // or name and the ID is preferred since it is immutable and more specific. - if (buildOptions.ValidateResources) - { - TaskAgentPool taskAgentPool = null; - var resourceStore = context.ResourceStore; - if (resourceStore != null) - { - if (poolId != 0) - { - taskAgentPool = resourceStore.GetPool(poolId); - if (taskAgentPool == null) - { - result.UnauthorizedResources.Pools.Add(new AgentPoolReference { Id = poolId }); - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFound(poolId))); - } - } - else if (!String.IsNullOrEmpty(poolName)) - { - taskAgentPool = resourceStore.GetPool(poolName); - if (taskAgentPool == null) - { - result.UnauthorizedResources.Pools.Add(new AgentPoolReference { Name = poolName }); - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFound(poolName))); - } - } - } - - // Store the resolved values inline to the resolved resource for this validation run - if (taskAgentPool != null) - { - this.Pool.Id = taskAgentPool.Id; - this.Pool.Name = taskAgentPool.Name; - } - } - } - } - - internal override JobExecutionContext CreateJobContext(PhaseExecutionContext context, string jobName, int attempt, bool continueOnError, int timeoutInMinutes, int cancelTimeoutInMinutes, IJobFactory jobFactory) - { - throw new NotSupportedException(nameof(AgentPoolTarget)); - } - - internal override ExpandPhaseResult Expand(PhaseExecutionContext context, bool continueOnError, int timeoutInMinutes, int cancelTimeoutInMinutes, IJobFactory jobFactory, JobExpansionOptions options) - { - throw new NotSupportedException(nameof(AgentPoolTarget)); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_agentIds?.Count == 0) - { - m_agentIds = null; - } - } - - [DataMember(Name = "AgentIds", EmitDefaultValue = false)] - private List m_agentIds; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentQueueReference.cs b/src/Sdk/DTPipelines/Pipelines/AgentQueueReference.cs deleted file mode 100644 index 9e80f0bcd..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentQueueReference.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class AgentQueueReference : ResourceReference - { - public AgentQueueReference() - { - } - - private AgentQueueReference(AgentQueueReference referenceToCopy) - : base(referenceToCopy) - { - this.Id = referenceToCopy.Id; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - public AgentQueueReference Clone() - { - return new AgentQueueReference(this); - } - - public override String ToString() - { - return base.ToString() ?? this.Id.ToString(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentQueueStore.cs b/src/Sdk/DTPipelines/Pipelines/AgentQueueStore.cs deleted file mode 100644 index b6f8582e4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentQueueStore.cs +++ /dev/null @@ -1,161 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class AgentQueueStore : IAgentQueueStore - { - public AgentQueueStore( - IList queues, - IAgentQueueResolver resolver = null) - { - this.Resolver = resolver; - Add(queues?.ToArray()); - } - - /// - /// Get the queue resolver configured for this store. - /// - public IAgentQueueResolver Resolver - { - get; - } - - public void Authorize(IList queues) - { - if (queues?.Count > 0) - { - foreach (var queue in queues) - { - Add(queue); - } - } - } - - public IList GetAuthorizedReferences() - { - return m_resourcesById.Values.Select(x => new AgentQueueReference { Id = x.Id }).ToList(); - } - - public TaskAgentQueue Get(AgentQueueReference reference) - { - if (reference == null) - { - return null; - } - - var referenceId = reference.Id; - var referenceName = reference.Name?.Literal; - if (reference.Id == 0 && String.IsNullOrEmpty(referenceName)) - { - return null; - } - - TaskAgentQueue authorizedResource = null; - if (referenceId != 0) - { - if (m_resourcesById.TryGetValue(referenceId, out authorizedResource)) - { - return authorizedResource; - } - } - else if (!String.IsNullOrEmpty(referenceName)) - { - if (m_resourcesByName.TryGetValue(referenceName, out List matchingResources)) - { - if (matchingResources.Count > 1) - { - throw new AmbiguousResourceSpecificationException(PipelineStrings.AmbiguousServiceEndpointSpecification(referenceId)); - } - - return matchingResources[0]; - } - } - - // If we have an authorizer then attempt to authorize the reference for use - authorizedResource = this.Resolver?.Resolve(reference); - if (authorizedResource != null) - { - Add(authorizedResource); - } - - return authorizedResource; - } - - private void Add(params TaskAgentQueue[] resources) - { - if (resources?.Length > 0) - { - foreach (var resource in resources) - { - // Track by ID - if (m_resourcesById.TryGetValue(resource.Id, out _)) - { - continue; - } - - m_resourcesById.Add(resource.Id, resource); - - // not all references have names - var name = resource.Name; - if (string.IsNullOrWhiteSpace(name)) - { - continue; - } - - // Track by name - if (!m_resourcesByName.TryGetValue(name, out var list)) - { - list = new List(); - m_resourcesByName.Add(name, list); - } - - // Clobber previously added alternate name, with the real hosted queue. - // For example, during the "Hosted macOS High Sierra" transition, until the real queue - // existed, it was treated as an alternate name for the "Hosted macOS" queue. After the - // real "Hosted macOS High Sierra" queue was created, it took priority. - if (list.Count > 0 && list[0].Pool?.IsHosted == true && resource.Pool?.IsHosted == true) - { - list[0] = resource; - } - // Otherwise add the queue - else - { - list.Add(resource); - } - - // Track by alternate name for specific hosted pools. - // For example, "Hosted macOS Preview" and "Hosted macOS" are equivalent. - if (resource.Pool?.IsHosted == true && s_alternateNames.TryGetValue(name, out var alternateNames)) - { - foreach (var alternateName in alternateNames) - { - if (!m_resourcesByName.TryGetValue(alternateName, out list)) - { - list = new List(); - m_resourcesByName.Add(alternateName, list); - } - - if (list.Count == 0 || list[0].Pool?.IsHosted != true) - { - list.Add(resource); - } - } - } - } - } - } - - private static readonly Dictionary s_alternateNames = new Dictionary(StringComparer.OrdinalIgnoreCase) - { - { "Hosted macOS", new[] { "Hosted macOS Preview" } }, - { "Hosted macOS Preview", new[] { "Hosted macOS" } }, - }; - private readonly Dictionary m_resourcesById = new Dictionary(); - private readonly Dictionary> m_resourcesByName = new Dictionary>(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/AgentQueueTarget.cs b/src/Sdk/DTPipelines/Pipelines/AgentQueueTarget.cs deleted file mode 100644 index 938009af4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/AgentQueueTarget.cs +++ /dev/null @@ -1,647 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides options for phase execution on an agent within a queue. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class AgentQueueTarget : PhaseTarget - { - public AgentQueueTarget() - : base(PhaseTargetType.Queue) - { - } - - private AgentQueueTarget(AgentQueueTarget targetToClone) - : base(targetToClone) - { - this.Queue = targetToClone.Queue?.Clone(); - this.Execution = targetToClone.Execution?.Clone(); - - if (targetToClone.AgentSpecification != null) - { - this.AgentSpecification = new JObject(targetToClone.AgentSpecification); - } - - if (targetToClone.SidecarContainers?.Count > 0) - { - m_sidecarContainers = new Dictionary>(targetToClone.SidecarContainers, StringComparer.OrdinalIgnoreCase); - } - } - - /// - /// Gets or sets the target queue from which agents will be selected. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(QueueJsonConverter))] - public AgentQueueReference Queue - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public JObject AgentSpecification - { - get; - set; - } - - /// - /// Gets or sets parallel execution options which control expansion and execution of the phase. - /// - [DataMember(EmitDefaultValue = false)] - public ParallelExecutionOptions Execution - { - get; - set; - } - - /// - /// Gets or sets workspace options which control how agent manage the workspace of the phase. - /// - [DataMember(EmitDefaultValue = false)] - public WorkspaceOptions Workspace - { - get; - set; - } - - /// - /// Gets or sets the container the phase will be run in. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue Container - { - get; - set; - } - - /// - /// Gets the sidecar containers that will run alongside the phase. - /// - public IDictionary> SidecarContainers - { - get - { - if (m_sidecarContainers == null) - { - m_sidecarContainers = new Dictionary>(StringComparer.OrdinalIgnoreCase); - } - return m_sidecarContainers; - } - } - - public override PhaseTarget Clone() - { - return new AgentQueueTarget(this); - } - - public override Boolean IsValid(TaskDefinition task) - { - ArgumentUtility.CheckForNull(task, nameof(task)); - return task.RunsOn.Contains(TaskRunsOnConstants.RunsOnAgent, StringComparer.OrdinalIgnoreCase); - } - - /// - /// Creates a clone of this and attempts to resolve all expressions and macros. - /// - internal AgentQueueTarget Evaluate( - IPipelineContext context, - ValidationResult result) - { - var qname = String.Empty; - try - { - qname = context.ExpandVariables(this.Queue?.Name?.GetValue(context).Value); - } - catch (DistributedTask.Expressions.ExpressionException ee) - { - result.Errors.Add(new PipelineValidationError(ee.Message)); - return null; - } - - var literalTarget = this.Clone() as AgentQueueTarget; - - var spec = this.AgentSpecification; - if (spec != null) - { - spec = context.Evaluate(this.AgentSpecification).Value; - literalTarget.AgentSpecification = spec; - } - - // Note! The "vmImage" token of the agent spec is currently treated specially. - // This is a temporary relationship that allows vmImage agent specs to specify - // the hosted pool to use. - // It would be better to factor out this work into a separate, plug-in validator. - if (String.IsNullOrEmpty(qname) && spec != null) - { - const string VMImage = "vmImage"; // should be: YamlConstants.VMImage, which is inaccessible :( - spec.TryGetValue(VMImage, out var token); - if (token != null && token.Type == JTokenType.String) - { - var rawTokenValue = token.Value(); - var resolvedPoolName = PoolNameForVMImage(rawTokenValue); - if (resolvedPoolName == null) - { - result.Errors.Add(new PipelineValidationError($"Unexpected vmImage '{rawTokenValue}'")); - return null; - } - else - { - spec.Remove(VMImage); - literalTarget.Queue = new AgentQueueReference - { - Name = resolvedPoolName - }; - } - } - } - else - { - literalTarget.Queue.Name = qname; - } - - return literalTarget; - } - - /// - /// returns true for strings structured like expressions or macros. - /// they could techincally be literals though. - /// - internal static Boolean IsProbablyExpressionOrMacro(String s) - { - return ExpressionValue.IsExpression(s) || VariableUtility.IsVariable(s); - } - - /// - /// returns true if this model is composed only of literal values (no expressions) - /// - internal Boolean IsLiteral() - { - var queue = this.Queue; - if (queue != null) - { - var queueName = queue.Name; - if (queueName != null) - { - if (!queueName.IsLiteral || VariableUtility.IsVariable(queueName.Literal)) - { - return false; - } - } - } - - var spec = this.AgentSpecification; - if (spec != null) - { - bool IsLiteral(JObject o) - { - foreach (var pair in o) - { - switch (pair.Value.Type) - { - case JTokenType.String: - if (IsProbablyExpressionOrMacro(pair.Value.Value())) - { - return false; - } - break; - case JTokenType.Object: - if (!IsLiteral(pair.Value.Value())) - { - return false; - } - break; - default: - break; - } - } - - return true; - } - - if (!IsLiteral(spec)) - { - return false; - } - } - - return true; - } - - /// - /// Temporary code to translate vmImage. Pool providers work will move this to a different layer - /// - /// - /// Hosted pool name - internal static String PoolNameForVMImage(String vmImageValue) - { - switch ((vmImageValue ?? String.Empty).ToUpperInvariant()) - { - case "UBUNTU 16.04": - case "UBUNTU-16.04": - case "UBUNTU LATEST": - case "UBUNTU-LATEST": - return "Hosted Ubuntu 1604"; - case "UBUNTU 18.04": - case "UBUNTU-18.04": - return "Hosted Ubuntu 1804"; - case "VISUAL STUDIO 2015 ON WINDOWS SERVER 2012R2": - case "VS2015-WIN2012R2": - return "Hosted"; - case "VISUAL STUDIO 2017 ON WINDOWS SERVER 2016": - case "VS2017-WIN2016": - return "Hosted VS2017"; - case "WINDOWS-2019-VS2019": - case "WINDOWS-2019": - case "WINDOWS LATEST": - case "WINDOWS-LATEST": - return "Hosted Windows 2019 with VS2019"; - case "WINDOWS SERVER 1803": - case "WIN1803": - return "Hosted Windows Container"; - case "MACOS 10.13": - case "MACOS-10.13": - case "XCODE 9 ON MACOS 10.13": - case "XCODE9-MACOS10.13": - case "XCODE 10 ON MACOS 10.13": - case "XCODE10-MACOS10.13": - return "Hosted macOS High Sierra"; - case "MACOS 10.14": - case "MACOS-10.14": - case "MACOS LATEST": - case "MACOS-LATEST": - return "Hosted macOS"; - default: - return null; - } - } - - /// - /// PipelineBuildContexts have build options. - /// GraphExecutionContexts have dependencies. - /// We might need either depending on the situation. - /// - private TaskAgentPoolReference ValidateQueue( - IPipelineContext context, - ValidationResult result, - BuildOptions buildOptions) - { - var queueId = 0; - var queueName = (String)null; - var queueNameIsUnresolvableExpression = false; // true iff Name is an expression, we're allowed to use them, and it has no current value - var queue = this.Queue; - if (queue != null) - { - queueId = queue.Id; - - // resolve name - var expressionValueName = queue.Name; - if (expressionValueName != null && (buildOptions.EnableResourceExpressions || expressionValueName.IsLiteral)) - { - // resolve expression - try - { - queueName = expressionValueName.GetValue(context).Value; - queueNameIsUnresolvableExpression = !expressionValueName.IsLiteral && String.IsNullOrEmpty(queueName); - } - catch (Exception ee) - { - // something bad happened trying to fetch the value. - // We do not really care what though. Just record the error and move on. - queueName = null; - - if (buildOptions.ValidateExpressions && buildOptions.ValidateResources) - { - result.Errors.Add(new PipelineValidationError(ee.Message)); - } - } - - // resolve name macro - if (buildOptions.EnableResourceExpressions && queueName != null && VariableUtility.IsVariable(queueName)) - { - queueName = context.ExpandVariables(queueName); - if (VariableUtility.IsVariable(queueName)) - { - // name appears to be a macro that is not defined. - queueNameIsUnresolvableExpression = true; - } - } - } - } - - if (queueNameIsUnresolvableExpression || (queueId == 0 && String.IsNullOrEmpty(queueName))) - { - // could not determine what queue user was talking about - if (!buildOptions.AllowEmptyQueueTarget && buildOptions.ValidateResources) - { - // expression-based queue names are allowed to be unresolved at compile time. - // TEMPORARY: literal queue names do not error at compile time if special keys exist - if (!queueNameIsUnresolvableExpression || buildOptions.ValidateExpressions) - { - if (!String.IsNullOrEmpty(queueName)) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFoundByName(queueName))); - } - else - { - var expressionValueName = queue?.Name; - if (expressionValueName == null || expressionValueName.IsLiteral) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotDefined())); - } - else if (expressionValueName != null) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFoundByName(expressionValueName.Expression))); - } - } - } - } - } - else - { - // we have a valid queue. record the reference - result.AddQueueReference(id: queueId, name: queueName); - - // Attempt to resolve the queue using any identifier specified. We will look up by either ID - // or name and the ID is preferred since it is immutable and more specific. - if (buildOptions.ValidateResources) - { - TaskAgentQueue taskAgentQueue = null; - var resourceStore = context.ResourceStore; - if (resourceStore != null) - { - if (queueId != 0) - { - taskAgentQueue = resourceStore.GetQueue(queueId); - if (taskAgentQueue == null) - { - result.UnauthorizedResources.Queues.Add(new AgentQueueReference { Id = queueId }); - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFound(queueId))); - } - } - else if (!String.IsNullOrEmpty(queueName)) - { - taskAgentQueue = resourceStore.GetQueue(queueName); - if (taskAgentQueue == null) - { - result.UnauthorizedResources.Queues.Add(new AgentQueueReference { Name = queueName }); - result.Errors.Add(new PipelineValidationError(PipelineStrings.QueueNotFoundByName(queueName))); - } - } - } - - // Store the resolved values inline to the resolved resource for this validation run - if (taskAgentQueue != null) - { - this.Queue.Id = taskAgentQueue.Id; - return taskAgentQueue.Pool; - } - } - } - - return null; - } - - internal override void Validate( - IPipelineContext context, - BuildOptions buildOptions, - ValidationResult result, - IList steps, - ISet taskDemands) - { - // validate queue - var resolvedPool = ValidateQueue(context, result, buildOptions); - Boolean includeTaskDemands = resolvedPool == null || !resolvedPool.IsHosted; - - // Add advanced-checkout min agent demand - Boolean advancedCheckout = false; - int checkoutTasks = 0; - int injectedSystemTasks = 0; - bool countInjectSystemTasks = true; - for (int index = 0; index < steps.Count; index++) - { - var step = steps[index]; - // Task - if (step.Type == StepType.Task) - { - var task = step as TaskStep; - if (task.Name.StartsWith("__system_")) - { - if (countInjectSystemTasks) - { - injectedSystemTasks++; - } - } - else if (task.IsCheckoutTask()) - { - countInjectSystemTasks = false; - checkoutTasks++; - if (context.EnvironmentVersion < 2) - { - if (index > 0 && index - injectedSystemTasks > 0) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.CheckoutMustBeTheFirstStep())); - } - } - else - { - if (index > 0) - { - advancedCheckout = true; - } - } - - if (task.Inputs.TryGetValue(PipelineConstants.CheckoutTaskInputs.Repository, out String repository) && - !String.Equals(repository, PipelineConstants.SelfAlias, StringComparison.OrdinalIgnoreCase) && - !String.Equals(repository, PipelineConstants.NoneAlias, StringComparison.OrdinalIgnoreCase) && - !String.Equals(repository, PipelineConstants.DesignerRepo, StringComparison.OrdinalIgnoreCase)) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.CheckoutStepRepositoryNotSupported(task.Inputs[PipelineConstants.CheckoutTaskInputs.Repository]))); - } - } - else - { - countInjectSystemTasks = false; - } - } - } - - if (checkoutTasks > 1) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.CheckoutMultipleRepositoryNotSupported())); - } - - if (advancedCheckout) - { - taskDemands.Add(new DemandMinimumVersion(PipelineConstants.AgentVersionDemandName, PipelineConstants.AdvancedCheckoutMinAgentVersion)); - } - - // Now we need to ensure we have only a single demand for the mimimum agent version. We effectively remove - // every agent version demand we find and keep track of the one with the highest value. Assuming we located - // one or more of these demands we will ensure it is merged in at the end. - var minimumAgentVersionDemand = ResolveAgentVersionDemand(taskDemands); - minimumAgentVersionDemand = ResolveAgentVersionDemand(this.Demands, minimumAgentVersionDemand); - - // not include demands from task if phase is running inside container - // container suppose provide any required tool task needs - if (this.Container != null) - { - includeTaskDemands = false; - } - - // Merge the phase demands with the implicit demands from tasks. - if (includeTaskDemands && buildOptions.RollupStepDemands) - { - this.Demands.UnionWith(taskDemands); - } - - // If we resolved a minimum agent version demand then we go ahead and merge it in - // We want to do this even if targetting Hosted - if (minimumAgentVersionDemand != null) - { - this.Demands.Add(minimumAgentVersionDemand); - } - } - - private static DemandMinimumVersion ResolveAgentVersionDemand( - ISet demands, - DemandMinimumVersion currentMinimumVersion = null) - { - var minVersionDemand = DemandMinimumVersion.MaxAndRemove(demands); - if (minVersionDemand != null && (currentMinimumVersion == null || DemandMinimumVersion.CompareVersion(minVersionDemand.Value, currentMinimumVersion.Value) > 0)) - { - return minVersionDemand; - } - else - { - return currentMinimumVersion; - } - } - - internal override JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String jobName, - Int32 attempt, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory) - { - context.Trace?.EnterProperty("CreateJobContext"); - var execution = this.Execution ?? new ParallelExecutionOptions(); - var jobContext = execution.CreateJobContext( - context, - jobName, - attempt, - this.Container, - this.SidecarContainers, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory); - context.Trace?.LeaveProperty("CreateJobContext"); - - if (jobContext != null) - { - jobContext.Job.Definition.Workspace = this.Workspace?.Clone(); - } - - return jobContext; - } - - internal override ExpandPhaseResult Expand( - PhaseExecutionContext context, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory, - JobExpansionOptions options) - { - context.Trace?.EnterProperty("Expand"); - var execution = this.Execution ?? new ParallelExecutionOptions(); - var result = execution.Expand( - context, - this.Container, - this.SidecarContainers, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory, - options); - context.Trace?.LeaveProperty("Expand"); - - foreach (var job in result.Jobs) - { - job.Definition.Workspace = this.Workspace?.Clone(); - } - - return result; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_sidecarContainers?.Count == 0) - { - m_sidecarContainers = null; - } - } - - [DataMember(Name = "SidecarContainers", EmitDefaultValue = false)] - private IDictionary> m_sidecarContainers; - - /// - /// Ensures conversion of a TaskAgentQueue into an AgentQueueReference works properly when the serializer - /// is configured to write/honor type information. This is a temporary converter that may be removed after - /// M127 ships. - /// - private sealed class QueueJsonConverter : VssSecureJsonConverter - { - public override Boolean CanWrite => false; - - public override Boolean CanConvert(Type objectType) - { - return objectType.Equals(typeof(AgentQueueReference)); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - var rawValue = JObject.Load(reader); - using (var objectReader = rawValue.CreateReader()) - { - var newValue = new AgentQueueReference(); - serializer.Populate(objectReader, newValue); - return newValue; - } - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Artifacts/ArtifactConstants.cs b/src/Sdk/DTPipelines/Pipelines/Artifacts/ArtifactConstants.cs deleted file mode 100644 index 790250359..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Artifacts/ArtifactConstants.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Pipelines.Artifacts -{ - public static class ArtifactConstants - { - internal static class ArtifactType - { - internal const String Build = nameof(Build); - internal const String Container = nameof(Container); - internal const String Package = nameof(Package); - internal const String SourceControl = nameof(SourceControl); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Artifacts/DownloadStepExtensions.cs b/src/Sdk/DTPipelines/Pipelines/Artifacts/DownloadStepExtensions.cs deleted file mode 100644 index 192e71bd2..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Artifacts/DownloadStepExtensions.cs +++ /dev/null @@ -1,150 +0,0 @@ -using System; -using System.Collections.Generic; - -using GitHub.DistributedTask.Pipelines; -using GitHub.DistributedTask.Pipelines.Artifacts; -namespace GitHub.DistributedTask.Orchestration.Server.Artifacts -{ - public static class DownloadStepExtensions - { - public static Boolean IsDownloadBuildStepExists(this IReadOnlyList steps) - { - foreach (var step in steps) - { - if (step is TaskStep taskStep) - { - if (taskStep.IsDownloadBuildTask()) - { - return true; - } - } - } - - return false; - } - - public static Boolean IsDownloadBuildTask(this Step step) - { - if (step is TaskStep taskStep && - taskStep.Reference != null && - taskStep.Reference.Name.Equals(YamlArtifactConstants.DownloadBuild, StringComparison.OrdinalIgnoreCase)) - { - return true; - } - - return false; - } - - public static Boolean IsDownloadStepDisabled(this Step step) - { - // either download task or downloadBuild task has none keyword return true. - if (step is TaskStep taskStep && - taskStep.Inputs.TryGetValue(PipelineArtifactConstants.DownloadTaskInputs.Alias, out String alias) && - String.Equals(alias, YamlArtifactConstants.None, StringComparison.OrdinalIgnoreCase) && - (step.IsDownloadBuildTask() || step.IsDownloadTask())) - { - return true; - } - - return false; - } - - public static Boolean IsDownloadTask(this Step step) - { - if (step is TaskStep taskStep && - taskStep.Reference != null && - taskStep.Reference.Id.Equals(PipelineArtifactConstants.DownloadTask.Id) && - taskStep.Reference.Version == PipelineArtifactConstants.DownloadTask.Version) - { - return true; - } - else - { - return false; - } - } - - public static Boolean IsDownloadCurrentPipelineArtifactStep(this Step step) - { - if (step is TaskStep taskStep && - taskStep.IsDownloadTask() && - taskStep.Inputs.TryGetValue(PipelineArtifactConstants.DownloadTaskInputs.Alias, out String alias) && - String.Equals(alias, YamlArtifactConstants.Current, StringComparison.OrdinalIgnoreCase)) - { - return true; - } - - return false; - } - - public static Boolean IsDownloadPipelineArtifactStepDisabled(this TaskStep step) - { - if (step.IsDownloadTask() && - step.Inputs.TryGetValue(PipelineArtifactConstants.DownloadTaskInputs.Alias, out String alias) && - String.Equals(alias, YamlArtifactConstants.None, StringComparison.OrdinalIgnoreCase)) - { - return true; - } - - return false; - } - - public static Boolean IsDownloadExternalPipelineArtifactStep(this TaskStep step) - { - if (step.IsDownloadTask() && - step.Inputs != null && - step.Inputs.TryGetValue(PipelineArtifactConstants.DownloadTaskInputs.Alias, out String alias) && - !String.IsNullOrEmpty(alias) && - !alias.Equals(YamlArtifactConstants.Current, StringComparison.OrdinalIgnoreCase) && - !alias.Equals(YamlArtifactConstants.None, StringComparison.OrdinalIgnoreCase)) - { - return true; - } - - return false; - } - - public static String GetAliasFromTaskStep(this TaskStep step) - { - return step.Inputs.TryGetValue(PipelineArtifactConstants.DownloadTaskInputs.Alias, out String alias) - ? alias - : String.Empty; - } - - public static Boolean IsDownloadPipelineArtifactStepExists(this IReadOnlyList steps) - { - foreach (var step in steps) - { - if (step is TaskStep taskStep) - { - if (taskStep.IsDownloadTask()) - { - return true; - } - } - } - - return false; - } - - public static void Merge( - this IDictionary first, - IDictionary second) - { - foreach (var key in second?.Keys ?? new List()) - { - first[key] = second[key]; - } - } - - public static void Merge( - this IDictionary first, - IReadOnlyDictionary second) - { - foreach (var key in second?.Keys ?? new List()) - { - first[key] = second[key]; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Artifacts/IArtifactResolver.cs b/src/Sdk/DTPipelines/Pipelines/Artifacts/IArtifactResolver.cs deleted file mode 100644 index aee03a05d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Artifacts/IArtifactResolver.cs +++ /dev/null @@ -1,49 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines.Artifacts -{ - /// - /// Provides a mechanism to resolve the artifacts - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IArtifactResolver - { - /// - /// Given a resource, it gets the corresponding task id from its extension - /// - /// - /// - Guid GetArtifactDownloadTaskId(Resource resource); - - /// - /// Given a resource and step, it maps the resource properties to task inputs - /// - /// - /// - void PopulateMappedTaskInputs(Resource resource, TaskStep taskStep); - - /// - /// Given an artifact step, it resolves the artifact and returns a download artifact task - /// - /// - /// - /// - Boolean ResolveStep(IPipelineContext pipelineContext, JobStep step, out IList resolvedSteps); - - /// - /// Given resource store and task step it translate the taskStep into actual task reference with mapped inputs - /// - /// - /// - /// - Boolean ResolveStep(IResourceStore resourceStore, TaskStep taskStep, out String errorMessage); - - /// - /// Validate the given resource in the YAML file. Also resolve version for the resource if not resolved already - /// - /// - Boolean ValidateDeclaredResource(Resource resource, out PipelineValidationError error); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Artifacts/PipelineArtifactConstants.cs b/src/Sdk/DTPipelines/Pipelines/Artifacts/PipelineArtifactConstants.cs deleted file mode 100644 index 867756bdf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Artifacts/PipelineArtifactConstants.cs +++ /dev/null @@ -1,113 +0,0 @@ -using System; - -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Artifacts -{ - public static class PipelineArtifactConstants - { - internal static class CommonArtifactTaskInputValues - { - internal const String DefaultDownloadPath = "$(Pipeline.Workspace)"; - internal const String DefaultDownloadPattern = "**"; - } - - public static class PipelineArtifactTaskInputs - { - public const String ArtifactName = "artifactName"; - - public const String BuildType = "buildType"; - - public const String BuildId = "buildId"; - - public const String BuildVersionToDownload = "buildVersionToDownload"; - - public const String Definition = "definition"; - - public const String DownloadType = "downloadType"; - - public const String DownloadPath = "downloadPath"; - - public const String FileSharePath = "fileSharePath"; - - public const String ItemPattern = "itemPattern"; - - public const String Project = "project"; - } - - public static class PipelineArtifactTaskInputValues - { - public const String DownloadTypeSingle = "single"; - public const String SpecificBuildType = "specific"; - public const String CurrentBuildType = "current"; - public const String AutomaticMode = "automatic"; - public const String ManualMode = "manual"; - } - - internal static class YamlConstants - { - internal const String Connection = "connection"; - internal const String Current = "current"; - internal const String None = "none"; - } - - public static class ArtifactTypes - { - public const string AzurePipelineArtifactType = "Pipeline"; - } - - public static class DownloadTaskInputs - { - public const String Alias = "alias"; - public const String Artifact = "artifact"; - public const String Mode = "mode"; - public const String Path = "path"; - public const String Patterns = "patterns"; - } - - public static class TraceConstants - { - public const String Area = "PipelineArtifacts"; - public const String DownloadPipelineArtifactFeature = "DownloadPipelineArtifact"; - } - - public static readonly TaskDefinition DownloadTask = new TaskDefinition - { - Id = new Guid("30f35852-3f7e-4c0c-9a88-e127b4f97211"), - Name = "Download", - FriendlyName = "Download Artifact", - Author = "Microsoft", - RunsOn = { TaskRunsOnConstants.RunsOnAgent }, - Version = new TaskVersion("1.0.0"), - Description = "Downloads pipeline type artifacts.", - HelpMarkDown = "[More Information](https://github.com)", - Inputs = { - new TaskInputDefinition() - { - Name = DownloadTaskInputs.Artifact, - Required = true, - InputType = TaskInputType.String - }, - new TaskInputDefinition() - { - Name = DownloadTaskInputs.Patterns, - Required = false, - DefaultValue = "**", - InputType = TaskInputType.String - }, - new TaskInputDefinition() - { - Name = DownloadTaskInputs.Path, - Required = false, - InputType = TaskInputType.String - }, - new TaskInputDefinition() - { - Name=DownloadTaskInputs.Alias, - Required = false, - InputType = TaskInputType.String - } - }, - }; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Artifacts/YamlArtifactConstants.cs b/src/Sdk/DTPipelines/Pipelines/Artifacts/YamlArtifactConstants.cs deleted file mode 100644 index 5fe5bba9a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Artifacts/YamlArtifactConstants.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.Pipelines.Artifacts -{ - public static class YamlArtifactConstants - { - public const String Alias = "alias"; - public const String Connection = "connection"; - public const String Current = "current"; - public const String Download = "download"; - public const String DownloadBuild = "downloadBuild"; - public const String None = "none"; - public const String Path = "path"; - public const String Patterns = "patterns"; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/BuildOptions.cs b/src/Sdk/DTPipelines/Pipelines/BuildOptions.cs deleted file mode 100644 index c92128945..000000000 --- a/src/Sdk/DTPipelines/Pipelines/BuildOptions.cs +++ /dev/null @@ -1,119 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism for controlling validation behaviors. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class BuildOptions - { - public static BuildOptions None { get; } = new BuildOptions(); - - /// - /// Gets or sets a value indicating whether or not a queue target without a queue should be considered an - /// error. - /// - public Boolean AllowEmptyQueueTarget - { - get; - set; - } - - /// - /// Allow hyphens in names checked by the NameValidator. Used for yaml workflow schema - /// - public Boolean AllowHyphenNames - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether to demand the latest agent version. - /// - public Boolean DemandLatestAgent - { - get; - set; - } - - /// - /// If true, resource definitions are allowed to use expressions - /// - public Boolean EnableResourceExpressions - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not to resolve resource version. - /// - public Boolean ResolveResourceVersions - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether input aliases defined in a task definition are honored. - /// - public Boolean ResolveTaskInputAliases - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not the individual step demands should be rolled up into their - /// parent phase's demands. Settings this value to true will result in Phase's demand sets being a superset - /// of their children's demands. - /// - public Boolean RollupStepDemands - { - get; - set; - } - - /// - /// If true, all expressions must be resolvable given a provided context. - /// This is normally going to be false for plan compile time and true for plan runtime. - /// - public Boolean ValidateExpressions - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not to validate resource existence and other constraints. - /// - public Boolean ValidateResources - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not step names provided by the caller should be validated for - /// correctness and uniqueness. Setting this value to false will automatically fix invalid step names and - /// de-duplicate step names which may lead to unexpected behavior at runtime when binding output variables. - /// - public Boolean ValidateStepNames - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not to run input validation defined by the task author. - /// - public Boolean ValidateTaskInputs - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/BuildResource.cs b/src/Sdk/DTPipelines/Pipelines/BuildResource.cs deleted file mode 100644 index b6e6a15a4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/BuildResource.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class BuildPropertyNames - { - public static readonly String Branch = "branch"; - public static readonly String Connection = "connection"; - public static readonly String Source = "source"; - public static readonly String Type = "type"; - public static readonly String Version = "version"; - } - - /// - /// Provides a data contract for a build resource referenced by a pipeline. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class BuildResource : Resource - { - public BuildResource() - { - } - - protected BuildResource(BuildResource resourceToCopy) - : base(resourceToCopy) - { - } - - /// - /// Gets or sets the type of build resource. - /// - public String Type - { - get - { - return this.Properties.Get(BuildPropertyNames.Type); - } - set - { - this.Properties.Set(BuildPropertyNames.Type, value); - } - } - - /// - /// Gets or sets the version of the build resource. - /// - public String Version - { - get - { - return this.Properties.Get(BuildPropertyNames.Version); - } - set - { - this.Properties.Set(BuildPropertyNames.Version, value); - } - } - - public BuildResource Clone() - { - return new BuildResource(this); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointContext.cs b/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointContext.cs deleted file mode 100644 index c33bd72e1..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointContext.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.Pipelines.Checkpoints -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class CheckpointContext - { - /// - /// Unique id of the checkpoint, also used as the timeline record id - /// - [DataMember(IsRequired = true)] - public Guid Id { get; set; } - - /// - /// Auth token for querying DistributedTask - /// - [DataMember(IsRequired = true)] - public String Token { get; set; } - - /// - /// Checkpoint Instance Id - /// Use this for sending decision events and tracing telemetry. - /// - [DataMember(IsRequired = true)] - public String OrchestrationId { get; set; } - - /// - /// PlanId - /// - [DataMember(IsRequired = true)] - public Guid PlanId { get; set; } - - /// - /// Which TaskHub to use when sending decision events; - /// Use this for sending decision events. - /// - [DataMember(IsRequired = true)] - public String HubName { get; set; } - - /// - /// The project requesting decision. - /// - [DataMember(EmitDefaultValue = false)] - public CheckpointScope Project { get; set; } - - /// - /// The pipeline (definition) requesting decision. - /// - [DataMember(EmitDefaultValue = false)] - public PipelineScope Pipeline { get; set; } - - /// - /// The graph node requesting decision. - /// - [DataMember(EmitDefaultValue = false)] - public GraphNodeScope GraphNode { get; set; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointDecision.cs b/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointDecision.cs deleted file mode 100644 index 28bdbbdbf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointDecision.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.Pipelines.Checkpoints -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class CheckpointDecision - { - /// - /// Checkpoint id, provided on context - /// - [DataMember(IsRequired = true)] - public Guid Id { get; set; } - - /// - /// Decision - /// - [DataMember(IsRequired = true)] - public String Result { get; set; } - - /// - /// Additional information (optional) - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Message { get; set; } - - // Decision possibilities - public const String Approved = "Approved"; - public const String Denied = "Denied"; - public const String Canceled = "Canceled"; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointScope.cs b/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointScope.cs deleted file mode 100644 index bfcab3c79..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Checkpoints/CheckpointScope.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.Pipelines.Checkpoints -{ - /// - /// Provides context regarding the state of the orchestration. - /// Consumers may choose to use this information to cache decisions. - /// EG, if you wanted to return the same decision for this and all - /// future requests issuing from the same project / pipeline / stage / run - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class CheckpointScope - { - /// - /// May be used in uniquely identify this scope for future reference. - /// - [DataMember(IsRequired = true)] - public String Id { get; set; } - - /// - /// The friendly name of the scope - /// - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class GraphNodeScope : CheckpointScope - { - /// - /// Facilitates approving only a single attempt of a graph node in a specific run of a pipeline. - /// - [DataMember(IsRequired = true)] - public Int32 Attempt { get; set; } = 1; - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class PipelineScope : CheckpointScope - { - /// - /// Pipeline URLs - /// - [DataMember(IsRequired = true)] - public TaskOrchestrationOwner Owner { get; set; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Checkpoints/ResourceInfo.cs b/src/Sdk/DTPipelines/Pipelines/Checkpoints/ResourceInfo.cs deleted file mode 100644 index 66daffc0d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Checkpoints/ResourceInfo.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.Pipelines.Checkpoints -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - [ClientIgnore] - public class ResourceInfo - { - [DataMember(EmitDefaultValue = false)] - public String Id { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String TypeName { get; set; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ConditionResult.cs b/src/Sdk/DTPipelines/Pipelines/ConditionResult.cs deleted file mode 100644 index 1ca93e757..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ConditionResult.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ConditionResult - { - [DataMember] - public Boolean Value - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Trace - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ContinuousIntegrationTrigger.cs b/src/Sdk/DTPipelines/Pipelines/ContinuousIntegrationTrigger.cs deleted file mode 100644 index 1cc138e77..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ContinuousIntegrationTrigger.cs +++ /dev/null @@ -1,89 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class ContinuousIntegrationTrigger : PipelineTrigger - { - public ContinuousIntegrationTrigger() - : base(PipelineTriggerType.ContinuousIntegration) - { - Enabled = true; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean Enabled - { - get; - set; - } - - /// - /// Indicates whether changes should be batched while another CI pipeline is running. - /// - /// - /// If this is true, then changes submitted while a CI pipeline is running will be batched and built in one new CI pipeline when the current pipeline finishes. - /// If this is false, then a new CI pipeline will be triggered for each change to the repository. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean BatchChanges - { - get; - set; - } - - /// - /// A list of filters that describe which branches will trigger pipelines. - /// - public IList BranchFilters - { - get - { - if (m_branchFilters == null) - { - m_branchFilters = new List(); - } - return m_branchFilters; - } - } - - /// - /// A list of filters that describe which paths will trigger pipelines. - /// - public IList PathFilters - { - get - { - if (m_pathFilters == null) - { - m_pathFilters = new List(); - } - return m_pathFilters; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_branchFilters?.Count == 0) - { - m_branchFilters = null; - } - - if (m_pathFilters?.Count == 0) - { - m_pathFilters = null; - } - } - - [DataMember(Name = "BranchFilters", EmitDefaultValue = false)] - private List m_branchFilters; - - [DataMember(Name = "PathFilters", EmitDefaultValue = false)] - private List m_pathFilters; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/CounterStore.cs b/src/Sdk/DTPipelines/Pipelines/CounterStore.cs deleted file mode 100644 index b77ad8a25..000000000 --- a/src/Sdk/DTPipelines/Pipelines/CounterStore.cs +++ /dev/null @@ -1,61 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a default implementation of a counter store. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class CounterStore : ICounterStore - { - public CounterStore( - IDictionary counters = null, - ICounterResolver resolver = null) - { - if (counters?.Count > 0) - { - m_counters.AddRange(counters); - } - - this.Resolver = resolver; - } - - public IReadOnlyDictionary Counters - { - get - { - return m_counters; - } - } - - private ICounterResolver Resolver - { - get; - } - - public Int32 Increment( - IPipelineContext context, - String prefix, - Int32 seed) - { - if (m_counters.TryGetValue(prefix, out Int32 existingValue)) - { - return existingValue; - } - - Int32 newValue = seed; - if (this.Resolver != null) - { - newValue = this.Resolver.Increment(context, prefix, seed); - m_counters[prefix] = newValue; - } - - return newValue; - } - - private readonly Dictionary m_counters = new Dictionary(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/CreateJobResult.cs b/src/Sdk/DTPipelines/Pipelines/CreateJobResult.cs deleted file mode 100644 index 2802869c0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/CreateJobResult.cs +++ /dev/null @@ -1,50 +0,0 @@ -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public struct CreateJobResult - { - public CreateJobResult( - JobExecutionContext context, - Job job) - { - this.Job = job; - this.Context = context; - } - - public Job Job - { - get; - } - - public JobExecutionContext Context - { - get; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public struct CreateTaskResult - { - public CreateTaskResult( - TaskStep task, - TaskDefinition definition) - { - this.Task = task; - this.Definition = definition; - } - - public TaskStep Task - { - get; - } - - public TaskDefinition Definition - { - get; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/DeploymentExecutionOptions.cs b/src/Sdk/DTPipelines/Pipelines/DeploymentExecutionOptions.cs deleted file mode 100644 index 5ec777815..000000000 --- a/src/Sdk/DTPipelines/Pipelines/DeploymentExecutionOptions.cs +++ /dev/null @@ -1,74 +0,0 @@ -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - internal enum DeploymentRollingOption - { - [EnumMember] - Absolute, - - [EnumMember] - Percentage - } - - [DataContract] - internal class DeploymentExecutionOptions - { - public DeploymentExecutionOptions() - { - } - - private DeploymentExecutionOptions(DeploymentExecutionOptions optionsToCopy) - { - this.RollingOption = optionsToCopy.RollingOption; - this.RollingValue = optionsToCopy.RollingValue; - } - - [DataMember] - public DeploymentRollingOption RollingOption - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public uint RollingValue - { - get; - set; - } - - public DeploymentExecutionOptions Clone() - { - return new DeploymentExecutionOptions(this); - } - - public void Validate( - IPipelineContext context, - ValidationResult result) - { - switch (RollingOption) - { - case DeploymentRollingOption.Absolute: - if (RollingValue == 0) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.InvalidAbsoluteRollingValue())); - } - break; - - case DeploymentRollingOption.Percentage: - if (RollingValue == 0 || RollingValue > 100) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.InvalidPercentageRollingValue())); - } - break; - - default: - result.Errors.Add(new PipelineValidationError(PipelineStrings.InvalidRollingOption(RollingOption))); - break; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/DeploymentGroupTarget.cs b/src/Sdk/DTPipelines/Pipelines/DeploymentGroupTarget.cs deleted file mode 100644 index 9bd5cc6e0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/DeploymentGroupTarget.cs +++ /dev/null @@ -1,158 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - internal class DeploymentGroupTarget : PhaseTarget - { - public DeploymentGroupTarget() - : base(PhaseTargetType.DeploymentGroup) - { - } - - private DeploymentGroupTarget(DeploymentGroupTarget targetToClone) - : base(targetToClone) - { - this.DeploymentGroup = targetToClone.DeploymentGroup?.Clone(); - this.Execution = targetToClone.Execution?.Clone(); - - if (targetToClone.m_tags != null && targetToClone.m_tags.Count > 0) - { - m_tags = new HashSet(targetToClone.m_tags, StringComparer.OrdinalIgnoreCase); - } - } - - [DataMember] - public DeploymentGroupReference DeploymentGroup - { - get; - set; - } - - public ISet Tags - { - get - { - if (m_tags == null) - { - m_tags = new HashSet(StringComparer.OrdinalIgnoreCase); - } - return m_tags; - } - } - - /// - /// Gets targets Ids filter on which deployment should be done. - /// - public List TargetIds - { - get - { - if (m_targetIds == null) - { - m_targetIds = new List(); - } - return m_targetIds; - } - } - - [DataMember(EmitDefaultValue = false)] - public DeploymentExecutionOptions Execution - { - get; - set; - } - - public override PhaseTarget Clone() - { - return new DeploymentGroupTarget(this); - } - - public override Boolean IsValid(TaskDefinition task) - { - return task.RunsOn.Contains(TaskRunsOnConstants.RunsOnDeploymentGroup, StringComparer.OrdinalIgnoreCase); - } - - internal override void Validate( - IPipelineContext context, - BuildOptions buildOptions, - ValidationResult result, - IList steps, - ISet taskDemands) - { - this.Execution?.Validate(context, result); - } - - internal override JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String jobName, - Int32 attempt, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory) - { - context.Trace?.EnterProperty("CreateJobContext"); - var result = new ParallelExecutionOptions().CreateJobContext( - context, - jobName, - attempt, - null, - null, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory); - context.Trace?.LeaveProperty("CreateJobContext"); - return result; - } - - internal override ExpandPhaseResult Expand( - PhaseExecutionContext context, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory, - JobExpansionOptions options) - { - context.Trace?.EnterProperty("Expand"); - var result = new ParallelExecutionOptions().Expand( - context: context, - container: null, - sidecarContainers: null, - continueOnError: continueOnError, - timeoutInMinutes: timeoutInMinutes, - cancelTimeoutInMinutes: cancelTimeoutInMinutes, - jobFactory: jobFactory, - options: options); - context.Trace?.LeaveProperty("Expand"); - return result; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_tags?.Count == 0) - { - m_tags = null; - } - - if (m_targetIds?.Count == 0) - { - m_targetIds = null; - } - } - - [DataMember(Name = "Tags", EmitDefaultValue = false)] - private ISet m_tags; - - [DataMember(Name = "TargetIds")] - private List m_targetIds; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Environment/EnvironmentReference.cs b/src/Sdk/DTPipelines/Pipelines/Environment/EnvironmentReference.cs deleted file mode 100644 index 93e441d75..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Environment/EnvironmentReference.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class EnvironmentReference : ResourceReference - { - public EnvironmentReference() - { - } - - private EnvironmentReference(EnvironmentReference referenceToCopy) - : base(referenceToCopy) - { - this.Id = referenceToCopy.Id; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - public EnvironmentReference Clone() - { - return new EnvironmentReference(this); - } - - public override String ToString() - { - return base.ToString() ?? this.Id.ToString(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/EnvironmentDeploymentTarget.cs b/src/Sdk/DTPipelines/Pipelines/EnvironmentDeploymentTarget.cs deleted file mode 100644 index c34748631..000000000 --- a/src/Sdk/DTPipelines/Pipelines/EnvironmentDeploymentTarget.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class EnvironmentDeploymentTarget - { - [DataMember] - public Int32 EnvironmentId { get; set; } - - [DataMember] - public String EnvironmentName { get; set; } - - [DataMember] - public EnvironmentResourceReference Resource { get; set; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/EnvironmentStore.cs b/src/Sdk/DTPipelines/Pipelines/EnvironmentStore.cs deleted file mode 100644 index b0e96bf65..000000000 --- a/src/Sdk/DTPipelines/Pipelines/EnvironmentStore.cs +++ /dev/null @@ -1,97 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class EnvironmentStore : IEnvironmentStore - { - public EnvironmentStore( - IList environments, - IEnvironmentResolver resolver = null) - { - m_resolver = resolver; - m_environmentsByName = new Dictionary(StringComparer.OrdinalIgnoreCase); - m_environmentsById = new Dictionary(); - Add(environments?.ToArray()); - } - - public void Add(params EnvironmentInstance[] environments) - { - if (environments is null) - { - return; - } - foreach (var e in environments) - { - if (e != null) - { - m_environmentsById[e.Id] = e; - - var name = e.Name; - if (!string.IsNullOrWhiteSpace(name)) - { - m_environmentsByName[name] = e; - } - } - } - } - - public EnvironmentInstance ResolveEnvironment(String name) - { - if (!m_environmentsByName.TryGetValue(name, out var environment) - && m_resolver != null) - { - environment = m_resolver?.Resolve(name); - Add(environment); - } - - return environment; - } - - public EnvironmentInstance ResolveEnvironment(Int32 id) - { - if (!m_environmentsById.TryGetValue(id, out var environment) - && m_resolver != null) - { - environment = m_resolver?.Resolve(id); - Add(environment); - } - - return environment; - } - - public EnvironmentInstance Get(EnvironmentReference reference) - { - if (reference is null) - { - return null; - } - - if (reference.Name?.IsLiteral == true) - { - return ResolveEnvironment(reference.Name.Literal); - } - - return ResolveEnvironment(reference.Id); - } - - public IList GetReferences() - { - return m_environmentsById.Values - .Select(x => new EnvironmentReference - { - Id = x.Id, - Name = x.Name - }) - .ToList(); - } - - private IEnvironmentResolver m_resolver; - private IDictionary m_environmentsByName; - private IDictionary m_environmentsById; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ExecutionOptions.cs b/src/Sdk/DTPipelines/Pipelines/ExecutionOptions.cs deleted file mode 100644 index 6da517f9b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ExecutionOptions.cs +++ /dev/null @@ -1,107 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism for controlling runtime behaviors. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class ExecutionOptions - { - public ExecutionOptions() - { - } - - /// - /// Gets or sets a value indicating whether or not to remove secrets from job message. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean RestrictSecrets - { - get; - set; - } - - /// - /// Gets or sets a value indicating what scope the system jwt token will have. - /// - [DataMember(EmitDefaultValue = false)] - public String SystemTokenScope - { - get; - set; - } - - /// - /// Gets or sets value indicating any custom claims the system jwt token will have. - /// - public IDictionary SystemTokenCustomClaims - { - get - { - if (m_systemTokenCustomClaims == null) - { - m_systemTokenCustomClaims = new Dictionary(); - } - return m_systemTokenCustomClaims; - } - } - - /// - /// Gets or sets a value indicating what's the max number jobs we allow after expansion. - /// - [DataMember(EmitDefaultValue = false)] - public Int32? MaxJobExpansion - { - get; - set; - } - - /// - /// Gets or sets a value indicating the max parallelism slots available to overwrite MaxConcurrency of test job slicing - /// - [DataMember(EmitDefaultValue = false)] - public Int32? MaxParallelism - { - get; - set; - } - - /// - /// Gets or sets a value indicating if we should allow expressions to define secured resources. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean EnableResourceExpressions - { - get; - set; - } - - /// - /// Driven by FF: DistributedTask.LegalNodeNames - /// - [DataMember(EmitDefaultValue = false)] - public Boolean EnforceLegalNodeNames - { - get; - set; - } - - /// - /// Allows hyphens in yaml names - /// - [DataMember(EmitDefaultValue = false)] - public Boolean AllowHyphenNames - { - get; - set; - } - - [DataMember(Name = nameof(SystemTokenCustomClaims), EmitDefaultValue = false)] - private IDictionary m_systemTokenCustomClaims; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ExpandPhaseResult.cs b/src/Sdk/DTPipelines/Pipelines/ExpandPhaseResult.cs deleted file mode 100644 index 11c5e736b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ExpandPhaseResult.cs +++ /dev/null @@ -1,66 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Represents the runtime values of a phase which has been expanded for execution. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class ExpandPhaseResult - { - /// - /// Initializes a new ExpandPhaseResult innstance with a default maximum concurrency of 1. - /// - public ExpandPhaseResult() - { - this.MaxConcurrency = 1; - } - - /// - /// Gets or sets the execution behavior when an error is encountered. - /// - public Boolean ContinueOnError - { - get; - set; - } - - /// - /// Gets or sets the execution behavior when an error is encountered. - /// - public Boolean FailFast - { - get; - set; - } - - /// - /// Gets or sets the maximum concurrency for the jobs. - /// - public Int32 MaxConcurrency - { - get; - set; - } - - /// - /// Gets the list of jobs for this phase. - /// - public IList Jobs - { - get - { - if (m_jobs == null) - { - m_jobs = new List(); - } - return m_jobs; - } - } - - private List m_jobs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ExpressionResult.cs b/src/Sdk/DTPipelines/Pipelines/ExpressionResult.cs deleted file mode 100644 index 289881008..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ExpressionResult.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Represents the result of an ExpressionValue<T> evaluation. - /// - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ExpressionResult - { - /// - /// Initializes a new ExpressionResult instance with the specified value. The value is implicilty treated as - /// non-secret. - /// - /// The resolved value - public ExpressionResult(T value) - : this(value, false) - { - } - - /// - /// Initializes a new ExpressionResult instance with the specified values. - /// - /// The resolved value - /// True if secrets were accessed while resolving the value; otherwise, false - public ExpressionResult( - T value, - Boolean containsSecrets) - { - this.ContainsSecrets = containsSecrets; - this.Value = value; - } - - /// - /// Gets or sets a value indicating whether or not secrets were accessed while resolving . - /// - [DataMember(EmitDefaultValue = false)] - public Boolean ContainsSecrets - { - get; - set; - } - - /// - /// Gets or sets the literal value result. - /// - [DataMember] - public T Value - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ExpressionValue.cs b/src/Sdk/DTPipelines/Pipelines/ExpressionValue.cs index e23c04bc8..47f9e6f7e 100644 --- a/src/Sdk/DTPipelines/Pipelines/ExpressionValue.cs +++ b/src/Sdk/DTPipelines/Pipelines/ExpressionValue.cs @@ -146,26 +146,6 @@ namespace GitHub.DistributedTask.Pipelines /// internal Boolean IsLiteral => String.IsNullOrEmpty(m_expression); - /// - /// Retrieves the referenced value from the provided execution context. - /// - /// The execution context used for variable resolution - /// The value of the variable if found; otherwise, null - public ExpressionResult GetValue(IPipelineContext context = null) - { - if (this.IsLiteral) - { - return new ExpressionResult(m_literalValue, containsSecrets: false); - } - - if (context != null) - { - return context.Evaluate(m_expression); - } - - return null; - } - /// /// Converts the value to a string representation. /// diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/CounterNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/CounterNode.cs deleted file mode 100644 index ad18857ea..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/CounterNode.cs +++ /dev/null @@ -1,28 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class CounterNode : FunctionNode - { - protected override Object EvaluateCore(EvaluationContext evaluationContext) - { - int seed = 0; - var prefix = String.Empty; - if (Parameters.Count > 0) - { - prefix = Parameters[0].EvaluateString(evaluationContext); - } - - if (Parameters.Count > 1) - { - seed = Convert.ToInt32(Parameters[1].EvaluateNumber(evaluationContext)); - } - - var context = evaluationContext.State as IPipelineContext; - return context.CounterStore?.Increment(context, prefix, seed) ?? seed; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/ExpressionConstants.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/ExpressionConstants.cs deleted file mode 100644 index ad3878098..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/ExpressionConstants.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class ExpressionConstants - { - /// - /// Gets the name of the variables node. - /// - public static readonly String Variables = "variables"; - - /// - /// Gets the pipeline context available in pipeline expressions. - /// - public static readonly INamedValueInfo PipelineNamedValue = new NamedValueInfo("pipeline"); - - /// - /// Gets the variable context available in pipeline expressions. - /// - public static readonly INamedValueInfo VariablesNamedValue = new NamedValueInfo("variables"); - - /// - /// Gets the counter function available in pipeline expressions. - /// - public static readonly IFunctionInfo CounterFunction = new FunctionInfo("counter", 0, 2); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/InputValidationConstants.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/InputValidationConstants.cs deleted file mode 100644 index 657eb4aaa..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/InputValidationConstants.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - internal static class InputValidationConstants - { - public static readonly String IsEmail = "isEmail"; - public static readonly String IsInRange = "isInRange"; - public static readonly String IsIPv4Address = "isIPv4Address"; - public static readonly String IsSha1 = "isSha1"; - public static readonly String IsUrl = "isUrl"; - public static readonly String IsMatch = "isMatch"; - public static readonly String Length = "length"; - - public static readonly IFunctionInfo[] Functions = new IFunctionInfo[] - { - new FunctionInfo(InputValidationConstants.IsEmail, IsEmailNode.minParameters, IsEmailNode.maxParameters), - new FunctionInfo(InputValidationConstants.IsInRange, IsInRangeNode.minParameters, IsInRangeNode.maxParameters), - new FunctionInfo(InputValidationConstants.IsIPv4Address, IsIPv4AddressNode.minParameters, IsIPv4AddressNode.maxParameters), - new FunctionInfo(InputValidationConstants.IsMatch, IsMatchNode.minParameters, IsMatchNode.maxParameters), - new FunctionInfo(InputValidationConstants.IsSha1, IsSHA1Node.minParameters, IsSHA1Node.maxParameters), - new FunctionInfo(InputValidationConstants.IsUrl, IsUrlNode.minParameters, IsUrlNode.maxParameters), - new FunctionInfo(InputValidationConstants.Length, LengthNode.minParameters, LengthNode.maxParameters), - }; - - public static readonly INamedValueInfo[] NamedValues = new INamedValueInfo[] - { - new NamedValueInfo("value"), - }; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/InputValueNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/InputValueNode.cs deleted file mode 100644 index 9c7fd5930..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/InputValueNode.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using GitHub.DistributedTask.Expressions; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - internal class InputValueNode : NamedValueNode - { - protected sealed override Object EvaluateCore(EvaluationContext evaluationContext) - { - var validationContext = evaluationContext.State as InputValidationContext; - return validationContext.Value; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsEmailNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsEmailNode.cs deleted file mode 100644 index 39ac71010..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsEmailNode.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsEmailNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 1; - public static Int32 maxParameters = 1; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isEmail(value: string) - String value = Parameters[0].EvaluateString(context) ?? String.Empty; - return RegexUtility.IsMatch(value, WellKnownRegularExpressions.Email); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsIPv4AddressNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsIPv4AddressNode.cs deleted file mode 100644 index 475833213..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsIPv4AddressNode.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsIPv4AddressNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 1; - public static Int32 maxParameters = 1; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isIpV4Address(value: string) - String value = Parameters[0].EvaluateString(context) ?? String.Empty; - return RegexUtility.IsMatch(value, WellKnownRegularExpressions.IPv4Address); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsInRangeNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsInRangeNode.cs deleted file mode 100644 index e18598949..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsInRangeNode.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsInRangeNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 3; - public static Int32 maxParameters = 3; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isInRange(value: string, min: string, max: string) - decimal value = Parameters[0].EvaluateNumber(context); - decimal min = Parameters[1].EvaluateNumber(context); - decimal max = Parameters[2].EvaluateNumber(context); - return value >= min && value <= max; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsMatchNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsMatchNode.cs deleted file mode 100644 index 7a45f353c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsMatchNode.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsMatchNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 2; - public static Int32 maxParameters = 3; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isMatch(value: string, regEx: string, options?: string) - String value = Parameters[0].EvaluateString(context) ?? String.Empty; - String regEx = Parameters[1].EvaluateString(context) ?? String.Empty; - String regExOptionsString = String.Empty; - - if (Parameters.Count == 3) - { - regExOptionsString = Parameters[2].EvaluateString(context) ?? String.Empty; - } - - return RegexUtility.IsMatch(value, regEx, regExOptionsString); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsSHA1Node.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsSHA1Node.cs deleted file mode 100644 index ecc4d8a05..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsSHA1Node.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsSHA1Node : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 1; - public static Int32 maxParameters = 1; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isSha1(value: string) - String value = Parameters[0].EvaluateString(context) ?? String.Empty; - return RegexUtility.IsMatch(value, WellKnownRegularExpressions.SHA1); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/IsUrlNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/IsUrlNode.cs deleted file mode 100644 index 9c94e77ab..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/IsUrlNode.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class IsUrlNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 1; - public static Int32 maxParameters = 1; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // isUrl(value: string) - String value = Parameters[0].EvaluateString(context) ?? String.Empty; - return RegexUtility.IsMatch(value, WellKnownRegularExpressions.Url); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/LengthNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/LengthNode.cs deleted file mode 100644 index 0675c001f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/LengthNode.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class LengthNode : FunctionNode - { - protected sealed override Boolean TraceFullyRealized => false; - - public static Int32 minParameters = 1; - public static Int32 maxParameters = 1; - - protected sealed override Object EvaluateCore(EvaluationContext context) - { - // Length(value: object) - var evaluationResult = Parameters[0].Evaluate(context); - bool kindNotSupported = false; - Int32 length = -1; - - switch (evaluationResult.Kind) - { - case ValueKind.Array: - length = ((JArray)evaluationResult.Value).Count; - break; - case ValueKind.String: - length = ((String)evaluationResult.Value).Length; - break; - case ValueKind.Object: - if (evaluationResult.Value is IReadOnlyDictionary) - { - length = ((IReadOnlyDictionary)evaluationResult.Value).Count; - } - else if (evaluationResult.Value is ICollection) - { - length = ((ICollection)evaluationResult.Value).Count; - } - else - { - kindNotSupported = true; - } - break; - case ValueKind.Boolean: - case ValueKind.Null: - case ValueKind.Number: - case ValueKind.Version: - kindNotSupported = true; - break; - } - - if (kindNotSupported) - { - throw new NotSupportedException(PipelineStrings.InvalidTypeForLengthFunction(evaluationResult.Kind)); - } - - return new Decimal(length); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/PipelineContextNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/PipelineContextNode.cs deleted file mode 100644 index 6e35657bf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/PipelineContextNode.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System; -using System.ComponentModel; -using System.Collections.Generic; -using GitHub.DistributedTask.Expressions; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - internal sealed class PipelineContextNode : NamedValueNode - { - protected override Object EvaluateCore(EvaluationContext context) - { - var state = context.State as IPipelineContext; - var result = new Dictionary(StringComparer.OrdinalIgnoreCase); - - // startTime - if (state.Variables.TryGetValue(WellKnownDistributedTaskVariables.PipelineStartTime, out VariableValue startTimeVariable) && - !String.IsNullOrEmpty(startTimeVariable.Value)) - { - // Leverage the expression SDK to convert to datetime - var startTimeResult = EvaluationResult.CreateIntermediateResult(context, startTimeVariable.Value, out _); - if (startTimeResult.TryConvertToDateTime(context, out DateTimeOffset startTime)) - { - result["startTime"] = startTime; - } - } - - return result; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Expressions/VariablesContextNode.cs b/src/Sdk/DTPipelines/Pipelines/Expressions/VariablesContextNode.cs deleted file mode 100644 index d548f5ab0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Expressions/VariablesContextNode.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; - -namespace GitHub.DistributedTask.Pipelines.Expressions -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class VariablesContextNode : NamedValueNode - { - protected override Object EvaluateCore(EvaluationContext context) - { - var executionContext = context.State as IPipelineContext; - return executionContext.Variables; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/GraphCondition.cs b/src/Sdk/DTPipelines/Pipelines/GraphCondition.cs deleted file mode 100644 index 06fd7409c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/GraphCondition.cs +++ /dev/null @@ -1,247 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Text; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Expressions2.Sdk; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.Pipelines.Expressions; -using GitHub.DistributedTask.Pipelines.ObjectTemplating; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class GraphCondition where TInstance : IGraphNodeInstance - { - private protected GraphCondition(String condition) - { - m_condition = !String.IsNullOrEmpty(condition) ? condition : Default; - m_parser = new ExpressionParser(); - m_parsedCondition = m_parser.CreateTree(m_condition, new ConditionTraceWriter(), s_namedValueInfo, FunctionInfo); - } - - /// - /// Gets the default condition if none is specified - /// - public static String Default - { - get - { - return $"{PipelineTemplateConstants.Success}()"; - } - } - - /// - /// Gets a value indicating whether the event payload is used within the condition - /// - public Boolean RequiresEventPayload - { - get - { - CheckRequiredProperties(); - return m_requiresEventPayload.Value; - } - } - - /// - /// Gets a value indicating whether dependency outputs are used within the condition - /// - public Boolean RequiresOutputs - { - get - { - CheckRequiredProperties(); - return m_requiresOutputs.Value; - } - } - - /// - /// Gets a value indicating whether variables are used within the condition - /// - public Boolean RequiresVariables - { - get - { - return false; - } - } - - private void CheckRequiredProperties() - { - var matches = m_parsedCondition.CheckReferencesContext(PipelineTemplateConstants.EventPattern, PipelineTemplateConstants.OutputsPattern); - m_requiresEventPayload = matches[0]; - m_requiresOutputs = matches[1]; - } - - private static IEnumerable GetNeeds( - IReadOnlyList parameters, - EvaluationContext context, - GraphExecutionContext expressionContext) - { - if (expressionContext.Data.TryGetValue(PipelineTemplateConstants.Needs, out var needsData) && - needsData is DictionaryContextData needs) - { - if (parameters.Count == 0) - { - foreach (var pair in needs) - { - yield return pair.Value as DictionaryContextData; - } - } - else - { - foreach (var parameter in parameters) - { - var parameterResult = parameter.Evaluate(context); - var dependencyName = default(String); - if (parameterResult.IsPrimitive) - { - dependencyName = parameterResult.ConvertToString(); - } - - if (!String.IsNullOrEmpty(dependencyName) && - needs.TryGetValue(dependencyName, out var need)) - { - yield return need as DictionaryContextData; - } - else - { - yield return default; - } - } - } - } - } - - private readonly String m_condition; - private readonly ExpressionParser m_parser; - private Boolean? m_requiresEventPayload; - private Boolean? m_requiresOutputs; - protected readonly IExpressionNode m_parsedCondition; - - private static readonly INamedValueInfo[] s_namedValueInfo = new INamedValueInfo[] - { - new NamedValueInfo>(PipelineTemplateConstants.GitHub), - new NamedValueInfo>(PipelineTemplateConstants.Needs), - }; - - public static readonly IFunctionInfo[] FunctionInfo = new IFunctionInfo[] - { - new FunctionInfo(PipelineTemplateConstants.Always, 0, 0), - new FunctionInfo(PipelineTemplateConstants.Failure, 0, Int32.MaxValue), - new FunctionInfo(PipelineTemplateConstants.Cancelled, 0, 0), - new FunctionInfo(PipelineTemplateConstants.Success, 0, Int32.MaxValue), - }; - - protected sealed class ConditionTraceWriter : ITraceWriter - { - public String Trace - { - get - { - return m_info.ToString(); - } - } - - public void Info(String message) - { - m_info.AppendLine(message); - } - - public void Verbose(String message) - { - // Not interested - } - - private StringBuilder m_info = new StringBuilder(); - } - - private sealed class AlwaysFunction : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - return true; - } - } - - private sealed class CancelledFunction : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var conditionContext = context.State as GraphExecutionContext; - return conditionContext.State == PipelineState.Canceling; - } - } - - private sealed class FailureFunction : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var conditionContext = context.State as GraphExecutionContext; - if (conditionContext.State != PipelineState.InProgress) - { - return false; - } - - Boolean anyFailed = false; - foreach (var need in GetNeeds(Parameters, context, conditionContext)) - { - if (need == null || - !need.TryGetValue(PipelineTemplateConstants.Result, out var resultData) || - !(resultData is StringContextData resultString)) - { - return false; - } - - if (String.Equals(resultString, PipelineTemplateConstants.Failure, StringComparison.OrdinalIgnoreCase)) - { - anyFailed = true; - break; - } - } - - return anyFailed; - } - } - - private sealed class SuccessFunction : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var conditionContext = context.State as GraphExecutionContext; - if (conditionContext.State != PipelineState.InProgress) - { - return false; - } - - Boolean allSucceeded = true; - foreach (var need in GetNeeds(Parameters, context, conditionContext)) - { - if (!allSucceeded || - need == null || - !need.TryGetValue(PipelineTemplateConstants.Result, out var resultData) || - !(resultData is StringContextData resultString) || - !String.Equals(resultString, PipelineTemplateConstants.Success, StringComparison.OrdinalIgnoreCase)) - { - return false; - } - } - - return true; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/GroupStep.cs b/src/Sdk/DTPipelines/Pipelines/GroupStep.cs deleted file mode 100644 index c66bc1a32..000000000 --- a/src/Sdk/DTPipelines/Pipelines/GroupStep.cs +++ /dev/null @@ -1,86 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class GroupStep : JobStep - { - [JsonConstructor] - public GroupStep() - { - } - - private GroupStep(GroupStep groupStepToClone) - : base(groupStepToClone) - { - if (groupStepToClone.m_steps?.Count > 0) - { - foreach (var step in groupStepToClone.m_steps) - { - this.Steps.Add(step.Clone() as TaskStep); - } - } - - if (groupStepToClone.m_outputs?.Count > 0) - { - this.m_outputs = new Dictionary(groupStepToClone.m_outputs, StringComparer.OrdinalIgnoreCase); - } - } - - public override StepType Type => StepType.Group; - - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - public IDictionary Outputs - { - get - { - if (m_outputs == null) - { - m_outputs = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_outputs; - } - } - - public override Step Clone() - { - return new GroupStep(this); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_steps?.Count == 0) - { - m_steps = null; - } - - if (m_outputs?.Count == 0) - { - m_outputs = null; - } - } - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private IList m_steps; - - [DataMember(Name = "Outputs", EmitDefaultValue = false)] - private IDictionary m_outputs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IAgentPoolResolver.cs b/src/Sdk/DTPipelines/Pipelines/IAgentPoolResolver.cs deleted file mode 100644 index 018605801..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IAgentPoolResolver.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism of resolving an AgentPoolReference to a TaskAgentPool. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IAgentPoolResolver - { - /// - /// Attempts to resolve the agent pool references to TaskAgentPool instances. - /// - /// The agent pools which should be resolved - /// A list containing the resolved agent pools - IList Resolve(ICollection references); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IAgentPoolResolverExtensions - { - /// - /// Attempts to resolve the agent pool reference to a TaskAgentPool. - /// - /// The agent pool which should be resolved - /// The agent pool if resolved; otherwise, null - public static TaskAgentPool Resolve( - this IAgentPoolResolver resolver, - AgentPoolReference reference) - { - return resolver.Resolve(new[] { reference }).FirstOrDefault(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IAgentPoolStore.cs b/src/Sdk/DTPipelines/Pipelines/IAgentPoolStore.cs deleted file mode 100644 index f6e6626f4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IAgentPoolStore.cs +++ /dev/null @@ -1,27 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IAgentPoolStore - { - /// - /// Adds a reference which should be considered authorized. Future - /// calls to retrieve this resource will be treated as pre-authorized regardless - /// of authorization context used. - /// - /// The pools which should be authorized - void Authorize(IList pools); - - IList GetAuthorizedReferences(); - - TaskAgentPool Get(AgentPoolReference reference); - - /// - /// Gets the IAgentPoolResolver used by this store, if any. - /// - IAgentPoolResolver Resolver { get; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IAgentQueueResolver.cs b/src/Sdk/DTPipelines/Pipelines/IAgentQueueResolver.cs deleted file mode 100644 index 14771855f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IAgentQueueResolver.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism of resolving an AgentQueueReference to a TaskAgentQueue. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IAgentQueueResolver - { - /// - /// Attempts to resolve the agent queue references to TaskAgentQueue instances. - /// - /// The agent queues which should be resolved - /// A list containing the resolved agent queues - IList Resolve(ICollection references); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IAgentQueueResolverExtensions - { - /// - /// Attempts to resolve the agent queue reference to a TaskAgentQueue. - /// - /// The agent queue which should be resolved - /// The agent queue if resolved; otherwise, null - public static TaskAgentQueue Resolve( - this IAgentQueueResolver resolver, - AgentQueueReference reference) - { - return resolver.Resolve(new[] { reference }).FirstOrDefault(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IAgentQueueStore.cs b/src/Sdk/DTPipelines/Pipelines/IAgentQueueStore.cs deleted file mode 100644 index 16d3f1e21..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IAgentQueueStore.cs +++ /dev/null @@ -1,27 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IAgentQueueStore - { - /// - /// Adds a reference which should be considered authorized. Future - /// calls to retrieve this resource will be treated as pre-authorized regardless - /// of authorization context used. - /// - /// The queue which should be authorized - void Authorize(IList queues); - - IList GetAuthorizedReferences(); - - TaskAgentQueue Get(AgentQueueReference reference); - - /// - /// Gets the IAgentQueueResolver used by this store, if any. - /// - IAgentQueueResolver Resolver { get; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ICounterResolver.cs b/src/Sdk/DTPipelines/Pipelines/ICounterResolver.cs deleted file mode 100644 index bd3e349ef..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ICounterResolver.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ICounterResolver - { - Int32 Increment(IPipelineContext context, String prefix, Int32 seed); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ICounterStore.cs b/src/Sdk/DTPipelines/Pipelines/ICounterStore.cs deleted file mode 100644 index cfaba4c3e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ICounterStore.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ICounterStore - { - /// - /// Gets the counters which are allocated for this store. - /// - IReadOnlyDictionary Counters { get; } - - /// - /// Increments the counter with the given prefix. If no such counter exists, a new one will be created with - /// as the initial value. - /// - /// The counter prefix - /// The initial value for the counter if the counter does not exist - /// The incremented value - Int32 Increment(IPipelineContext context, String prefix, Int32 seed); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IEnvironmentResolver.cs b/src/Sdk/DTPipelines/Pipelines/IEnvironmentResolver.cs deleted file mode 100644 index b0f58b1c5..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IEnvironmentResolver.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IEnvironmentResolver - { - EnvironmentInstance Resolve(String environmentName); - - EnvironmentInstance Resolve(Int32 environmentId); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IEnvironmentStore.cs b/src/Sdk/DTPipelines/Pipelines/IEnvironmentStore.cs deleted file mode 100644 index 942a08f1b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IEnvironmentStore.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a contract for resolving environment from a given store. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IEnvironmentStore - { - EnvironmentInstance ResolveEnvironment(String environmentName); - - EnvironmentInstance ResolveEnvironment(Int32 environmentId); - - EnvironmentInstance Get(EnvironmentReference reference); - - IList GetReferences(); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IGraphNode.cs b/src/Sdk/DTPipelines/Pipelines/IGraphNode.cs deleted file mode 100644 index 178041f86..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IGraphNode.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IGraphNode - { - String Name - { - get; - set; - } - - String DisplayName - { - get; - set; - } - - String Condition - { - get; - set; - } - - ISet DependsOn - { - get; - } - - void Validate(PipelineBuildContext context, ValidationResult result); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IGraphNodeInstance - { - Int32 Attempt { get; set; } - String Identifier { get; set; } - String Name { get; set; } - DateTime? StartTime { get; set; } - DateTime? FinishTime { get; set; } - TaskResult? Result { get; set; } - Boolean SecretsAccessed { get; } - IDictionary Outputs { get; } - void ResetSecretsAccessed(); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IJobFactory.cs b/src/Sdk/DTPipelines/Pipelines/IJobFactory.cs deleted file mode 100644 index edfe7050a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IJobFactory.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.Collections.Generic; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines -{ - internal interface IJobFactory - { - String Name { get; } - - Job CreateJob( - JobExecutionContext context, - ExpressionValue container, - IDictionary> sidecarContainers, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - String displayName = null); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IPackageStore.cs b/src/Sdk/DTPipelines/Pipelines/IPackageStore.cs deleted file mode 100644 index 4837420b4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IPackageStore.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IPackageStore - { - PackageVersion GetLatestVersion(String packageType); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IPhaseProvider.cs b/src/Sdk/DTPipelines/Pipelines/IPhaseProvider.cs deleted file mode 100644 index b306d20d4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IPhaseProvider.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// This is a temprary extension point for provider phase to participate in pipeline resource discover - /// This extension point can be removed after we have the schema driven resource discover - /// - public interface IPhaseProvider - { - String Provider { get; } - - /// - /// Validate pipeline with builder context to provide additional validation errors - /// and pipeline resource discover. - /// - ValidationResult Validate(PipelineBuildContext context, ProviderPhase phase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IPipelineContext.cs b/src/Sdk/DTPipelines/Pipelines/IPipelineContext.cs deleted file mode 100644 index 4ceb339cf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IPipelineContext.cs +++ /dev/null @@ -1,59 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Logging; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides the environment and services available during build and execution of a pipeline. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IPipelineContext - { - ICounterStore CounterStore { get; } - - DictionaryContextData Data { get; } - - Int32 EnvironmentVersion { get; } - - EvaluationOptions ExpressionOptions { get; } - - IPipelineIdGenerator IdGenerator { get; } - - IPackageStore PackageStore { get; } - - PipelineResources ReferencedResources { get; } - - IResourceStore ResourceStore { get; } - - IReadOnlyList StepProviders { get; } - - ISecretMasker SecretMasker { get; } - - ITaskStore TaskStore { get; } - - IPipelineTraceWriter Trace { get; } - - ISet SystemVariableNames { get; } - - IDictionary Variables { get; } - - String ExpandVariables(String value, Boolean maskSecrets = false); - - ExpressionResult Evaluate(String expression); - - ExpressionResult Evaluate(JObject value); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IPipelineTraceWriter : ITraceWriter - { - void EnterProperty(String name); - void LeaveProperty(String name); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IPipelineContextExtensions.cs b/src/Sdk/DTPipelines/Pipelines/IPipelineContextExtensions.cs deleted file mode 100644 index 4affd0923..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IPipelineContextExtensions.cs +++ /dev/null @@ -1,81 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IPipelineContextExtensions - { - /// - /// Uses the current context to validate the steps provided. - /// - /// The current pipeline context - /// The list of steps which should be validated - /// The options controlling the level of validation performed - /// A list of validation errors which were encountered, if any - public static IList Validate( - this IPipelineContext context, - IList steps, - PhaseTarget target, - BuildOptions options) - { - var builder = new PipelineBuilder(context); - return builder.Validate(steps, target, options); - } - - /// - /// Evaluates a property which is specified as an expression and writes the resulting value to the - /// corresponding trace log if one is specified on the context. - /// - /// The result type of the expression - /// The pipeline context - /// The name of the property being evaluated - /// The expression which should be evaluated - /// The default value if no expression is specified - /// True to write the default value if no expression is specified; otherwise, false - /// The result of the expression evaluation - internal static ExpressionResult Evaluate( - this IPipelineContext context, - String name, - ExpressionValue expression, - T defaultValue, - Boolean traceDefault = true) - { - ExpressionResult result = null; - if (expression != null) - { - if (expression.IsLiteral) - { - context.Trace?.Info($"{name}: {GetTraceValue(expression.Literal)}"); - result = new ExpressionResult(expression.Literal); - } - else - { - context.Trace?.EnterProperty(name); - result = expression.GetValue(context); - context.Trace?.LeaveProperty(name); - } - } - else if (traceDefault && context.Trace != null) - { - context.Trace.Info($"{name}: {defaultValue}"); - } - - return result ?? new ExpressionResult(defaultValue); - } - - private static String GetTraceValue(T value) - { - if (value.GetType().IsValueType) - { - return value.ToString(); - } - else - { - return $"{System.Environment.NewLine}{JsonUtility.ToString(value, indent: true)}"; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IPipelineIdGenerator.cs b/src/Sdk/DTPipelines/Pipelines/IPipelineIdGenerator.cs deleted file mode 100644 index bfb5ca8d4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IPipelineIdGenerator.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IPipelineIdGenerator - { - Guid GetInstanceId(params String[] segments); - - String GetInstanceName(params String[] segments); - - String GetStageIdentifier(String stageName); - - Guid GetStageInstanceId(String stageName, Int32 attempt); - - String GetStageInstanceName(String stageName, Int32 attempt); - - String GetPhaseIdentifier(String stageName, String phaseName); - - Guid GetPhaseInstanceId(String stageName, String phaseName, Int32 attempt); - - String GetPhaseInstanceName(String stageName, String phaseName, Int32 attempt); - - String GetJobIdentifier(String stageName, String phaseName, String jobName); - - Guid GetJobInstanceId(String stageName, String phaseName, String jobName, Int32 attempt); - - String GetJobInstanceName(String stageName, String phaseName, String jobName, Int32 attempt); - - Guid GetTaskInstanceId(String stageName, String phaseName, String jobName, Int32 jobAttempt, String name3); - - String GetTaskInstanceName(String stageName, String phaseName, String jobName, Int32 jobAttempt, String name); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IResourceStore.cs b/src/Sdk/DTPipelines/Pipelines/IResourceStore.cs deleted file mode 100644 index b85ce4933..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IResourceStore.cs +++ /dev/null @@ -1,87 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Artifacts; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - public interface IBuildStore : IStepProvider - { - void Add(BuildResource resource); - void Add(IEnumerable resources); - BuildResource Get(String alias); - IEnumerable GetAll(); - IArtifactResolver Resolver { get; } - } - - public interface IContainerStore - { - void Add(ContainerResource resource); - void Add(IEnumerable resources); - ContainerResource Get(String alias); - IEnumerable GetAll(); - } - - public interface IPipelineStore : IStepProvider - { - void Add(PipelineResource resource); - void Add(IEnumerable resources); - PipelineResource Get(String alias); - IEnumerable GetAll(); - } - - public interface IRepositoryStore : IStepProvider - { - void Add(RepositoryResource resource); - void Add(IEnumerable resources); - RepositoryResource Get(String alias); - IEnumerable GetAll(); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IResourceStore : IStepProvider - { - IBuildStore Builds { get; } - - IContainerStore Containers { get; } - - IServiceEndpointStore Endpoints { get; } - - ISecureFileStore Files { get; } - - IEnvironmentStore Environments { get; } - - IPipelineStore Pipelines { get; } - - IAgentQueueStore Queues { get; } - - IAgentPoolStore Pools { get; } - - IRepositoryStore Repositories { get; } - - IVariableGroupStore VariableGroups { get; } - - PipelineResources GetAuthorizedResources(); - - ServiceEndpoint GetEndpoint(Guid endpointId); - - ServiceEndpoint GetEndpoint(String endpointId); - - SecureFile GetFile(Guid fileId); - - SecureFile GetFile(String fileId); - - TaskAgentQueue GetQueue(Int32 queueId); - - TaskAgentQueue GetQueue(String queueId); - - TaskAgentPool GetPool(Int32 poolId); - - TaskAgentPool GetPool(String poolName); - - VariableGroup GetVariableGroup(Int32 groupId); - - VariableGroup GetVariableGroup(String groupId); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IResourceStoreExtensions.cs b/src/Sdk/DTPipelines/Pipelines/IResourceStoreExtensions.cs deleted file mode 100644 index 181edeb2a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IResourceStoreExtensions.cs +++ /dev/null @@ -1,198 +0,0 @@ -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IResourceStoreExtensions - { - /// - /// Extracts the full resources from the which are referenced in the - /// collection. - /// - /// The store which contains the resources - /// The resources which should be included with the job - /// A new JobResources instance with the filtered set of resources from the store - public static JobResources GetJobResources( - this IResourceStore store, - PipelineResources resources) - { - var jobResources = new JobResources(); - jobResources.Containers.AddRange(resources.Containers.Select(x => x.Clone())); - - foreach (var endpointRef in resources.Endpoints) - { - var endpoint = store.Endpoints.Get(endpointRef); - if (endpoint != null) - { - jobResources.Endpoints.Add(endpoint); - } - } - - foreach (var fileRef in resources.Files) - { - var file = store.Files.Get(fileRef); - if (file != null) - { - jobResources.SecureFiles.Add(file); - } - } - - foreach (var repository in resources.Repositories) - { - jobResources.Repositories.Add(store.Repositories.Get(repository.Alias)); - } - - return jobResources; - } - - /// - /// Retrieves a service endpoint from the store using the provided reference. - /// - /// The resource store which should be queried - /// The service endpoint reference which should be resolved - /// A ServiceEndpoint instance matching the specified reference if found; otherwise, null - public static ServiceEndpoint GetEndpoint( - this IResourceStore store, - ServiceEndpointReference reference) - { - return store.Endpoints.Get(reference); - } - - /// - /// Retrieves a secure file from the store using the provided reference. - /// - /// The resource store which should be queried - /// The secure file reference which should be resolved - /// A SecureFile instance matching the specified reference if found; otherwise, null - public static SecureFile GetFile( - this IResourceStore store, - SecureFileReference reference) - { - return store.Files.Get(reference); - } - - /// - /// Retrieves an agent queue from the store using the provided reference. - /// - /// The resource store which should be queried - /// The agent queue reference which should be resolved - /// A TaskAgentQueue instance matching the specified reference if found; otherwise, null - public static TaskAgentQueue GetQueue( - this IResourceStore store, - AgentQueueReference reference) - { - return store.Queues.Get(reference); - } - - /// - /// Retrieves an agent pool from the store using the provided reference. - /// - /// The resource store which should be queried - /// The agent pool reference which should be resolved - /// A TaskAgentPool instance matching the specified reference if found; otherwise, null - public static TaskAgentPool GetPool( - this IResourceStore store, - AgentPoolReference reference) - { - return store.Pools.Get(reference); - } - - /// - /// Retrieves a variable group from the store using the provided reference. - /// - /// The resource store which should be queried - /// The variable group reference which should be resolved - /// A VariableGroup instance matching the specified reference if found; otherwise, null - public static VariableGroup GetVariableGroup( - this IResourceStore store, - VariableGroupReference reference) - { - return store.VariableGroups.Get(reference); - } - - /// - /// Given a partially formed reference, returns the associated reference stored with the plan. - /// - public static ResourceReference GetSnappedReference( - this IResourceStore store, - ResourceReference r) - { - if (r is VariableGroupReference vgr) - { - var m = store.VariableGroups.Get(vgr); - if (m != null) - { - return new VariableGroupReference - { - Id = m.Id, - Name = m.Name - }; - } - } - else if (r is AgentQueueReference aqr) - { - var m = store.Queues.Get(aqr); - if (m != null) - { - return new AgentQueueReference - { - Id = m.Id, - Name = m.Name - }; - } - } - else if (r is AgentPoolReference apr) - { - var m = store.Pools.Get(apr); - if (m != null) - { - return new AgentPoolReference - { - Id = m.Id, - Name = m.Name - }; - } - } - else if (r is ServiceEndpointReference ser) - { - var m = store.Endpoints.Get(ser); - if (m != null) - { - return new ServiceEndpointReference - { - Id = m.Id, - Name = m.Name - }; - } - } - else if (r is SecureFileReference sfr) - { - var m = store.Files.Get(sfr); - if (m != null) - { - return new SecureFileReference - { - Id = m.Id, - Name = m.Name - }; - } - } - else if (r is EnvironmentReference er) - { - var m = store.Environments.Get(er); - if (m != null) - { - return new EnvironmentReference - { - Id = m.Id, - Name = m.Name - }; - } - } - - return r; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ISecureFileResolver.cs b/src/Sdk/DTPipelines/Pipelines/ISecureFileResolver.cs deleted file mode 100644 index be08e791e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ISecureFileResolver.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism of resolving an SecureFileReference to a SecureFile. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ISecureFileResolver - { - /// - /// Attempts to resolve secure file references to a SecureFile instances. - /// - /// The file references which should be resolved - /// The resolved secure files - IList Resolve(ICollection references); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class ISecureFileResolverExtensions - { - /// - /// Attempts to resolve the secure file reference to a SecureFile. - /// - /// The file reference which should be resolved - /// The secure file if resolved; otherwise, null - public static SecureFile Resolve( - this ISecureFileResolver resolver, - SecureFileReference reference) - { - return resolver.Resolve(new[] { reference }).FirstOrDefault(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ISecureFileStore.cs b/src/Sdk/DTPipelines/Pipelines/ISecureFileStore.cs deleted file mode 100644 index ea695805d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ISecureFileStore.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ISecureFileStore - { - IList GetAuthorizedReferences(); - - SecureFile Get(SecureFileReference reference); - - /// - /// Gets the ISecureFileResolver used by this store, if any. - /// - ISecureFileResolver Resolver { get; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IServiceEndpointResolver.cs b/src/Sdk/DTPipelines/Pipelines/IServiceEndpointResolver.cs deleted file mode 100644 index c8646f51b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IServiceEndpointResolver.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism of resolving an ServiceEndpointReference to a ServiceEndpoint. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IServiceEndpointResolver - { - /// - /// Adds the endpoint reference as authorized to ensure future retrievals of the endpoint - /// are allowed regardless of security context. - /// - /// The endpoint reference which should be considered authorized - void Authorize(ServiceEndpointReference reference); - - /// - /// Attempts to resolve endpoint references to ServiceEndpoint instances. - /// - /// The endpoint references which should be resolved - /// The resolved service endpoints - IList Resolve(ICollection references); - - IList GetAuthorizedReferences(); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IServiceEndpointResolverExtensions - { - /// - /// Attempts to resolve the endpoint reference to a ServiceEndpoint. - /// - /// The endpoint reference which should be resolved - /// The service endpoint if resolved; otherwise, null - public static ServiceEndpoint Resolve( - this IServiceEndpointResolver resolver, - ServiceEndpointReference reference) - { - return resolver.Resolve(new[] { reference }).FirstOrDefault(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IServiceEndpointStore.cs b/src/Sdk/DTPipelines/Pipelines/IServiceEndpointStore.cs deleted file mode 100644 index b72d7d95b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IServiceEndpointStore.cs +++ /dev/null @@ -1,39 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides access to service endpoints which are referenced within a pipeline. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IServiceEndpointStore - { - /// - /// Retrieves the list of all endpoints authorized for use in this store. - /// - /// The list of ServiceEndpointReference objects authorized for use - IList GetAuthorizedReferences(); - - /// - /// Adds an endpoint reference which should be considered authorized. Future - /// calls to retrieve this resource will be treated as pre-authorized regardless - /// of authorization context used. - /// - /// The endpoint which should be authorized - void Authorize(ServiceEndpointReference endpoint); - - /// - /// Attempts to authorize an endpoint for use. - /// - /// The endpoint reference to be resolved - /// The endpoint if found and authorized; otherwise, null - ServiceEndpoint Get(ServiceEndpointReference endpoint); - - /// - /// Gets the IServiceEndpointResolver used by this store, if any. - /// - IServiceEndpointResolver Resolver { get; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IStepProvider.cs b/src/Sdk/DTPipelines/Pipelines/IStepProvider.cs deleted file mode 100644 index 4358edd85..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IStepProvider.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Pipelines -{ - public interface IStepProvider - { - IList GetPreSteps(IPipelineContext context, IReadOnlyList steps); - Dictionary> GetPostTaskSteps(IPipelineContext context, IReadOnlyList steps); - IList GetPostSteps(IPipelineContext context, IReadOnlyList steps); - - /// - /// Given a JobStep (eg., download step) it will translate into corresndponding task steps - /// - /// - /// Input step to be resolved - /// Resolved output steps - /// true if this is resolved, false otherwise. Passing a powershell step to ResolveStep would return false - Boolean ResolveStep(IPipelineContext context, JobStep step, out IList resolvedSteps); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ITaskResolver.cs b/src/Sdk/DTPipelines/Pipelines/ITaskResolver.cs deleted file mode 100644 index 18bba5c67..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ITaskResolver.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ITaskResolver - { - TaskDefinition Resolve(Guid taskId, String versionSpec); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ITaskStore.cs b/src/Sdk/DTPipelines/Pipelines/ITaskStore.cs deleted file mode 100644 index 2afc0673c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ITaskStore.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a contract for resolving tasks from a given store. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ITaskStore - { - /// - /// Resolves a task from the store using the unqiue identifier and version. - /// - /// The unique identifier of the task - /// The version of the task which is desired - /// The closest matching task definition if found; otherwise, null - TaskDefinition ResolveTask(Guid taskId, String version); - - /// - /// Resolves a task from the store using the specified name and version. - /// - /// The name of the task - /// The version of the task which is desired - /// The closest matching task definition if found; otherwise, null - TaskDefinition ResolveTask(String name, String version); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ITaskTemplateResolver.cs b/src/Sdk/DTPipelines/Pipelines/ITaskTemplateResolver.cs deleted file mode 100644 index e9d8ce669..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ITaskTemplateResolver.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ITaskTemplateResolver - { - Boolean CanResolve(TaskTemplateReference template); - - IList ResolveTasks(TaskTemplateStep template); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ITaskTemplateStore.cs b/src/Sdk/DTPipelines/Pipelines/ITaskTemplateStore.cs deleted file mode 100644 index 75b1a994b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ITaskTemplateStore.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism for task templates to be resolved at build time. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ITaskTemplateStore - { - void AddProvider(ITaskTemplateResolver provider); - - IEnumerable ResolveTasks(TaskTemplateStep step); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IVariable.cs b/src/Sdk/DTPipelines/Pipelines/IVariable.cs deleted file mode 100644 index afa278990..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IVariable.cs +++ /dev/null @@ -1,88 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - public enum VariableType - { - Inline = 0, - Group = 1, - } - - [JsonConverter(typeof(VariableJsonConverter))] - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IVariable - { - VariableType Type { get; } - } - - internal class VariableJsonConverter : VssSecureJsonConverter - { - public VariableJsonConverter() - { - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(IVariable).IsAssignableFrom(objectType); - } - - public override Object ReadJson(JsonReader reader, Type objectType, Object existingValue, JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - var resultObj = JObject.Load(reader); - var variableType = VariableType.Inline; - if (resultObj.TryGetValue("type", StringComparison.OrdinalIgnoreCase, out var rawValue)) - { - if (rawValue.Type == JTokenType.Integer) - { - variableType = (VariableType)(Int32)rawValue; - } - if (rawValue.Type == JTokenType.String) - { - variableType = (VariableType)Enum.Parse(typeof(VariableType), (String)rawValue, true); - } - } - else if (resultObj.TryGetValue("id", StringComparison.OrdinalIgnoreCase, out _) || - resultObj.TryGetValue("groupType", StringComparison.OrdinalIgnoreCase, out _) || - resultObj.TryGetValue("secretStore", StringComparison.OrdinalIgnoreCase, out _)) - { - variableType = VariableType.Group; - } - - IVariable result = null; - switch (variableType) - { - case VariableType.Group: - result = new VariableGroupReference(); - break; - - default: - result = new Variable(); - break; - } - - using (var objectReader = resultObj.CreateReader()) - { - serializer.Populate(objectReader, result); - } - - return result; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IVariableGroupResolver.cs b/src/Sdk/DTPipelines/Pipelines/IVariableGroupResolver.cs deleted file mode 100644 index 3d41ada2d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IVariableGroupResolver.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism of resolving an VariableGroupReference to a VariableGroup. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IVariableGroupResolver - { - /// - /// Attempts to resolve variable group references to VariableGroup instances. - /// - /// The variable groups which should be resolved - /// The resolved variable groups - IList Resolve(ICollection references); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class IVariableGroupResolverExtensions - { - public static VariableGroup Resolve( - this IVariableGroupResolver resolver, - VariableGroupReference reference) - { - return resolver.Resolve(new[] { reference }).FirstOrDefault(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IVariableGroupStore.cs b/src/Sdk/DTPipelines/Pipelines/IVariableGroupStore.cs deleted file mode 100644 index c2f5272b9..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IVariableGroupStore.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IVariableGroupStore : IStepProvider - { - IList GetAuthorizedReferences(); - - VariableGroup Get(VariableGroupReference queue); - - IVariableValueProvider GetValueProvider(VariableGroupReference queue); - - /// - /// Gets the IVariableGroupsResolver used by this store, if any. - /// - IVariableGroupResolver Resolver { get; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/IVariableValueProvider.cs b/src/Sdk/DTPipelines/Pipelines/IVariableValueProvider.cs deleted file mode 100644 index 8cc315963..000000000 --- a/src/Sdk/DTPipelines/Pipelines/IVariableValueProvider.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IVariableValueProvider - { - String GroupType - { - get; - } - - Boolean ShouldGetValues(IPipelineContext context); - - IList GetSteps(IPipelineContext context, VariableGroupReference group, IEnumerable keys); - - IDictionary GetValues(VariableGroup group, ServiceEndpoint endpoint, IEnumerable keys, Boolean includeSecrets); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Job.cs b/src/Sdk/DTPipelines/Pipelines/Job.cs deleted file mode 100644 index aa389b1b8..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Job.cs +++ /dev/null @@ -1,291 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class Job - { - [JsonConstructor] - public Job() - { - } - - private Job(Job jobToCopy) - { - this.Id = jobToCopy.Id; - this.Name = jobToCopy.Name; - this.DisplayName = jobToCopy.DisplayName; - this.Container = jobToCopy.Container?.Clone(); - this.ServiceContainers = jobToCopy.ServiceContainers?.Clone(); - this.ContinueOnError = jobToCopy.ContinueOnError; - this.TimeoutInMinutes = jobToCopy.TimeoutInMinutes; - this.CancelTimeoutInMinutes = jobToCopy.CancelTimeoutInMinutes; - this.Workspace = jobToCopy.Workspace?.Clone(); - this.Target = jobToCopy.Target?.Clone(); - this.EnvironmentVariables = jobToCopy.EnvironmentVariables?.Clone(); - - if (jobToCopy.m_demands != null && jobToCopy.m_demands.Count > 0) - { - m_demands = new List(jobToCopy.m_demands.Select(x => x.Clone())); - } - - if (jobToCopy.m_steps != null && jobToCopy.m_steps.Count > 0) - { - m_steps = new List(jobToCopy.m_steps.Select(x => x.Clone() as JobStep)); - } - - if (jobToCopy.m_variables != null && jobToCopy.m_variables.Count > 0) - { - m_variables = new List(jobToCopy.m_variables); - } - - if (jobToCopy.m_sidecarContainers != null && jobToCopy.m_sidecarContainers.Count > 0) - { - m_sidecarContainers = new Dictionary(jobToCopy.m_sidecarContainers, StringComparer.OrdinalIgnoreCase); - } - } - - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String DisplayName - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken Container - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken ServiceContainers - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean ContinueOnError - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken EnvironmentVariables - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 TimeoutInMinutes - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 CancelTimeoutInMinutes - { - get; - set; - } - - public IList Demands - { - get - { - if (m_demands == null) - { - m_demands = new List(); - } - return m_demands; - } - } - - [DataMember(EmitDefaultValue = false)] - public IdentityRef ExecuteAs - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public WorkspaceOptions Workspace - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public PhaseTarget Target - { - get; - set; - } - - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - public IList Scopes - { - get - { - if (m_scopes == null) - { - m_scopes = new List(); - } - return m_scopes; - } - } - - public IDictionary SidecarContainers - { - get - { - if (m_sidecarContainers == null) - { - m_sidecarContainers = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_sidecarContainers; - } - } - - public IList Variables - { - get - { - if (m_variables == null) - { - m_variables = new List(); - } - return m_variables; - } - } - - public Job Clone() - { - return new Job(this); - } - - /// - /// Creates an instance of a task using the specified execution context. - /// - /// The job execution context - /// The name of the task in the steps list - /// - public CreateTaskResult CreateTask( - JobExecutionContext context, - String taskName) - { - ArgumentUtility.CheckStringForNullOrEmpty(taskName, nameof(taskName)); - - TaskDefinition definition = null; - var task = this.Steps.SingleOrDefault(x => taskName.Equals(x.Name, StringComparison.OrdinalIgnoreCase))?.Clone() as TaskStep; - if (task != null) - { - definition = context.TaskStore.ResolveTask(task.Reference.Id, task.Reference.Version); - foreach (var input in definition.Inputs.Where(x => x != null)) - { - var key = input.Name?.Trim() ?? String.Empty; - if (!String.IsNullOrEmpty(key)) - { - if (!task.Inputs.ContainsKey(key)) - { - task.Inputs[key] = input.DefaultValue?.Trim() ?? String.Empty; - } - } - } - - // Now expand any macros which appear in inputs - foreach (var input in task.Inputs.ToArray()) - { - task.Inputs[input.Key] = context.ExpandVariables(input.Value); - } - - // Set the system variables populated while running an individual task - context.Variables[WellKnownDistributedTaskVariables.TaskInstanceId] = task.Id.ToString("D"); - context.Variables[WellKnownDistributedTaskVariables.TaskDisplayName] = task.DisplayName ?? task.Name; - context.Variables[WellKnownDistributedTaskVariables.TaskInstanceName] = task.Name; - } - - return new CreateTaskResult(task, definition); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_demands?.Count == 0) - { - m_demands = null; - } - - if (m_steps?.Count == 0) - { - m_steps = null; - } - - if (m_scopes?.Count == 0) - { - m_scopes = null; - } - - if (m_variables?.Count == 0) - { - m_variables = null; - } - } - - [DataMember(Name = "Demands", EmitDefaultValue = false)] - private List m_demands; - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private List m_steps; - - [DataMember(Name = "Scopes", EmitDefaultValue = false)] - private List m_scopes; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private List m_variables; - - [DataMember(Name = "SidecarContainers", EmitDefaultValue = false)] - private IDictionary m_sidecarContainers; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/JobExpansionOptions.cs b/src/Sdk/DTPipelines/Pipelines/JobExpansionOptions.cs deleted file mode 100644 index 5277822c4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/JobExpansionOptions.cs +++ /dev/null @@ -1,106 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Pipelines -{ - public class JobExpansionOptions - { - public JobExpansionOptions(ICollection configurations) - { - AddConfigurations(configurations); - } - - internal JobExpansionOptions(IDictionary configurations) - { - UpdateConfigurations(configurations); - } - - internal JobExpansionOptions( - String configuration, - Int32 attemptNumber = NoSpecifiedAttemptNumber) - { - if (!String.IsNullOrEmpty(configuration)) - { - this.Configurations.Add(configuration, attemptNumber); - } - } - - /// - /// Specifies a filter for the expansion of specific Phase configurations. - /// The key is the configuration name, the value is the explicitly requested - /// attempt number. - /// If mapping is null, there is no filter and all configurations will be - /// produced. - /// - internal IDictionary Configurations - { - get - { - if (m_configurations == null) - { - m_configurations = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_configurations; - } - } - - public Boolean IsIncluded(String configuration) - { - return m_configurations == null || m_configurations.ContainsKey(configuration); - } - - /// - /// Add new configurations, with no specified custom attempt number - /// - public void AddConfigurations(ICollection configurations) - { - if (configurations == null) - { - return; - } - - var localConfigs = this.Configurations; - foreach (var c in configurations) - { - if (!localConfigs.ContainsKey(c)) - { - localConfigs[c] = NoSpecifiedAttemptNumber; - } - } - } - - /// - /// add (or replace) any configurations and their associated attempt numbers with new provided values. - /// - public void UpdateConfigurations(IDictionary configurations) - { - if (configurations == null) - { - return; - } - - var localConfigs = this.Configurations; - foreach (var pair in configurations) - { - localConfigs[pair.Key] = pair.Value; - } - } - - /// - /// returns custom attempt number or JobExpansionOptions.NoSpecifiedAttemptNumber if none specified. - /// - /// configuration or "job name" - public Int32 GetAttemptNumber(String configuration) - { - if (m_configurations != null && m_configurations.TryGetValue(configuration, out Int32 number)) - { - return number; - } - - return NoSpecifiedAttemptNumber; - } - - public const Int32 NoSpecifiedAttemptNumber = -1; - private Dictionary m_configurations; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/JobFactory.cs b/src/Sdk/DTPipelines/Pipelines/JobFactory.cs deleted file mode 100644 index 798547fbf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/JobFactory.cs +++ /dev/null @@ -1,480 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Globalization; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.Pipelines.ObjectTemplating; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class JobFactory : PhaseNode - { - public JobFactory() - { - } - - private JobFactory(JobFactory copy) - : base(copy) - { - if (copy.m_steps != null && copy.m_steps.Count > 0) - { - m_steps = new List(copy.m_steps.Select(x => x.Clone())); - } - } - - /// - /// Gets the phase type. - /// - [DataMember(EmitDefaultValue = false)] - public override PhaseType Type => PhaseType.JobFactory; - - public IList Scopes - { - get - { - if (m_scopes == null) - { - m_scopes = new List(); - } - return m_scopes; - } - } - - /// - /// Gets the list of steps associated with this phase. At runtime the steps will be used as a template for - /// the execution of a job. - /// - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken Strategy - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public ScalarToken JobDisplayName - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken JobTarget - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public ScalarToken JobTimeout - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public ScalarToken JobCancelTimeout - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken JobContainer - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken JobServiceContainers - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken EnvironmentVariables - { - get; - set; - } - - public void CheckExpandReferences( - out bool isEventReferenced, - out bool isOutputsReferenced) - { - isEventReferenced = false; - isOutputsReferenced = false; - var expressionTokens = Strategy.Traverse() - .Concat(JobDisplayName.Traverse()) - .Concat(JobTarget.Traverse()) - .Concat(JobTimeout.Traverse()) - .Concat(JobCancelTimeout.Traverse()) - .OfType() - .ToArray(); - var parser = new ExpressionParser(); - foreach (var expressionToken in expressionTokens) - { - var tree = parser.ValidateSyntax(expressionToken.Expression, null); - var isReferenced = tree.CheckReferencesContext( - PipelineTemplateConstants.EventPattern, - PipelineTemplateConstants.OutputsPattern); - if (!isEventReferenced) - { - isEventReferenced = isReferenced[0]; - } - - if (!isOutputsReferenced) - { - isOutputsReferenced = isReferenced[1]; - } - } - } - - public ExpandPhaseResult Expand( - PhaseExecutionContext context, - JobExpansionOptions options = null) - { - var result = new ExpandPhaseResult(); - - var trace = new JobFactoryTrace(context.Trace); - var schema = new PipelineTemplateSchemaFactory().CreateSchema(); - var templateEvaluator = new PipelineTemplateEvaluator(trace, schema); - - trace.Info("Evaluating strategy"); - var displayName = JobDisplayName is ExpressionToken ? null : DisplayName; - var strategy = templateEvaluator.EvaluateStrategy(Strategy, context.Data, displayName); - - foreach (var jobContext in ExpandContexts(context, options, strategy, trace, templateEvaluator)) - { - result.Jobs.Add(jobContext.Job); - } - - if (strategy.MaxParallel > 0) - { - result.MaxConcurrency = strategy.MaxParallel; - } - else - { - result.MaxConcurrency = result.Jobs.Count; - } - - result.FailFast = strategy.FailFast; - - return result; - } - - public IEnumerable ExpandContexts( - PhaseExecutionContext context, - JobExpansionOptions options = null, - StrategyResult strategy = null, - DistributedTask.ObjectTemplating.ITraceWriter trace = null, - PipelineTemplateEvaluator templateEvaluator = null) - { - if (trace == null) - { - trace = new JobFactoryTrace(context.Trace); - } - - if (templateEvaluator == null) - { - var schema = new PipelineTemplateSchemaFactory().CreateSchema(); - templateEvaluator = new PipelineTemplateEvaluator(trace, schema); - } - - // Strategy - if (strategy == null) - { - trace.Info("Evaluating strategy"); - var displayName = JobDisplayName is ExpressionToken ? null : DisplayName; - strategy = templateEvaluator.EvaluateStrategy(Strategy, context.Data, displayName); - } - - // Check max jobs - var maxJobs = context.ExecutionOptions.MaxJobExpansion ?? 100; - if (strategy.Configurations.Count > maxJobs) - { - throw new MaxJobExpansionException($"Strategy produced more than {maxJobs}"); - } - - // Create jobs - for (var i = 0; i < strategy.Configurations.Count; i++) - { - var configuration = strategy.Configurations[i]; - var jobName = configuration.Name; - var attempt = 1; - if (options?.Configurations.Count > 0) - { - if (!options.Configurations.TryGetValue(jobName, out attempt)) - { - continue; - } - } - - yield return CreateJob(trace, context, templateEvaluator, jobName, configuration.DisplayName, attempt, i + 1, strategy.Configurations.Count, configuration.ContextData); - } - } - - /// - /// Resolves external references and ensures the steps are compatible with the selected target. - /// - /// The validation context - public override void Validate( - PipelineBuildContext context, - ValidationResult result) - { - base.Validate(context, result); - - var phaseStepValidationResult = new Phase.StepValidationResult(); - - // Require the latest agent version. - if (context.BuildOptions.DemandLatestAgent) - { - var latestPackageVersion = context.PackageStore?.GetLatestVersion(WellKnownPackageTypes.Agent); - if (latestPackageVersion == null) - { - throw new NotSupportedException("Unable to determine the latest agent package version"); - } - - phaseStepValidationResult.MinAgentVersion = latestPackageVersion.ToString(); - } - - Phase.ValidateSteps(context, this, new AgentQueueTarget(), result, Steps, phaseStepValidationResult); - - // Resolve the target to ensure we have stable identifiers for the orchestration engine - // phase targets with expressions need to be evaluated against resolved job contexts. - bool validateTarget = false; - if (this.Target.Type == PhaseTargetType.Pool || this.Target.Type == PhaseTargetType.Server) - { - validateTarget = true; - } - else if (this.Target is AgentQueueTarget agentQueueTarget && agentQueueTarget.IsLiteral()) - { - validateTarget = true; - } - - if (validateTarget) - { - this.Target.Validate( - context, - context.BuildOptions, - result, - this.Steps, - phaseStepValidationResult.TaskDemands); - } - } - - private JobExecutionContext CreateJob( - DistributedTask.ObjectTemplating.ITraceWriter trace, - PhaseExecutionContext phaseContext, - PipelineTemplateEvaluator templateEvaluator, - String jobName, - String configurationDisplayName, - Int32 attempt, - Int32 positionInPhase, - Int32 totalJobsInPhase, - IDictionary contextData) - { - trace.Info($"Creating job '{jobName}'"); - var jobContext = new JobExecutionContext( - context: phaseContext, - job: new JobInstance(jobName, attempt), - variables: null, - positionInPhase: positionInPhase, - totalJobsInPhase: totalJobsInPhase, - data: contextData); - var job = new Job - { - Id = jobContext.GetInstanceId(), - Name = jobContext.Job.Name, - EnvironmentVariables = EnvironmentVariables, - Container = JobContainer, - ServiceContainers = JobServiceContainers, - }; - - if (JobDisplayName is ExpressionToken) - { - trace.Info("Evaluating display name"); - job.DisplayName = templateEvaluator.EvaluateJobDisplayName(JobDisplayName, jobContext.Data, DisplayName); - } - else if (!String.IsNullOrEmpty(configurationDisplayName)) - { - job.DisplayName = configurationDisplayName; - } - else - { - job.DisplayName = DisplayName; - } - - trace.Info("Evaluating timeout"); - job.TimeoutInMinutes = templateEvaluator.EvaluateJobTimeout(JobTimeout, jobContext.Data); - trace.Info("Evaluating cancel timeout"); - job.CancelTimeoutInMinutes = templateEvaluator.EvaluateJobCancelTimeout(JobCancelTimeout, jobContext.Data); - trace.Info("Evaluating target"); - job.Target = templateEvaluator.EvaluateJobTarget(JobTarget, jobContext.Data); - - jobContext.Job.Definition = job; - - // Resolve the pool by name - if (job.Target is AgentPoolTarget pool && - pool.Pool?.Id == 0 && - !String.IsNullOrEmpty(pool.Pool.Name?.Literal)) - { - var resolved = jobContext.ResourceStore.GetPool(pool.Pool.Name.Literal); - if (resolved != null) - { - pool.Pool = new AgentPoolReference { Id = resolved.Id, Name = resolved.Name }; - } - } - - // Resolve the queue by name - if (job.Target is AgentQueueTarget queue && - queue.Queue?.Id == 0 && - !String.IsNullOrEmpty(queue.Queue.Name?.Literal)) - { - var resolved = jobContext.ResourceStore.GetQueue(queue.Queue.Name.Literal); - if (resolved != null) - { - queue.Queue = new AgentQueueReference { Id = resolved.Id, Name = resolved.Name }; - } - } - - // Always add self - var self = jobContext.ResourceStore?.Repositories.Get(PipelineConstants.SelfAlias); - if (self == null) - { - throw new InvalidOperationException($"Repository '{PipelineConstants.SelfAlias}' not found"); - } - - jobContext.ReferencedResources.Repositories.Add(self); - - // Add the endpoint - if (self.Endpoint != null) - { - jobContext.ReferencedResources.AddEndpointReference(self.Endpoint); - var repositoryEndpoint = jobContext.ResourceStore?.GetEndpoint(self.Endpoint); - if (repositoryEndpoint == null) - { - throw new ResourceNotFoundException(PipelineStrings.ServiceEndpointNotFound(self.Endpoint)); - } - } - - // Update the execution context with the job-specific system variables - UpdateJobContextVariablesFromJob(jobContext, job); - - var steps = new List(); - var identifier = jobContext.GetInstanceName(); - foreach (var step in Steps) - { - if (step.Type == StepType.Action) - { - job.Steps.Add(Phase.CreateJobActionStep(jobContext, identifier, step as ActionStep)); - } - else - { - throw new NotSupportedException($"Unexpected step type '{step.Type}'"); - } - } - - foreach (var scope in Scopes) - { - job.Scopes.Add(scope); - } - - return jobContext; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_scopes?.Count == 0) - { - m_scopes = null; - } - - if (m_steps?.Count == 0) - { - m_steps = null; - } - } - - private sealed class JobFactoryTrace : DistributedTask.ObjectTemplating.ITraceWriter - { - public JobFactoryTrace(DistributedTask.Expressions2.ITraceWriter trace) - { - m_trace = trace; - } - - public void Error( - String message, - params Object[] args) - { - Info("##[error]", message, args); - } - - public void Info( - String message, - params Object[] args) - { - Info(String.Empty, message, args); - } - - public void Verbose( - String message, - params Object[] args) - { - Info("##[debug]", message, args); - } - - private void Info( - String prefix, - String message, - params Object[] args) - { - if (m_trace == null) - { - return; - } - - if (args?.Length > 0) - { - m_trace.Info(String.Format(CultureInfo.InvariantCulture, $"{prefix}{message}", args)); - } - else - { - m_trace.Info($"{prefix}{message}"); - } - } - - private DistributedTask.Expressions2.ITraceWriter m_trace; - } - - [DataMember(Name = "Scopes", EmitDefaultValue = false)] - private IList m_scopes; - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private IList m_steps; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/JobResources.cs b/src/Sdk/DTPipelines/Pipelines/JobResources.cs index 7136b0775..fc9ba7618 100644 --- a/src/Sdk/DTPipelines/Pipelines/JobResources.cs +++ b/src/Sdk/DTPipelines/Pipelines/JobResources.cs @@ -54,21 +54,6 @@ namespace GitHub.DistributedTask.Pipelines } } - /// - /// Gets the collection of secure files associated with the current job - /// - public List SecureFiles - { - get - { - if (m_secureFiles == null) - { - m_secureFiles = new List(); - } - return m_secureFiles; - } - } - [OnSerializing] private void OnSerializing(StreamingContext context) { @@ -86,11 +71,6 @@ namespace GitHub.DistributedTask.Pipelines { m_repositories = null; } - - if (m_secureFiles?.Count == 0) - { - m_secureFiles = null; - } } [DataMember(Name = "Containers", EmitDefaultValue = false)] @@ -101,8 +81,5 @@ namespace GitHub.DistributedTask.Pipelines [DataMember(Name = "Repositories", EmitDefaultValue = false)] private List m_repositories; - - [DataMember(Name = "SecureFiles", EmitDefaultValue = false)] - private List m_secureFiles; } } diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/GraphConditionNamedValue.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/GraphConditionNamedValue.cs deleted file mode 100644 index cccc24d1b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/GraphConditionNamedValue.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2.Sdk; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - /// - /// Named-value node used when evaluating graph-node conditions - /// - [EditorBrowsable(EditorBrowsableState.Never)] - internal sealed class GraphConditionNamedValue : NamedValue where TInstance : IGraphNodeInstance - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var graphContext = context.State as GraphExecutionContext; - graphContext.Data.TryGetValue(Name, out var result); - return result; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/IFileProvider.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/IFileProvider.cs deleted file mode 100644 index f086d2be8..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/IFileProvider.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IFileProvider - { - String GetFileContent(String path); - - String ResolvePath(String defaultRoot, String path); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/JobDisplayNameBuilder.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/JobDisplayNameBuilder.cs deleted file mode 100644 index 56b83a615..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/JobDisplayNameBuilder.cs +++ /dev/null @@ -1,59 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - internal sealed class JobDisplayNameBuilder - { - public JobDisplayNameBuilder(String jobFactoryDisplayName) - { - if (!String.IsNullOrEmpty(jobFactoryDisplayName)) - { - m_jobFactoryDisplayName = jobFactoryDisplayName; - m_segments = new List(); - } - } - - public void AppendSegment(String value) - { - if (String.IsNullOrEmpty(value) || m_segments == null) - { - return; - } - - m_segments.Add(value); - } - - public String Build() - { - if (String.IsNullOrEmpty(m_jobFactoryDisplayName)) - { - return null; - } - - var displayName = default(String); - if (m_segments.Count == 0) - { - displayName = m_jobFactoryDisplayName; - } - else - { - var joinedSegments = String.Join(", ", m_segments); - displayName = String.Format(CultureInfo.InvariantCulture, "{0} ({1})", m_jobFactoryDisplayName, joinedSegments); - } - - const Int32 maxDisplayNameLength = 100; - if (displayName.Length > maxDisplayNameLength) - { - displayName = displayName.Substring(0, maxDisplayNameLength - 3) + "..."; - } - - m_segments.Clear(); - return displayName; - } - - private readonly String m_jobFactoryDisplayName; - private readonly List m_segments; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/MatrixBuilder.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/MatrixBuilder.cs deleted file mode 100644 index a23feaab1..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/MatrixBuilder.cs +++ /dev/null @@ -1,445 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Expressions2.Sdk; -using GitHub.DistributedTask.ObjectTemplating; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.ContextData; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - internal sealed class MatrixBuilder - { - internal MatrixBuilder( - TemplateContext context, - String jobFactoryDisplayName) - { - m_context = context; - m_jobFactoryDisplayName = jobFactoryDisplayName; - } - - internal void AddVector( - String name, - SequenceToken vector) - { - m_vectors.Add(name, vector.ToContextData()); - } - - internal DictionaryContextData Vectors => m_vectors; - - internal void Exclude(SequenceToken exclude) - { - m_excludeSequence = exclude; - } - - internal void Include(SequenceToken include) - { - m_includeSequence = include; - } - - internal IEnumerable Build() - { - if (m_vectors.Count > 0) - { - // Parse includes/excludes - var include = new MatrixInclude(m_context, m_vectors, m_includeSequence); - var exclude = new MatrixExclude(m_context, m_vectors, m_excludeSequence); - - // Calculate the cross product size - var productSize = 1; - foreach (var vectorPair in m_vectors) - { - checked - { - var vector = vectorPair.Value.AssertArray("vector"); - productSize *= vector.Count; - } - } - - var nameBuilder = new ReferenceNameBuilder(); - var displayNameBuilder = new JobDisplayNameBuilder(m_jobFactoryDisplayName); - - // Cross product - for (var productIndex = 0; productIndex < productSize; productIndex++) - { - // Matrix - var matrix = new DictionaryContextData(); - var blockSize = productSize; - foreach (var vectorPair in m_vectors) - { - var vectorName = vectorPair.Key; - var vector = vectorPair.Value.AssertArray("vector"); - blockSize = blockSize / vector.Count; - var vectorIndex = (productIndex / blockSize) % vector.Count; - matrix.Add(vectorName, vector[vectorIndex]); - } - - // Exclude - if (exclude.Match(matrix)) - { - continue; - } - - // New configuration - var configuration = new StrategyConfiguration(); - m_context.Memory.AddBytes(TemplateMemory.MinObjectSize); - - // Gather segments for name and display name - foreach (var matrixData in matrix.Traverse(omitKeys: true)) - { - var segment = default(String); - switch (matrixData?.Type) - { - case PipelineContextDataType.Boolean: - case PipelineContextDataType.Number: - case PipelineContextDataType.String: - segment = matrixData.ToString(); - break; - } - - if (!String.IsNullOrEmpty(segment)) - { - // Name segment - nameBuilder.AppendSegment(segment); - - // Display name segment - displayNameBuilder.AppendSegment(segment); - } - } - - // Name - configuration.Name = nameBuilder.Build(); - m_context.Memory.AddBytes(configuration.Name); - - // Display name - configuration.DisplayName = displayNameBuilder.Build(); - m_context.Memory.AddBytes(configuration.DisplayName); - - // Include - if (include.Match(matrix, out var extra)) - { - matrix.Add(extra); - } - - // Matrix context - configuration.ContextData.Add(PipelineTemplateConstants.Matrix, matrix); - m_context.Memory.AddBytes(PipelineTemplateConstants.Matrix); - m_context.Memory.AddBytes(matrix, traverse: true); - - // Add configuration - yield return configuration; - } - } - } - - private sealed class MatrixInclude - { - public MatrixInclude( - TemplateContext context, - DictionaryContextData vectors, - SequenceToken includeSequence) - { - // Convert to excludes sets - if (includeSequence?.Count > 0) - { - foreach (var includeItem in includeSequence) - { - var includeMapping = includeItem.AssertMapping("matrix includes item"); - - // Distinguish filters versus extra - var filter = new MappingToken(null, null, null); - var extra = new DictionaryContextData(); - foreach (var includePair in includeMapping) - { - var includeKeyLiteral = includePair.Key.AssertString("matrix include item key"); - if (vectors.ContainsKey(includeKeyLiteral.Value)) - { - filter.Add(includeKeyLiteral, includePair.Value); - } - else - { - extra.Add(includeKeyLiteral.Value, includePair.Value.ToContextData()); - } - } - - // At least one filter - if (filter.Count == 0) - { - context.Error(includeMapping, $"Matrix include mapping does not contain any filters"); - continue; - } - - // At least one extra - if (extra.Count == 0) - { - context.Error(includeMapping, $"Matrix include mapping does not contain any extra values to include"); - continue; - } - - // Add filter - m_filters.Add(new MatrixIncludeFilter(filter, extra)); - } - } - } - - public Boolean Match( - DictionaryContextData matrix, - out DictionaryContextData extra) - { - extra = default(DictionaryContextData); - foreach (var filter in m_filters) - { - if (filter.Match(matrix, out var items)) - { - if (extra == null) - { - extra = new DictionaryContextData(); - } - - foreach (var pair in items) - { - extra[pair.Key] = pair.Value; - } - } - } - - return extra != null; - } - - private readonly List m_filters = new List(); - } - - private sealed class MatrixIncludeFilter : MatrixFilter - { - public MatrixIncludeFilter( - MappingToken filter, - DictionaryContextData extra) - : base(filter) - { - m_extra = extra; - } - - public Boolean Match( - DictionaryContextData matrix, - out DictionaryContextData extra) - { - if (base.Match(matrix)) - { - extra = m_extra; - return true; - } - - extra = null; - return false; - } - - private readonly DictionaryContextData m_extra; - } - - private sealed class MatrixExclude - { - public MatrixExclude( - TemplateContext context, - DictionaryContextData vectors, - SequenceToken excludeSequence) - { - // Convert to excludes sets - if (excludeSequence?.Count > 0) - { - foreach (var excludeItem in excludeSequence) - { - var excludeMapping = excludeItem.AssertMapping("matrix excludes item"); - - // Check empty - if (excludeMapping.Count == 0) - { - context.Error(excludeMapping, $"Matrix exclude filter must not be empty"); - continue; - } - - // Validate first-level keys - foreach (var excludePair in excludeMapping) - { - var excludeKey = excludePair.Key.AssertString("matrix excludes item key"); - if (!vectors.ContainsKey(excludeKey.Value)) - { - context.Error(excludeKey, $"Matrix exclude key '{excludeKey.Value}' does not match any key within the matrix"); - continue; - } - } - - // Add filter - m_filters.Add(new MatrixExcludeFilter(excludeMapping)); - } - } - } - - public Boolean Match(DictionaryContextData matrix) - { - foreach (var filter in m_filters) - { - if (filter.Match(matrix)) - { - return true; - } - } - - return false; - } - - private readonly List m_filters = new List(); - } - - private sealed class MatrixExcludeFilter : MatrixFilter - { - public MatrixExcludeFilter(MappingToken filter) - : base(filter) - { - } - - public new Boolean Match(DictionaryContextData matrix) - { - return base.Match(matrix); - } - } - - private abstract class MatrixFilter - { - protected MatrixFilter(MappingToken matrixFilter) - { - var state = new MappingState(null, matrixFilter); - while (state != null) - { - if (state.MoveNext()) - { - var value = state.Mapping[state.Index].Value; - if (value is LiteralToken literal) - { - AddExpression(state, literal); - } - else - { - var mapping = state.Mapping[state.Index].Value.AssertMapping("matrix filter"); - state = new MappingState(state, mapping); - } - } - else - { - state = state.Parent; - } - } - } - - protected Boolean Match(DictionaryContextData matrix) - { - if (matrix.Count == 0) - { - throw new InvalidOperationException("Matrix filter cannot be empty"); - } - - foreach (var expression in m_expressions) - { - var result = expression.Evaluate(null, null, matrix, null); - if (result.IsFalsy) - { - return false; - } - } - - return true; - } - - private void AddExpression( - MappingState state, - LiteralToken literal) - { - var expressionLiteral = default(String); - switch (literal.Type) - { - case TokenType.Null: - expressionLiteral = ExpressionConstants.Null; - break; - - case TokenType.Boolean: - var booleanToken = literal as BooleanToken; - expressionLiteral = booleanToken.Value ? ExpressionConstants.True : ExpressionConstants.False; - break; - - case TokenType.Number: - var numberToken = literal as NumberToken; - expressionLiteral = String.Format(CultureInfo.InvariantCulture, ExpressionConstants.NumberFormat, numberToken.Value); - break; - - case TokenType.String: - var stringToken = literal as StringToken; - expressionLiteral = $"'{ExpressionUtility.StringEscape(stringToken.Value)}'"; - break; - - default: - throw new NotSupportedException($"Unexpected literal type '{literal.Type}'"); - } - - var str = $"{state.Path} == {expressionLiteral}"; - var parser = new ExpressionParser(); - var expression = parser.CreateTree(str, null, s_matrixFilterNamedValues, null); - m_expressions.Add(expression); - } - - private static readonly INamedValueInfo[] s_matrixFilterNamedValues = new INamedValueInfo[] - { - new NamedValueInfo(PipelineTemplateConstants.Matrix), - }; - private readonly List m_expressions = new List(); - } - - private sealed class MappingState - { - public MappingState( - MappingState parent, - MappingToken mapping) - { - Parent = parent; - Mapping = mapping; - Index = -1; - } - - public Boolean MoveNext() - { - if (++Index < Mapping.Count) - { - var keyLiteral = Mapping[Index].Key.AssertString("matrix filter key"); - var parentPath = Parent?.Path ?? PipelineTemplateConstants.Matrix; - Path = $"{parentPath}['{ExpressionUtility.StringEscape(keyLiteral.Value)}']"; - return true; - } - else - { - return false; - } - } - - public MappingState Parent; - public MappingToken Mapping; - public Int32 Index; - public String Path; - } - - private sealed class MatrixNamedValue : NamedValue - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - return context.State; - } - } - - private readonly TemplateContext m_context; - private readonly String m_jobFactoryDisplayName; - private readonly DictionaryContextData m_vectors = new DictionaryContextData(); - private SequenceToken m_excludeSequence; - private SequenceToken m_includeSequence; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseOptions.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseOptions.cs deleted file mode 100644 index 4ea8bf2b6..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseOptions.cs +++ /dev/null @@ -1,45 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Reflection; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ParseOptions - { - public ParseOptions() - { - } - - internal ParseOptions(ParseOptions copy) - { - MaxFiles = copy.MaxFiles; - MaxFileSize = copy.MaxFileSize; - MaxResultSize = copy.MaxResultSize; - } - - public Int32 MaxDepth => 50; - - /// - /// Gets the maximum error message length before the message will be truncated. - /// - public Int32 MaxErrorMessageLength => 500; - - /// - /// Gets the maximum number of errors that can be recorded when parsing a pipeline. - /// - public Int32 MaxErrors => 10; - - /// - /// Gets or sets the maximum number of files that can be loaded when parsing a pipeline. Zero or less is treated as infinite. - /// - public Int32 MaxFiles { get; set; } = 50; - - public Int32 MaxFileSize { get; set; } = 1024 * 1024; // 1 mb - - public Int32 MaxParseEvents => 1000000; // 1 million - - public Int32 MaxResultSize { get; set; } = 10 * 1024 * 1024; // 10 mb - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseResult.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseResult.cs deleted file mode 100644 index b23b9c07a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ParseResult.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.IO; -using GitHub.DistributedTask.ObjectTemplating; -using GitHub.DistributedTask.ObjectTemplating.Tokens; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - internal sealed class ParseResult - { - public TemplateContext Context { get; set; } - - public TemplateToken Value { get; set; } - - public String ToYaml() - { - if (Value == null) - { - return null; - } - - // Serialize - using (var stringWriter = new StringWriter()) - { - TemplateWriter.Write(new YamlObjectWriter(stringWriter), Value); - stringWriter.Flush(); - return stringWriter.ToString(); - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateConverter.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateConverter.cs index 45f6dc697..e76c08aa6 100644 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateConverter.cs +++ b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateConverter.cs @@ -16,180 +16,6 @@ namespace GitHub.DistributedTask.Pipelines.ObjectTemplating { internal static class PipelineTemplateConverter { - internal static PipelineTemplate ConvertToPipeline( - TemplateContext context, - RepositoryResource self, - TemplateToken pipeline) - { - var result = new PipelineTemplate(); - result.Resources.Repositories.Add(self); - var defaultStage = new Stage - { - Name = PipelineConstants.DefaultJobName, - }; - result.Stages.Add(defaultStage); - - try - { - if (pipeline == null || context.Errors.Count > 0) - { - return result; - } - - var pipelineMapping = pipeline.AssertMapping("root"); - - foreach (var pipelinePair in pipelineMapping) - { - var pipelineKey = pipelinePair.Key.AssertString("root key"); - - switch (pipelineKey.Value) - { - case PipelineTemplateConstants.On: - break; - - case PipelineTemplateConstants.Name: - break; - - case PipelineTemplateConstants.Env: - result.EnvironmentVariables = pipelinePair.Value; - break; - - case PipelineTemplateConstants.Jobs: - defaultStage.Phases.AddRange(ConvertToJobFactories(context, result.Resources, pipelinePair.Value)); - break; - - default: - pipelineKey.AssertUnexpectedValue("root key"); // throws - break; - } - } - } - catch (Exception ex) - { - context.Errors.Add(ex); - } - finally - { - if (context.Errors.Count > 0) - { - foreach (var error in context.Errors) - { - result.Errors.Add(new PipelineValidationError(error.Code, error.Message)); - } - } - } - - return result; - } - - internal static String ConvertToJobDisplayName( - TemplateContext context, - TemplateToken displayName, - Boolean allowExpressions = false) - { - var result = default(String); - - // Expression - if (allowExpressions && displayName is ExpressionToken) - { - return result; - } - - // String - var displayNameString = displayName.AssertString($"job {PipelineTemplateConstants.Name}"); - result = displayNameString.Value; - return result; - } - - internal static PhaseTarget ConvertToJobTarget( - TemplateContext context, - TemplateToken runsOn, - Boolean allowExpressions = false) - { - var result = new AgentPoolTarget(); - - // Expression - if (allowExpressions && runsOn is ExpressionToken) - { - return result; - } - - // String - if (runsOn is StringToken runsOnString) - { - result.Pool = new AgentPoolReference { Name = "GitHub Actions" }; - result.AgentSpecification = new JObject - { - { PipelineTemplateConstants.VmImage, runsOnString.Value } - }; - } - // Mapping - else - { - var runsOnMapping = runsOn.AssertMapping($"job {PipelineTemplateConstants.RunsOn}"); - foreach (var runsOnProperty in runsOnMapping) - { - // Expression - if (allowExpressions && runsOnProperty.Key is ExpressionToken) - { - continue; - } - - // String - var propertyName = runsOnProperty.Key.AssertString($"job {PipelineTemplateConstants.RunsOn} key"); - - switch (propertyName.Value) - { - case PipelineTemplateConstants.Pool: - // Expression - if (allowExpressions && runsOnProperty.Value is ExpressionToken) - { - continue; - } - - // Literal - var pool = runsOnProperty.Value.AssertString($"job {PipelineTemplateConstants.RunsOn} key"); - result.Pool = new AgentPoolReference { Name = pool.Value }; - break; - - default: - propertyName.AssertUnexpectedValue($"job {PipelineTemplateConstants.RunsOn} key"); // throws - break; - } - } - } - - return result; - } - - internal static Int32? ConvertToJobTimeout( - TemplateContext context, - TemplateToken token, - Boolean allowExpressions = false) - { - if (allowExpressions && token is ExpressionToken) - { - return null; - } - - var numberToken = token.AssertNumber($"job {PipelineTemplateConstants.TimeoutMinutes}"); - return (Int32)numberToken.Value; - } - - internal static Int32? ConvertToJobCancelTimeout( - TemplateContext context, - TemplateToken token, - Boolean allowExpressions = false) - { - if (allowExpressions && token is ExpressionToken) - { - return null; - } - - var numberToken = token.AssertNumber($"job {PipelineTemplateConstants.CancelTimeoutMinutes}"); - return (Int32)numberToken.Value; - } - internal static Boolean? ConvertToStepContinueOnError( TemplateContext context, TemplateToken token, @@ -315,203 +141,6 @@ namespace GitHub.DistributedTask.Pipelines.ObjectTemplating return (Int32)numberToken.Value; } - internal static StrategyResult ConvertToStrategy( - TemplateContext context, - TemplateToken token, - String jobFactoryDisplayName, - Boolean allowExpressions = false) - { - var result = new StrategyResult(); - - // Expression - if (allowExpressions && token is ExpressionToken) - { - return result; - } - - var strategyMapping = token.AssertMapping(PipelineTemplateConstants.Strategy); - var matrixBuilder = default(MatrixBuilder); - var hasExpressions = false; - - foreach (var strategyPair in strategyMapping) - { - // Expression key - if (allowExpressions && strategyPair.Key is ExpressionToken) - { - hasExpressions = true; - continue; - } - - // Literal key - var strategyKey = strategyPair.Key.AssertString("strategy key"); - - switch (strategyKey.Value) - { - // Fail-Fast - case PipelineTemplateConstants.FailFast: - if (allowExpressions && strategyPair.Value is ExpressionToken) - { - hasExpressions = true; - continue; - } - - var failFastBooleanToken = strategyPair.Value.AssertBoolean($"strategy {PipelineTemplateConstants.FailFast}"); - result.FailFast = failFastBooleanToken.Value; - break; - - // Max-Parallel - case PipelineTemplateConstants.MaxParallel: - if (allowExpressions && strategyPair.Value is ExpressionToken) - { - hasExpressions = true; - continue; - } - - var maxParallelNumberToken = strategyPair.Value.AssertNumber($"strategy {PipelineTemplateConstants.MaxParallel}"); - result.MaxParallel = (Int32)maxParallelNumberToken.Value; - break; - - // Matrix - case PipelineTemplateConstants.Matrix: - - // Expression - if (allowExpressions && strategyPair.Value is ExpressionToken) - { - hasExpressions = true; - continue; - } - - var matrix = strategyPair.Value.AssertMapping("matrix"); - hasExpressions = hasExpressions || matrix.Traverse().Any(x => x is ExpressionToken); - matrixBuilder = new MatrixBuilder(context, jobFactoryDisplayName); - var hasVector = false; - - foreach (var matrixPair in matrix) - { - // Expression key - if (allowExpressions && matrixPair.Key is ExpressionToken) - { - hasVector = true; // For validation, treat as if a vector is defined - continue; - } - - var matrixKey = matrixPair.Key.AssertString("matrix key"); - switch (matrixKey.Value) - { - case PipelineTemplateConstants.Include: - if (allowExpressions && matrixPair.Value is ExpressionToken) - { - continue; - } - - var includeSequence = matrixPair.Value.AssertSequence("matrix includes"); - matrixBuilder.Include(includeSequence); - break; - - case PipelineTemplateConstants.Exclude: - if (allowExpressions && matrixPair.Value is ExpressionToken) - { - continue; - } - - var excludeSequence = matrixPair.Value.AssertSequence("matrix excludes"); - matrixBuilder.Exclude(excludeSequence); - break; - - default: - hasVector = true; - - if (allowExpressions && matrixPair.Value is ExpressionToken) - { - continue; - } - - var vectorName = matrixKey.Value; - var vectorSequence = matrixPair.Value.AssertSequence("matrix vector value"); - if (vectorSequence.Count == 0) - { - context.Error(vectorSequence, $"Matrix vector '{vectorName}' does not contain any values"); - } - else - { - matrixBuilder.AddVector(vectorName, vectorSequence); - } - break; - } - } - - if (!hasVector) - { - context.Error(matrix, $"Matrix must defined at least one vector"); - } - - break; - - default: - strategyKey.AssertUnexpectedValue("strategy key"); // throws - break; - } - } - - if (hasExpressions) - { - return result; - } - - if (matrixBuilder != null) - { - result.Configurations.AddRange(matrixBuilder.Build()); - } - - for (var i = 0; i < result.Configurations.Count; i++) - { - var configuration = result.Configurations[i]; - - var strategy = new DictionaryContextData() - { - { - "fail-fast", - new BooleanContextData(result.FailFast) - }, - { - "job-index", - new NumberContextData(i) - }, - { - "job-total", - new NumberContextData(result.Configurations.Count) - } - }; - - if (result.MaxParallel > 0) - { - strategy.Add( - "max-parallel", - new NumberContextData(result.MaxParallel) - ); - } - else - { - strategy.Add( - "max-parallel", - new NumberContextData(result.Configurations.Count) - ); - } - - configuration.ContextData.Add(PipelineTemplateConstants.Strategy, strategy); - context.Memory.AddBytes(PipelineTemplateConstants.Strategy); - context.Memory.AddBytes(strategy, traverse: true); - - if (!configuration.ContextData.ContainsKey(PipelineTemplateConstants.Matrix)) - { - configuration.ContextData.Add(PipelineTemplateConstants.Matrix, null); - context.Memory.AddBytes(PipelineTemplateConstants.Matrix); - } - } - - return result; - } - internal static JobContainer ConvertToJobContainer( TemplateContext context, TemplateToken value, @@ -616,532 +245,5 @@ namespace GitHub.DistributedTask.Pipelines.ObjectTemplating return result; } - - private static IEnumerable ConvertToJobFactories( - TemplateContext context, - PipelineResources resources, - TemplateToken workflow) - { - var jobsMapping = workflow.AssertMapping(PipelineTemplateConstants.Jobs); - - foreach (var jobsPair in jobsMapping) - { - var jobNameToken = jobsPair.Key.AssertString($"{PipelineTemplateConstants.Jobs} key"); - if (!NameValidation.IsValid(jobNameToken.Value, true)) - { - context.Error(jobNameToken, $"Job name {jobNameToken.Value} is invalid. Names must start with a letter or '_' and contain only alphanumeric characters, '-', or '_'"); - } - var result = new JobFactory - { - Name = jobNameToken.Value - }; - - var jobFactoryDefinition = jobsPair.Value.AssertMapping($"{PipelineTemplateConstants.Jobs} value"); - - foreach (var jobFactoryProperty in jobFactoryDefinition) - { - var propertyName = jobFactoryProperty.Key.AssertString($"job property name"); - - switch (propertyName.Value) - { - case PipelineTemplateConstants.ContinueOnError: - var continueOnErrorBooleanToken = jobFactoryProperty.Value.AssertBoolean($"job {PipelineTemplateConstants.ContinueOnError}"); - result.ContinueOnError = continueOnErrorBooleanToken.Value; - break; - - case PipelineTemplateConstants.If: - var ifCondition = jobFactoryProperty.Value.AssertString($"job {PipelineTemplateConstants.If}"); - result.Condition = ConvertToIfCondition(context, ifCondition, true, true); - break; - - case PipelineTemplateConstants.Name: - var displayName = jobFactoryProperty.Value.AssertScalar($"job {PipelineTemplateConstants.Name}"); - ConvertToJobDisplayName(context, displayName, allowExpressions: true); // Validate early if possible - if (displayName is StringToken) - { - result.DisplayName = displayName.ToString(); - } - else - { - result.JobDisplayName = displayName.Clone(true) as ExpressionToken; - } - break; - - case PipelineTemplateConstants.Needs: - if (jobFactoryProperty.Value is StringToken needsLiteral) - { - result.DependsOn.Add(needsLiteral.Value); - } - else - { - var needs = jobFactoryProperty.Value.AssertSequence($"job {PipelineTemplateConstants.Needs}"); - foreach (var needsItem in needs) - { - var need = needsItem.AssertString($"job {PipelineTemplateConstants.Needs} item"); - result.DependsOn.Add(need.Value); - } - } - break; - - case PipelineTemplateConstants.RunsOn: - ConvertToJobTarget(context, jobFactoryProperty.Value, allowExpressions: true); // Validate early if possible - result.JobTarget = jobFactoryProperty.Value.Clone(true); - break; - - case PipelineTemplateConstants.Scopes: - foreach (var scope in ConvertToScopes(context, jobFactoryProperty.Value)) - { - result.Scopes.Add(scope); - } - break; - - case PipelineTemplateConstants.Steps: - result.Steps.AddRange(ConvertToSteps(context, jobFactoryProperty.Value)); - break; - - case PipelineTemplateConstants.Strategy: - ConvertToStrategy(context, jobFactoryProperty.Value, null, allowExpressions: true); // Validate early if possible - result.Strategy = jobFactoryProperty.Value.Clone(true); - break; - - case PipelineTemplateConstants.TimeoutMinutes: - ConvertToJobTimeout(context, jobFactoryProperty.Value, allowExpressions: true); // Validate early if possible - result.JobTimeout = jobFactoryProperty.Value.Clone(true) as ScalarToken; - break; - - case PipelineTemplateConstants.CancelTimeoutMinutes: - ConvertToJobCancelTimeout(context, jobFactoryProperty.Value, allowExpressions: true); // Validate early if possible - result.JobCancelTimeout = jobFactoryProperty.Value.Clone(true) as ScalarToken; - break; - - case PipelineTemplateConstants.Container: - ConvertToJobContainer(context, jobFactoryProperty.Value, allowExpressions: true); - result.JobContainer = jobFactoryProperty.Value.Clone(true); - break; - - case PipelineTemplateConstants.Services: - ConvertToJobServiceContainers(context, jobFactoryProperty.Value, allowExpressions: true); - result.JobServiceContainers = jobFactoryProperty.Value.Clone(true); - break; - - case PipelineTemplateConstants.Env: - result.EnvironmentVariables = jobFactoryProperty.Value.Clone(true); - break; - - default: - propertyName.AssertUnexpectedValue("job key"); // throws - break; - } - } - - // todo: Move "required" support into schema validation - if (result.JobTarget == null) - { - context.Error(jobFactoryDefinition, $"The '{PipelineTemplateConstants.RunsOn}' property is required"); - } - - if (String.IsNullOrEmpty(result.DisplayName)) - { - result.DisplayName = result.Name; - } - - if (result.Scopes.Count > 0) - { - result.Steps.Insert( - 0, - new ActionStep - { - Reference = new ScriptReference(), - DisplayName = "WARNING: TEMPLATES ARE HIGHLY EXPERIMENTAL", - Inputs = new MappingToken(null, null, null) - { - { - new StringToken(null, null, null, PipelineConstants.ScriptStepInputs.Script), - new StringToken(null, null, null, "echo WARNING: TEMPLATES ARE HIGHLY EXPERIMENTAL") - } - } - }); - result.Steps.Add( - new ActionStep - { - Reference = new ScriptReference(), - DisplayName = "WARNING: TEMPLATES ARE HIGHLY EXPERIMENTAL", - Inputs = new MappingToken(null, null, null) - { - { - new StringToken(null, null, null, PipelineConstants.ScriptStepInputs.Script), - new StringToken(null, null, null, "echo WARNING: TEMPLATES ARE HIGHLY EXPERIMENTAL") - } - } - }); - } - - yield return result; - } - } - - private static IEnumerable ConvertToScopes( - TemplateContext context, - TemplateToken scopes) - { - var scopesSequence = scopes.AssertSequence($"job {PipelineTemplateConstants.Scopes}"); - - foreach (var scopesItem in scopesSequence) - { - var result = new ContextScope(); - var scope = scopesItem.AssertMapping($"{PipelineTemplateConstants.Scopes} item"); - - foreach (var scopeProperty in scope) - { - var propertyName = scopeProperty.Key.AssertString($"{PipelineTemplateConstants.Scopes} item key"); - - switch (propertyName.Value) - { - case PipelineTemplateConstants.Name: - var nameLiteral = scopeProperty.Value.AssertString($"{PipelineTemplateConstants.Scopes} item {PipelineTemplateConstants.Name}"); - result.Name = nameLiteral.Value; - break; - - case PipelineTemplateConstants.Inputs: - result.Inputs = scopeProperty.Value.AssertMapping($"{PipelineTemplateConstants.Scopes} item {PipelineTemplateConstants.Inputs}"); - break; - - case PipelineTemplateConstants.Outputs: - result.Outputs = scopeProperty.Value.AssertMapping($"{PipelineTemplateConstants.Scopes} item {PipelineTemplateConstants.Outputs}"); - break; - } - } - - yield return result; - } - } - - private static List ConvertToSteps( - TemplateContext context, - TemplateToken steps) - { - var stepsSequence = steps.AssertSequence($"job {PipelineTemplateConstants.Steps}"); - - var result = new List(); - foreach (var stepsItem in stepsSequence) - { - var step = ConvertToStep(context, stepsItem); - if (step != null) // step = null means we are hitting error during step conversion, there should be an error in context.errors - { - if (step.Enabled) - { - result.Add(step); - } - } - } - - return result; - } - - private static ActionStep ConvertToStep( - TemplateContext context, - TemplateToken stepsItem) - { - var step = stepsItem.AssertMapping($"{PipelineTemplateConstants.Steps} item"); - var continueOnError = default(ScalarToken); - var env = default(TemplateToken); - var id = default(StringToken); - var ifCondition = default(String); - var ifToken = default(StringToken); - var name = default(ScalarToken); - var run = default(ScalarToken); - var scope = default(StringToken); - var timeoutMinutes = default(ScalarToken); - var uses = default(StringToken); - var with = default(TemplateToken); - var workingDir = default(ScalarToken); - var path = default(ScalarToken); - var clean = default(ScalarToken); - var fetchDepth = default(ScalarToken); - var lfs = default(ScalarToken); - var submodules = default(ScalarToken); - var shell = default(ScalarToken); - - foreach (var stepProperty in step) - { - var propertyName = stepProperty.Key.AssertString($"{PipelineTemplateConstants.Steps} item key"); - - switch (propertyName.Value) - { - case PipelineTemplateConstants.Clean: - clean = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Clean}"); - break; - - case PipelineTemplateConstants.ContinueOnError: - ConvertToStepContinueOnError(context, stepProperty.Value, allowExpressions: true); // Validate early if possible - continueOnError = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} {PipelineTemplateConstants.ContinueOnError}"); - break; - - case PipelineTemplateConstants.Env: - ConvertToStepEnvironment(context, stepProperty.Value, StringComparer.Ordinal, allowExpressions: true); // Validate early if possible - env = stepProperty.Value; - break; - - case PipelineTemplateConstants.FetchDepth: - fetchDepth = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.FetchDepth}"); - break; - - case PipelineTemplateConstants.Id: - id = stepProperty.Value.AssertString($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Id}"); - if (!NameValidation.IsValid(id.Value, true)) - { - context.Error(id, $"Step id {id.Value} is invalid. Ids must start with a letter or '_' and contain only alphanumeric characters, '-', or '_'"); - } - break; - - case PipelineTemplateConstants.If: - ifToken = stepProperty.Value.AssertString($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.If}"); - break; - - case PipelineTemplateConstants.Lfs: - lfs = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Lfs}"); - break; - - case PipelineTemplateConstants.Name: - name = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Name}"); - break; - - case PipelineTemplateConstants.Path: - path = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Path}"); - break; - - case PipelineTemplateConstants.Run: - run = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Run}"); - break; - - case PipelineTemplateConstants.Shell: - shell = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Shell}"); - break; - - case PipelineTemplateConstants.Scope: - scope = stepProperty.Value.AssertString($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Scope}"); - break; - - case PipelineTemplateConstants.Submodules: - submodules = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Submodules}"); - break; - - case PipelineTemplateConstants.TimeoutMinutes: - ConvertToStepTimeout(context, stepProperty.Value, allowExpressions: true); // Validate early if possible - timeoutMinutes = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.TimeoutMinutes}"); - break; - - case PipelineTemplateConstants.Uses: - uses = stepProperty.Value.AssertString($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.Uses}"); - break; - - case PipelineTemplateConstants.With: - ConvertToStepInputs(context, stepProperty.Value, allowExpressions: true); // Validate early if possible - with = stepProperty.Value; - break; - - case PipelineTemplateConstants.WorkingDirectory: - workingDir = stepProperty.Value.AssertScalar($"{PipelineTemplateConstants.Steps} item {PipelineTemplateConstants.WorkingDirectory}"); - break; - - default: - propertyName.AssertUnexpectedValue($"{PipelineTemplateConstants.Steps} item key"); // throws - break; - } - } - - // Fixup the if-condition - var isDefaultScope = String.IsNullOrEmpty(scope?.Value); - ifCondition = ConvertToIfCondition(context, ifToken, false, isDefaultScope); - - if (run != null) - { - var result = new ActionStep - { - ScopeName = scope?.Value, - ContextName = id?.Value, - ContinueOnError = continueOnError?.Clone(true) as ScalarToken, - DisplayNameToken = name?.Clone(true) as ScalarToken, - Condition = ifCondition, - TimeoutInMinutes = timeoutMinutes?.Clone(true) as ScalarToken, - Environment = env?.Clone(true), - Reference = new ScriptReference(), - }; - - var inputs = new MappingToken(null, null, null); - inputs.Add(new StringToken(null, null, null, PipelineConstants.ScriptStepInputs.Script), run.Clone(true)); - - if (workingDir != null) - { - inputs.Add(new StringToken(null, null, null, PipelineConstants.ScriptStepInputs.WorkingDirectory), workingDir.Clone(true)); - } - - if (shell != null) - { - inputs.Add(new StringToken(null, null, null, PipelineConstants.ScriptStepInputs.Shell), shell.Clone(true)); - } - - result.Inputs = inputs; - - return result; - } - else if (uses != null) - { - var result = new ActionStep - { - ScopeName = scope?.Value, - ContextName = id?.Value, - ContinueOnError = continueOnError?.Clone(true) as ScalarToken, - DisplayNameToken = name?.Clone(true) as ScalarToken, - Condition = ifCondition, - TimeoutInMinutes = timeoutMinutes?.Clone(true) as ScalarToken, - Inputs = with, - Environment = env, - }; - - if (uses.Value.StartsWith("docker://", StringComparison.Ordinal)) - { - var image = uses.Value.Substring("docker://".Length); - result.Reference = new ContainerRegistryReference { Image = image }; - } - else if (uses.Value.StartsWith("./") || uses.Value.StartsWith(".\\")) - { - result.Reference = new RepositoryPathReference - { - RepositoryType = PipelineConstants.SelfAlias, - Path = uses.Value - }; - } - else - { - var usesSegments = uses.Value.Split('@'); - var pathSegments = usesSegments[0].Split(new[] { '/', '\\' }, StringSplitOptions.RemoveEmptyEntries); - var gitRef = usesSegments.Length == 2 ? usesSegments[1] : String.Empty; - - if (usesSegments.Length != 2 || - pathSegments.Length < 2 || - String.IsNullOrEmpty(pathSegments[0]) || - String.IsNullOrEmpty(pathSegments[1]) || - String.IsNullOrEmpty(gitRef)) - { - // todo: loc - context.Error(uses, $"Expected format {{org}}/{{repo}}[/path]@ref. Actual '{uses.Value}'"); - } - else - { - var repositoryName = $"{pathSegments[0]}/{pathSegments[1]}"; - var directoryPath = pathSegments.Length > 2 ? String.Join("/", pathSegments.Skip(2)) : String.Empty; - - result.Reference = new RepositoryPathReference - { - RepositoryType = RepositoryTypes.GitHub, - Name = repositoryName, - Ref = gitRef, - Path = directoryPath, - }; - } - } - - return result; - } - else - { - // todo: build a "required" concept into the parser - context.Error(step, $"Either '{PipelineTemplateConstants.Uses}' or '{PipelineTemplateConstants.Run}' is required"); - return null; - } - } - - private static String ConvertToIfCondition( - TemplateContext context, - StringToken ifCondition, - Boolean isJob, - Boolean isDefaultScope) - { - if (String.IsNullOrWhiteSpace(ifCondition?.Value)) - { - return $"{PipelineTemplateConstants.Success}()"; - } - - var condition = ifCondition.Value; - - var expressionParser = new ExpressionParser(); - var functions = default(IFunctionInfo[]); - var namedValues = default(INamedValueInfo[]); - if (isJob) - { - namedValues = s_jobIfNamedValues; - functions = PhaseCondition.FunctionInfo; - } - else - { - namedValues = isDefaultScope ? s_stepNamedValues : s_stepInTemplateNamedValues; - functions = s_stepConditionFunctions; - } - - var node = default(ExpressionNode); - try - { - node = expressionParser.CreateTree(condition, null, namedValues, functions) as ExpressionNode; - } - catch (Exception ex) - { - context.Error(ifCondition, ex); - return null; - } - - if (node == null) - { - return $"{PipelineTemplateConstants.Success}()"; - } - - var hasStatusFunction = node.Traverse().Any(x => - { - if (x is Function function) - { - return String.Equals(function.Name, PipelineTemplateConstants.Always, StringComparison.OrdinalIgnoreCase) || - String.Equals(function.Name, PipelineTemplateConstants.Cancelled, StringComparison.OrdinalIgnoreCase) || - String.Equals(function.Name, PipelineTemplateConstants.Failure, StringComparison.OrdinalIgnoreCase) || - String.Equals(function.Name, PipelineTemplateConstants.Success, StringComparison.OrdinalIgnoreCase); - } - - return false; - }); - - return hasStatusFunction ? condition : $"{PipelineTemplateConstants.Success}() && ({condition})"; - } - - private static readonly INamedValueInfo[] s_jobIfNamedValues = new INamedValueInfo[] - { - new NamedValueInfo(PipelineTemplateConstants.GitHub), - }; - private static readonly INamedValueInfo[] s_stepNamedValues = new INamedValueInfo[] - { - new NamedValueInfo(PipelineTemplateConstants.Strategy), - new NamedValueInfo(PipelineTemplateConstants.Matrix), - new NamedValueInfo(PipelineTemplateConstants.Steps), - new NamedValueInfo(PipelineTemplateConstants.GitHub), - new NamedValueInfo(PipelineTemplateConstants.Job), - new NamedValueInfo(PipelineTemplateConstants.Runner), - new NamedValueInfo(PipelineTemplateConstants.Env), - }; - private static readonly INamedValueInfo[] s_stepInTemplateNamedValues = new INamedValueInfo[] - { - new NamedValueInfo(PipelineTemplateConstants.Strategy), - new NamedValueInfo(PipelineTemplateConstants.Matrix), - new NamedValueInfo(PipelineTemplateConstants.Steps), - new NamedValueInfo(PipelineTemplateConstants.Inputs), - new NamedValueInfo(PipelineTemplateConstants.GitHub), - new NamedValueInfo(PipelineTemplateConstants.Job), - new NamedValueInfo(PipelineTemplateConstants.Runner), - new NamedValueInfo(PipelineTemplateConstants.Env), - }; - private static readonly IFunctionInfo[] s_stepConditionFunctions = new IFunctionInfo[] - { - new FunctionInfo(PipelineTemplateConstants.Always, 0, 0), - new FunctionInfo(PipelineTemplateConstants.Cancelled, 0, 0), - new FunctionInfo(PipelineTemplateConstants.Failure, 0, 0), - new FunctionInfo(PipelineTemplateConstants.Success, 0, 0), - }; } } diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateEvaluator.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateEvaluator.cs index fc69ca272..de9e7bc65 100644 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateEvaluator.cs +++ b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateEvaluator.cs @@ -46,170 +46,6 @@ namespace GitHub.DistributedTask.Pipelines.ObjectTemplating public Int32 MaxResultSize { get; set; } = 10 * 1024 * 1024; // 10 mb - public StrategyResult EvaluateStrategy( - TemplateToken token, - DictionaryContextData contextData, - String jobFactoryDisplayName) - { - var result = new StrategyResult(); - - if (token != null && token.Type != TokenType.Null) - { - var context = CreateContext(contextData); - try - { - token = TemplateEvaluator.Evaluate(context, PipelineTemplateConstants.Strategy, token, 0, null, omitHeader: true); - context.Errors.Check(); - result = PipelineTemplateConverter.ConvertToStrategy(context, token, jobFactoryDisplayName); - } - catch (Exception ex) when (!(ex is TemplateValidationException)) - { - context.Errors.Add(ex); - } - - context.Errors.Check(); - } - - if (result.Configurations.Count == 0) - { - var configuration = new StrategyConfiguration - { - Name = PipelineConstants.DefaultJobName, - DisplayName = new JobDisplayNameBuilder(jobFactoryDisplayName).Build(), - }; - configuration.ContextData.Add(PipelineTemplateConstants.Matrix, null); - configuration.ContextData.Add( - PipelineTemplateConstants.Strategy, - new DictionaryContextData - { - { - "fail-fast", - new BooleanContextData(result.FailFast) - }, - { - "job-index", - new NumberContextData(0) - }, - { - "job-total", - new NumberContextData(1) - }, - { - "max-parallel", - new NumberContextData(1) - } - }); - result.Configurations.Add(configuration); - } - - return result; - } - - public String EvaluateJobDisplayName( - TemplateToken token, - DictionaryContextData contextData, - String defaultDisplayName) - { - var result = default(String); - - if (token != null && token.Type != TokenType.Null) - { - var context = CreateContext(contextData); - try - { - token = TemplateEvaluator.Evaluate(context, PipelineTemplateConstants.StringStrategyContext, token, 0, null, omitHeader: true); - context.Errors.Check(); - result = PipelineTemplateConverter.ConvertToJobDisplayName(context, token); - } - catch (Exception ex) when (!(ex is TemplateValidationException)) - { - context.Errors.Add(ex); - } - - context.Errors.Check(); - } - - return !String.IsNullOrEmpty(result) ? result : defaultDisplayName; - } - - public PhaseTarget EvaluateJobTarget( - TemplateToken token, - DictionaryContextData contextData) - { - var result = default(PhaseTarget); - - if (token != null && token.Type != TokenType.Null) - { - var context = CreateContext(contextData); - try - { - token = TemplateEvaluator.Evaluate(context, PipelineTemplateConstants.RunsOn, token, 0, null, omitHeader: true); - context.Errors.Check(); - result = PipelineTemplateConverter.ConvertToJobTarget(context, token); - } - catch (Exception ex) when (!(ex is TemplateValidationException)) - { - context.Errors.Add(ex); - } - - context.Errors.Check(); - } - - return result ?? throw new InvalidOperationException("Job target cannot be null"); - } - - public Int32 EvaluateJobTimeout( - TemplateToken token, - DictionaryContextData contextData) - { - var result = default(Int32?); - - if (token != null && token.Type != TokenType.Null) - { - var context = CreateContext(contextData); - try - { - token = TemplateEvaluator.Evaluate(context, PipelineTemplateConstants.NumberStrategyContext, token, 0, null, omitHeader: true); - context.Errors.Check(); - result = PipelineTemplateConverter.ConvertToJobTimeout(context, token); - } - catch (Exception ex) when (!(ex is TemplateValidationException)) - { - context.Errors.Add(ex); - } - - context.Errors.Check(); - } - - return result ?? PipelineConstants.DefaultJobTimeoutInMinutes; - } - - public Int32 EvaluateJobCancelTimeout( - TemplateToken token, - DictionaryContextData contextData) - { - var result = default(Int32?); - - if (token != null && token.Type != TokenType.Null) - { - var context = CreateContext(contextData); - try - { - token = TemplateEvaluator.Evaluate(context, PipelineTemplateConstants.NumberStrategyContext, token, 0, null, omitHeader: true); - context.Errors.Check(); - result = PipelineTemplateConverter.ConvertToJobCancelTimeout(context, token); - } - catch (Exception ex) when (!(ex is TemplateValidationException)) - { - context.Errors.Add(ex); - } - - context.Errors.Check(); - } - - return result ?? PipelineConstants.DefaultJobCancelTimeoutInMinutes; - } - public DictionaryContextData EvaluateStepScopeInputs( TemplateToken token, DictionaryContextData contextData) diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateParser.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateParser.cs deleted file mode 100644 index 62557d38c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/PipelineTemplateParser.cs +++ /dev/null @@ -1,239 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.IO; -using System.Threading; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.ObjectTemplating.Schema; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - using GitHub.DistributedTask.ObjectTemplating; - - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PipelineTemplateParser - { - static PipelineTemplateParser() - { - var schemaFactory = new PipelineTemplateSchemaFactory(); - s_schema = schemaFactory.CreateSchema(); - } - - public PipelineTemplateParser( - ITraceWriter trace, - ParseOptions options) - { - m_trace = trace ?? throw new ArgumentNullException(nameof(trace)); - m_parseOptions = new ParseOptions(options ?? throw new ArgumentNullException(nameof(options))); - } - - /// - /// Loads the YAML pipeline template - /// - /// Thrown when the entry YAML file does not exist - public PipelineTemplate LoadPipeline( - IFileProvider fileProvider, - RepositoryResource self, - String path, - CancellationToken cancellationToken) - { - fileProvider = fileProvider ?? throw new ArgumentNullException(nameof(fileProvider)); - self = self ?? throw new ArgumentNullException(nameof(self)); - var parseResult = LoadPipelineInternal(fileProvider, path, cancellationToken); - return PipelineTemplateConverter.ConvertToPipeline(parseResult.Context, self, parseResult.Value); - } - - internal ParseResult LoadPipelineInternal( - IFileProvider fileProvider, - String path, - CancellationToken cancellationToken) - { - // Setup the context - var templateLoader = new YamlTemplateLoader(new ParseOptions(m_parseOptions), fileProvider); - var context = new TemplateContext - { - CancellationToken = cancellationToken, - Errors = new TemplateValidationErrors(m_parseOptions.MaxErrors, m_parseOptions.MaxErrorMessageLength), - Memory = new TemplateMemory( - maxDepth: m_parseOptions.MaxDepth, - maxEvents: m_parseOptions.MaxParseEvents, - maxBytes: m_parseOptions.MaxResultSize), - Schema = s_schema, - TraceWriter = m_trace, - }; - - // Load the entry file - var token = default(TemplateToken); - try - { - token = templateLoader.LoadFile(context, null, null, path, PipelineTemplateConstants.WorkflowRoot); - } - catch (Exception ex) - { - context.Errors.Add(ex); - } - - var result = new ParseResult - { - Context = context, - Value = token, - }; - - if (token != null && context.Errors.Count == 0) - { - var templateReferenceCount = ResolveWorkflowTemplateReferences(context, templateLoader, token); - if (templateReferenceCount > 0 && context.Errors.Count == 0) - { - context.TraceWriter.Info(String.Empty); - context.TraceWriter.Info("# "); - context.TraceWriter.Info("# Template resolution complete. Final runtime YAML document:"); - context.TraceWriter.Info("# "); - context.TraceWriter.Info("{0}", result.ToYaml()); - } - } - - return result; - } - - private Int32 ResolveWorkflowTemplateReferences( - TemplateContext context, - YamlTemplateLoader templateLoader, - TemplateToken token) - { - var resolvedCount = 0; - var workflow = token.AssertMapping("workflow"); - foreach (var workflowProperty in workflow) - { - var workflowPropertyName = workflowProperty.Key.AssertString("workflow property"); - switch (workflowPropertyName.Value) - { - case PipelineTemplateConstants.Jobs: - resolvedCount += ResolveJobsTemplateReferences(context, templateLoader, workflowProperty.Value); - break; - - case PipelineTemplateConstants.Workflow: - resolvedCount += ResolveJobsTemplateReferences(context, templateLoader, workflowProperty.Value); - break; - } - } - - return resolvedCount; - } - - private Int32 ResolveJobsTemplateReferences( - TemplateContext context, - YamlTemplateLoader templateLoader, - TemplateToken token) - { - var resolvedCount = 0; - var jobs = token.AssertMapping("jobs"); - foreach (var jobsProperty in jobs) - { - var job = jobsProperty.Value.AssertMapping("jobs property value"); - var scopes = new SequenceToken(null, null, null); - foreach (var jobProperty in job) - { - var jobPropertyName = jobProperty.Key.AssertString("job property name"); - switch (jobPropertyName.Value) - { - case PipelineTemplateConstants.Steps: - resolvedCount += ResolveStepsTemplateReferences(context, templateLoader, jobProperty.Value, scopes); - break; - } - } - - if (scopes.Count > 0) - { - var scopesPropertyName = new StringToken(null, null, null, PipelineTemplateConstants.Scopes); - job.Add(scopesPropertyName, scopes); - context.Memory.AddBytes(scopesPropertyName); - context.Memory.AddBytes(scopes); // Do not traverse, nested objects already accounted for - } - } - - return resolvedCount; - } - - private Int32 ResolveStepsTemplateReferences( - TemplateContext context, - YamlTemplateLoader templateLoader, - TemplateToken token, - SequenceToken scopes) - { - var resolvedCount = 0; - var steps = token.AssertSequence("steps"); - var stepIndex = 0; - while (stepIndex < steps.Count && context.Errors.Count == 0) - { - var step = steps[stepIndex].AssertMapping("step"); - if (!TemplateReference.TryCreate(step, out var reference)) - { - stepIndex++; - continue; - } - - resolvedCount++; - var template = templateLoader.LoadFile( - context, - reference.TemplatePath.FileId, - reference.TemplateScope, - reference.TemplatePath.Value, - PipelineTemplateConstants.StepsTemplateRoot); - - if (context.Errors.Count != 0) - { - break; - } - - var scope = reference.CreateScope(context, template); - - if (context.Errors.Count != 0) - { - break; - } - - // Remove the template reference and memory overhead - steps.RemoveAt(stepIndex); - context.Memory.SubtractBytes(step, true); // Traverse - - // Remove the template memory overhead - context.Memory.SubtractBytes(template, true); // Traverse - - var templateSteps = GetSteps(template); - if (templateSteps?.Count > 0) - { - // Add the steps from the template - steps.InsertRange(stepIndex, templateSteps); - context.Memory.AddBytes(templateSteps, true); // Traverse - context.Memory.SubtractBytes(templateSteps, false); - - // Add the scope - scopes.Add(scope); - context.Memory.AddBytes(scope, true); // Traverse - } - } - - return resolvedCount; - } - - private SequenceToken GetSteps(TemplateToken template) - { - var mapping = template.AssertMapping("steps template"); - foreach (var property in mapping) - { - var propertyName = property.Key.AssertString("steps template property name"); - switch (propertyName.Value) - { - case PipelineTemplateConstants.Steps: - return property.Value.AssertSequence("steps template steps property value"); - } - } - - return null; - } - - private static TemplateSchema s_schema; - private readonly ParseOptions m_parseOptions; - private readonly ITraceWriter m_trace; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ReferenceNameBuilder.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ReferenceNameBuilder.cs deleted file mode 100644 index 2b42f2918..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/ReferenceNameBuilder.cs +++ /dev/null @@ -1,121 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Text; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - internal sealed class ReferenceNameBuilder - { - internal void AppendSegment(String value) - { - if (String.IsNullOrEmpty(value)) - { - return; - } - - if (m_name.Length == 0) - { - var first = value[0]; - if ((first >= 'a' && first <= 'z') || - (first >= 'A' && first <= 'Z') || - first == '_') - { - // Legal first char - } - else if ((first >= '0' && first <= '9') || first == '-') - { - // Illegal first char, but legal char. - // Prepend "_". - m_name.Append("_"); - } - else - { - // Illegal char - } - } - else - { - // Separator - m_name.Append(c_separator); - } - - foreach (var c in value) - { - if ((c >= 'a' && c <= 'z') || - (c >= 'A' && c <= 'Z') || - (c >= '0' && c <= '9') || - c == '_' || - c == '-') - { - // Legal - m_name.Append(c); - } - else - { - // Illegal - m_name.Append("_"); - } - } - } - - internal String Build() - { - var original = m_name.Length > 0 ? m_name.ToString() : "job"; - - var attempt = 1; - var suffix = default(String); - while (true) - { - if (attempt == 1) - { - suffix = String.Empty; - } - else if (attempt < 1000) - { - suffix = String.Format(CultureInfo.InvariantCulture, "_{0}", attempt); - } - else - { - throw new InvalidOperationException("Unable to create a unique name"); - } - - var candidate = original.Substring(0, Math.Min(original.Length, PipelineConstants.MaxNodeNameLength - suffix.Length)) + suffix; - - if (m_distinctNames.Add(candidate)) - { - m_name.Clear(); - return candidate; - } - - attempt++; - } - } - - internal Boolean TryAddKnownName( - String value, - out String error) - { - if (!NameValidation.IsValid(value, allowHyphens: true) && value.Length < PipelineConstants.MaxNodeNameLength) - { - error = $"The identifier '{value}' is invalid. IDs may only contain alphanumeric characters, '_', and '-'. IDs must start with a letter or '_' and and must be less than {PipelineConstants.MaxNodeNameLength} characters."; - return false; - } - else if (!m_distinctNames.Add(value)) - { - error = $"The identifier '{value}' may not be used more than once within the same scope."; - return false; - } - else - { - error = null; - return true; - } - } - - private const String c_separator = "_"; - private readonly HashSet m_distinctNames = new HashSet(StringComparer.OrdinalIgnoreCase); - private readonly StringBuilder m_name = new StringBuilder(); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TaskResultExtensions.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TaskResultExtensions.cs deleted file mode 100644 index ab6ab22d8..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TaskResultExtensions.cs +++ /dev/null @@ -1,37 +0,0 @@ -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - public static class TaskResultExtensions - { - public static PipelineContextData ToContextData(this TaskResult result) - { - switch (result) - { - case TaskResult.Succeeded: - case TaskResult.SucceededWithIssues: - return new StringContextData(PipelineTemplateConstants.Success); - case TaskResult.Failed: - case TaskResult.Abandoned: - return new StringContextData(PipelineTemplateConstants.Failure); - case TaskResult.Canceled: - return new StringContextData(PipelineTemplateConstants.Cancelled); - case TaskResult.Skipped: - return new StringContextData(PipelineTemplateConstants.Skipped); - } - - return null; - } - - public static PipelineContextData ToContextData(this TaskResult? result) - { - if (result.HasValue) - { - return result.Value.ToContextData(); - } - - return null; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TemplateReference.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TemplateReference.cs deleted file mode 100644 index 170ec23a0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/TemplateReference.cs +++ /dev/null @@ -1,197 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.IO; -using System.Threading; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.ObjectTemplating.Schema; -using GitHub.DistributedTask.Pipelines.ObjectTemplating; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - using GitHub.DistributedTask.ObjectTemplating; - - internal sealed class TemplateReference - { - private TemplateReference( - String scope, - String id, - String generatedId, - StringToken templatePath, - MappingToken inputs) - { - Scope = scope; - TemplatePath = templatePath; - Inputs = inputs; - - if (!String.IsNullOrEmpty(generatedId)) - { - Id = generatedId; - m_isGeneratedId = true; - } - else - { - Id = id; - } - } - - internal String Id { get; } - - internal MappingToken Inputs { get; } - - internal String Scope { get; } - - internal StringToken TemplatePath { get; } - - internal String TemplateScope - { - get - { - return !String.IsNullOrEmpty(Scope) ? $"{Scope}.{Id}" : Id; - } - } - - internal MappingToken CreateScope( - TemplateContext context, - TemplateToken template) - { - var mapping = template.AssertMapping("template file"); - - // Get the inputs and outputs from the template - var inputs = default(MappingToken); - var outputs = default(MappingToken); - foreach (var pair in mapping) - { - var propertyName = pair.Key.AssertString("template file property name"); - switch (propertyName.Value) - { - case PipelineTemplateConstants.Inputs: - inputs = pair.Value.AssertMapping("template file inputs"); - break; - - case PipelineTemplateConstants.Outputs: - if (!m_isGeneratedId) - { - outputs = pair.Value.AssertMapping("template file outputs"); - } - break; - } - } - - // Determine allowed input names - var allowedInputNames = new HashSet(StringComparer.OrdinalIgnoreCase); - if (inputs?.Count > 0) - { - foreach (var pair in inputs) - { - var inputPropertyName = pair.Key.AssertString("template file inputs property"); - allowedInputNames.Add(inputPropertyName.Value); - } - } - - // Validate override inputs names - var overrideInputs = new HashSet(StringComparer.OrdinalIgnoreCase); - var mergedInputs = new MappingToken(null, null, null); - if (Inputs?.Count > 0) - { - foreach (var pair in Inputs) - { - var inputPropertyName = pair.Key.AssertString("template reference inputs property"); - if (!allowedInputNames.Contains(inputPropertyName.Value)) - { - context.Error(inputPropertyName, $"Input '{inputPropertyName.Value}' is not allowed"); - continue; - } - - overrideInputs.Add(inputPropertyName.Value); - mergedInputs.Add(pair.Key, pair.Value); - } - } - - // Merge defaults - if (inputs?.Count > 0) - { - foreach (var pair in inputs) - { - var inputPropertyName = pair.Key.AssertString("template file inputs property"); - if (!overrideInputs.Contains(inputPropertyName.Value)) - { - mergedInputs.Add(pair.Key, pair.Value); - } - } - } - - // Build the scope object - var result = new MappingToken(null, null, null); - var namePropertyName = new StringToken(null, null, null, PipelineTemplateConstants.Name); - var namePropertyValue = new StringToken(null, null, null, TemplateScope); - result.Add(namePropertyName, namePropertyValue); - if (mergedInputs.Count > 0) - { - var inputsPropertyName = new StringToken(null, null, null, PipelineTemplateConstants.Inputs); - result.Add(inputsPropertyName, mergedInputs); - } - - if (outputs?.Count > 0) - { - var outputsPropertyName = new StringToken(null, null, null, PipelineTemplateConstants.Outputs); - result.Add(outputsPropertyName, outputs); - } - - return result; - } - - internal static Boolean TryCreate( - MappingToken mapping, - out TemplateReference reference) - { - var scope = default(String); - var id = default(String); - var generatedId = default(String); - var templatePath = default(StringToken); - var inputs = default(MappingToken); - foreach (var property in mapping) - { - var propertyName = property.Key.AssertString("candidate template reference property name"); - switch (propertyName.Value) - { - case PipelineTemplateConstants.Scope: - var scopeStringToken = property.Value.AssertString("step scope"); - scope = scopeStringToken.Value; - break; - - case PipelineTemplateConstants.Id: - var idStringToken = property.Value.AssertString("step id"); - id = idStringToken.Value; - break; - - case PipelineTemplateConstants.GeneratedId: - var generatedIdStringToken = property.Value.AssertString("step generated id"); - generatedId = generatedIdStringToken.Value; - break; - - case PipelineTemplateConstants.Template: - templatePath = property.Value.AssertString("step template reference"); - break; - - case PipelineTemplateConstants.Inputs: - inputs = property.Value.AssertMapping("step template reference inputs"); - break; - } - } - - if (templatePath != null) - { - reference = new TemplateReference(scope, id, generatedId, templatePath, inputs); - return true; - } - else - { - reference = null; - return false; - } - } - - private Boolean m_isGeneratedId; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectReader.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectReader.cs deleted file mode 100644 index 431cceac0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectReader.cs +++ /dev/null @@ -1,572 +0,0 @@ -using System; -using System.Globalization; -using System.IO; -using System.Linq; -using GitHub.DistributedTask.ObjectTemplating; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using YamlDotNet.Core; -using YamlDotNet.Core.Events; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - /// - /// Converts a YAML file into a TemplateToken - /// - internal sealed class YamlObjectReader : IObjectReader - { - internal YamlObjectReader( - Int32? fileId, - TextReader input) - { - m_fileId = fileId; - m_parser = new Parser(input); - } - - public Boolean AllowLiteral(out LiteralToken value) - { - if (EvaluateCurrent() is Scalar scalar) - { - // Tag specified - if (!String.IsNullOrEmpty(scalar.Tag)) - { - // String tag - if (String.Equals(scalar.Tag, c_stringTag, StringComparison.Ordinal)) - { - value = new StringToken(m_fileId, scalar.Start.Line, scalar.Start.Column, scalar.Value); - MoveNext(); - return true; - } - - // Not plain style - if (scalar.Style != ScalarStyle.Plain) - { - throw new NotSupportedException($"The scalar style '{scalar.Style}' on line {scalar.Start.Line} and column {scalar.Start.Column} is not valid with the tag '{scalar.Tag}'"); - } - - // Boolean, Float, Integer, or Null - switch (scalar.Tag) - { - case c_booleanTag: - value = ParseBoolean(scalar); - break; - case c_floatTag: - value = ParseFloat(scalar); - break; - case c_integerTag: - value = ParseInteger(scalar); - break; - case c_nullTag: - value = ParseNull(scalar); - break; - default: - throw new NotSupportedException($"Unexpected tag '{scalar.Tag}'"); - } - - MoveNext(); - return true; - } - - // Plain style, determine type using YAML 1.2 "core" schema https://yaml.org/spec/1.2/spec.html#id2804923 - if (scalar.Style == ScalarStyle.Plain) - { - if (MatchNull(scalar, out var nullToken)) - { - value = nullToken; - } - else if (MatchBoolean(scalar, out var booleanToken)) - { - value = booleanToken; - } - else if (MatchInteger(scalar, out var numberToken) || - MatchFloat(scalar, out numberToken)) - { - value = numberToken; - } - else - { - value = new StringToken(m_fileId, scalar.Start.Line, scalar.Start.Column, scalar.Value); - } - - MoveNext(); - return true; - } - - // Otherwise assume string - value = new StringToken(m_fileId, scalar.Start.Line, scalar.Start.Column, scalar.Value); - MoveNext(); - return true; - } - - value = default; - return false; - } - - public Boolean AllowSequenceStart(out SequenceToken value) - { - if (EvaluateCurrent() is SequenceStart sequenceStart) - { - value = new SequenceToken(m_fileId, sequenceStart.Start.Line, sequenceStart.Start.Column); - MoveNext(); - return true; - } - - value = default; - return false; - } - - public Boolean AllowSequenceEnd() - { - if (EvaluateCurrent() is SequenceEnd) - { - MoveNext(); - return true; - } - - return false; - } - - public Boolean AllowMappingStart(out MappingToken value) - { - if (EvaluateCurrent() is MappingStart mappingStart) - { - value = new MappingToken(m_fileId, mappingStart.Start.Line, mappingStart.Start.Column); - MoveNext(); - return true; - } - - value = default; - return false; - } - - public Boolean AllowMappingEnd() - { - if (EvaluateCurrent() is MappingEnd) - { - MoveNext(); - return true; - } - - return false; - } - - /// - /// Consumes the last parsing events, which are expected to be DocumentEnd and StreamEnd. - /// - public void ValidateEnd() - { - if (EvaluateCurrent() is DocumentEnd) - { - MoveNext(); - } - else - { - throw new InvalidOperationException("Expected document end parse event"); - } - - if (EvaluateCurrent() is StreamEnd) - { - MoveNext(); - } - else - { - throw new InvalidOperationException("Expected stream end parse event"); - } - - if (MoveNext()) - { - throw new InvalidOperationException("Expected end of parse events"); - } - } - - /// - /// Consumes the first parsing events, which are expected to be StreamStart and DocumentStart. - /// - public void ValidateStart() - { - if (EvaluateCurrent() != null) - { - throw new InvalidOperationException("Unexpected parser state"); - } - - if (!MoveNext()) - { - throw new InvalidOperationException("Expected a parse event"); - } - - if (EvaluateCurrent() is StreamStart) - { - MoveNext(); - } - else - { - throw new InvalidOperationException("Expected stream start parse event"); - } - - if (EvaluateCurrent() is DocumentStart) - { - MoveNext(); - } - else - { - throw new InvalidOperationException("Expected document start parse event"); - } - } - - private ParsingEvent EvaluateCurrent() - { - if (m_current == null) - { - m_current = m_parser.Current; - if (m_current != null) - { - if (m_current is Scalar scalar) - { - // Verify not using achors - if (scalar.Anchor != null) - { - throw new InvalidOperationException($"Anchors are not currently supported. Remove the anchor '{scalar.Anchor}'"); - } - } - else if (m_current is MappingStart mappingStart) - { - // Verify not using achors - if (mappingStart.Anchor != null) - { - throw new InvalidOperationException($"Anchors are not currently supported. Remove the anchor '{mappingStart.Anchor}'"); - } - } - else if (m_current is SequenceStart sequenceStart) - { - // Verify not using achors - if (sequenceStart.Anchor != null) - { - throw new InvalidOperationException($"Anchors are not currently supported. Remove the anchor '{sequenceStart.Anchor}'"); - } - } - else if (!(m_current is MappingEnd) && - !(m_current is SequenceEnd) && - !(m_current is DocumentStart) && - !(m_current is DocumentEnd) && - !(m_current is StreamStart) && - !(m_current is StreamEnd)) - { - throw new InvalidOperationException($"Unexpected parsing event type: {m_current.GetType().Name}"); - } - } - } - - return m_current; - } - - private Boolean MoveNext() - { - m_current = null; - return m_parser.MoveNext(); - } - - private BooleanToken ParseBoolean(Scalar scalar) - { - if (MatchBoolean(scalar, out var token)) - { - return token; - } - - ThrowInvalidValue(scalar, c_booleanTag); // throws - return default; - } - - private NumberToken ParseFloat(Scalar scalar) - { - if (MatchFloat(scalar, out var token)) - { - return token; - } - - ThrowInvalidValue(scalar, c_floatTag); // throws - return default; - } - - private NumberToken ParseInteger(Scalar scalar) - { - if (MatchInteger(scalar, out var token)) - { - return token; - } - - ThrowInvalidValue(scalar, c_integerTag); // throws - return default; - } - - private NullToken ParseNull(Scalar scalar) - { - if (MatchNull(scalar, out var token)) - { - return token; - } - - ThrowInvalidValue(scalar, c_nullTag); // throws - return default; - } - - private Boolean MatchBoolean( - Scalar scalar, - out BooleanToken value) - { - // YAML 1.2 "core" schema https://yaml.org/spec/1.2/spec.html#id2804923 - switch (scalar.Value ?? String.Empty) - { - case "true": - case "True": - case "TRUE": - value = new BooleanToken(m_fileId, scalar.Start.Line, scalar.Start.Column, true); - return true; - case "false": - case "False": - case "FALSE": - value = new BooleanToken(m_fileId, scalar.Start.Line, scalar.Start.Column, false); - return true; - } - - value = default; - return false; - } - - private Boolean MatchFloat( - Scalar scalar, - out NumberToken value) - { - // YAML 1.2 "core" schema https://yaml.org/spec/1.2/spec.html#id2804923 - var str = scalar.Value; - if (!String.IsNullOrEmpty(str)) - { - // Check for [-+]?(\.inf|\.Inf|\.INF)|\.nan|\.NaN|\.NAN - switch (str) - { - case ".inf": - case ".Inf": - case ".INF": - case "+.inf": - case "+.Inf": - case "+.INF": - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, Double.PositiveInfinity); - return true; - case "-.inf": - case "-.Inf": - case "-.INF": - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, Double.NegativeInfinity); - return true; - case ".nan": - case ".NaN": - case ".NAN": - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, Double.NaN); - return true; - } - - // Otherwise check [-+]?(\.[0-9]+|[0-9]+(\.[0-9]*)?)([eE][-+]?[0-9]+)? - - // Skip leading sign - var index = str[0] == '-' || str[0] == '+' ? 1 : 0; - - // Check for integer portion - var length = str.Length; - var hasInteger = false; - while (index < length && str[index] >= '0' && str[index] <= '9') - { - hasInteger = true; - index++; - } - - // Check for decimal point - var hasDot = false; - if (index < length && str[index] == '.') - { - hasDot = true; - index++; - } - - // Check for decimal portion - var hasDecimal = false; - while (index < length && str[index] >= '0' && str[index] <= '9') - { - hasDecimal = true; - index++; - } - - // Check [-+]?(\.[0-9]+|[0-9]+(\.[0-9]*)?) - if ((hasDot && hasDecimal) || hasInteger) - { - // Check for end - if (index == length) - { - // Try parse - if (Double.TryParse(str, NumberStyles.AllowLeadingSign | NumberStyles.AllowDecimalPoint, CultureInfo.InvariantCulture, out var doubleValue)) - { - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, doubleValue); - return true; - } - // Otherwise exceeds range - else - { - ThrowInvalidValue(scalar, c_floatTag); // throws - } - } - // Check [eE][-+]?[0-9] - else if (index < length && (str[index] == 'e' || str[index] == 'E')) - { - index++; - - // Skip sign - if (index < length && (str[index] == '-' || str[index] == '+')) - { - index++; - } - - // Check for exponent - var hasExponent = false; - while (index < length && str[index] >= '0' && str[index] <= '9') - { - hasExponent = true; - index++; - } - - // Check for end - if (hasExponent && index == length) - { - // Try parse - if (Double.TryParse(str, NumberStyles.AllowLeadingSign | NumberStyles.AllowDecimalPoint | NumberStyles.AllowExponent, CultureInfo.InvariantCulture, out var doubleValue)) - { - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, (Double)doubleValue); - return true; - } - // Otherwise exceeds range - else - { - ThrowInvalidValue(scalar, c_floatTag); // throws - } - } - } - } - } - - value = default; - return false; - } - - private Boolean MatchInteger( - Scalar scalar, - out NumberToken value) - { - // YAML 1.2 "core" schema https://yaml.org/spec/1.2/spec.html#id2804923 - var str = scalar.Value; - if (!String.IsNullOrEmpty(str)) - { - // Check for [0-9]+ - var firstChar = str[0]; - if (firstChar >= '0' && firstChar <= '9' && - str.Skip(1).All(x => x >= '0' && x <= '9')) - { - // Try parse - if (Double.TryParse(str, NumberStyles.None, CultureInfo.InvariantCulture, out var doubleValue)) - { - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, doubleValue); - return true; - } - - // Otherwise exceeds range - ThrowInvalidValue(scalar, c_integerTag); // throws - } - // Check for (-|+)[0-9]+ - else if ((firstChar == '-' || firstChar == '+') && - str.Length > 1 && - str.Skip(1).All(x => x >= '0' && x <= '9')) - { - // Try parse - if (Double.TryParse(str, NumberStyles.AllowLeadingSign, CultureInfo.InvariantCulture, out var doubleValue)) - { - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, doubleValue); - return true; - } - - // Otherwise exceeds range - ThrowInvalidValue(scalar, c_integerTag); // throws - } - // Check for 0x[0-9a-fA-F]+ - else if (firstChar == '0' && - str.Length > 2 && - str[1] == 'x' && - str.Skip(2).All(x => (x >= '0' && x <= '9') || (x >= 'a' && x <= 'f') || (x >= 'A' && x <= 'F'))) - { - // Try parse - if (Int32.TryParse(str.Substring(2), NumberStyles.AllowHexSpecifier, CultureInfo.InvariantCulture, out var integerValue)) - { - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, integerValue); - return true; - } - - // Otherwise exceeds range - ThrowInvalidValue(scalar, c_integerTag); // throws - } - // Check for 0o[0-9]+ - else if (firstChar == '0' && - str.Length > 2 && - str[1] == 'o' && - str.Skip(2).All(x => x >= '0' && x <= '7')) - { - // Try parse - var integerValue = default(Int32); - try - { - integerValue = Convert.ToInt32(str.Substring(2), 8); - } - // Otherwise exceeds range - catch (Exception) - { - ThrowInvalidValue(scalar, c_integerTag); // throws - } - - value = new NumberToken(m_fileId, scalar.Start.Line, scalar.Start.Column, integerValue); - return true; - } - } - - value = default; - return false; - } - - private Boolean MatchNull( - Scalar scalar, - out NullToken value) - { - // YAML 1.2 "core" schema https://yaml.org/spec/1.2/spec.html#id2804923 - switch (scalar.Value ?? String.Empty) - { - case "": - case "null": - case "Null": - case "NULL": - case "~": - value = new NullToken(m_fileId, scalar.Start.Line, scalar.Start.Column); - return true; - } - - value = default; - return false; - } - - private void ThrowInvalidValue( - Scalar scalar, - String tag) - { - throw new NotSupportedException($"The value '{scalar.Value}' on line {scalar.Start.Line} and column {scalar.Start.Column} is invalid for the type '{scalar.Tag}'"); - } - - private const String c_booleanTag = "tag:yaml.org,2002:bool"; - private const String c_floatTag = "tag:yaml.org,2002:float"; - private const String c_integerTag = "tag:yaml.org,2002:int"; - private const String c_nullTag = "tag:yaml.org,2002:null"; - private const String c_stringTag = "tag:yaml.org,2002:string"; - private readonly Int32? m_fileId; - private readonly Parser m_parser; - private ParsingEvent m_current; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectWriter.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectWriter.cs deleted file mode 100644 index 27b921865..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlObjectWriter.cs +++ /dev/null @@ -1,73 +0,0 @@ -using System; -using System.Globalization; -using System.IO; -using GitHub.DistributedTask.ObjectTemplating; -using YamlDotNet.Core.Events; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - /// - /// Converts a TemplateToken into YAML - /// - internal sealed class YamlObjectWriter : IObjectWriter - { - internal YamlObjectWriter(StringWriter writer) - { - m_emitter = new YamlDotNet.Core.Emitter(writer); - } - - public void WriteString(String value) - { - m_emitter.Emit(new Scalar(value ?? String.Empty)); - } - - public void WriteBoolean(Boolean value) - { - m_emitter.Emit(new Scalar(value ? "true" : "false")); - } - - public void WriteNumber(Double value) - { - m_emitter.Emit(new Scalar(value.ToString("G15", CultureInfo.InvariantCulture))); - } - - public void WriteNull() - { - m_emitter.Emit(new Scalar("null")); - } - - public void WriteSequenceStart() - { - m_emitter.Emit(new SequenceStart(null, null, true, SequenceStyle.Block)); - } - - public void WriteSequenceEnd() - { - m_emitter.Emit(new SequenceEnd()); - } - - public void WriteMappingStart() - { - m_emitter.Emit(new MappingStart()); - } - - public void WriteMappingEnd() - { - m_emitter.Emit(new MappingEnd()); - } - - public void WriteStart() - { - m_emitter.Emit(new StreamStart()); - m_emitter.Emit(new DocumentStart()); - } - - public void WriteEnd() - { - m_emitter.Emit(new DocumentEnd(isImplicit: true)); - m_emitter.Emit(new StreamEnd()); - } - - private readonly YamlDotNet.Core.IEmitter m_emitter; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlTemplateLoader.cs b/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlTemplateLoader.cs deleted file mode 100644 index 3d44a299d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ObjectTemplating/YamlTemplateLoader.cs +++ /dev/null @@ -1,251 +0,0 @@ -using System; -using System.Collections.Generic; -using System.IO; -using GitHub.DistributedTask.ObjectTemplating; -using GitHub.DistributedTask.ObjectTemplating.Tokens; - -namespace GitHub.DistributedTask.Pipelines.ObjectTemplating -{ - /// - /// Loads a YAML file, and returns the parsed TemplateToken - /// - internal sealed class YamlTemplateLoader - { - public YamlTemplateLoader( - ParseOptions parseOptions, - IFileProvider fileProvider) - { - m_parseOptions = new ParseOptions(parseOptions); - m_fileProvider = fileProvider ?? throw new ArgumentNullException(nameof(fileProvider)); - } - - public TemplateToken LoadFile( - TemplateContext context, - Int32? rootFileId, - String scope, - String path, - String templateType) - { - if (context.Errors.Count > 0) - { - throw new InvalidOperationException("Expected error count to be 0 when attempting to load a new file"); - } - - // Is entry file? - var isEntryFile = m_referencedFiles.Count == 0; - - // Root the path - path = m_fileProvider.ResolvePath(null, path); - - // Validate max files - m_referencedFiles.Add(path); - if (m_parseOptions.MaxFiles > 0 && m_referencedFiles.Count > m_parseOptions.MaxFiles) - { - throw new InvalidOperationException($"The maximum file count of {m_parseOptions.MaxFiles} has been exceeded"); - } - - // Get the file ID - var fileId = context.GetFileId(path); - - // Check the cache - if (!m_cache.TryGetValue(path, out String fileContent)) - { - // Fetch the file - context.CancellationToken.ThrowIfCancellationRequested(); - fileContent = m_fileProvider.GetFileContent(path); - - // Validate max file size - if (fileContent.Length > m_parseOptions.MaxFileSize) - { - throw new InvalidOperationException($"The maximum file size of {m_parseOptions.MaxFileSize} characters has been exceeded"); - } - - // Cache - m_cache[path] = fileContent; - } - - // Deserialize - var token = default(TemplateToken); - using (var stringReader = new StringReader(fileContent)) - { - var yamlObjectReader = new YamlObjectReader(fileId, stringReader); - token = TemplateReader.Read(context, templateType, yamlObjectReader, fileId, out _); - } - - // Trace - if (!isEntryFile) - { - context.TraceWriter.Info(String.Empty); - } - context.TraceWriter.Info("# "); - context.TraceWriter.Info("# {0}", path); - context.TraceWriter.Info("# "); - - // Validate ref names - if (context.Errors.Count == 0) - { - switch (templateType) - { - case PipelineTemplateConstants.WorkflowRoot: - ValidateWorkflow(context, scope, token); - break; - case PipelineTemplateConstants.StepsTemplateRoot: - var stepsTemplate = token.AssertMapping("steps template"); - foreach (var stepsTemplateProperty in stepsTemplate) - { - var stepsTemplatePropertyName = stepsTemplateProperty.Key.AssertString("steps template property name"); - switch (stepsTemplatePropertyName.Value) - { - case PipelineTemplateConstants.Steps: - ValidateSteps(context, scope, stepsTemplateProperty.Value); - break; - } - } - break; - default: - throw new NotImplementedException($"Unexpected template type '{templateType}' when loading yaml file"); - } - } - - return token; - } - - private void ValidateWorkflow( - TemplateContext context, - String scope, - TemplateToken token) - { - var workflow = token.AssertMapping("workflow"); - foreach (var workflowProperty in workflow) - { - var workflowPropertyName = workflowProperty.Key.AssertString("workflow property name"); - switch (workflowPropertyName.Value) - { - case PipelineTemplateConstants.Jobs: - case PipelineTemplateConstants.Workflow: - var jobs = workflowProperty.Value.AssertMapping("workflow property value"); - foreach (var jobsProperty in jobs) - { - var job = jobsProperty.Value.AssertMapping("jobs property value"); - foreach (var jobProperty in job) - { - var jobPropertyName = jobProperty.Key.AssertString("job property name"); - switch (jobPropertyName.Value) - { - case PipelineTemplateConstants.Steps: - ValidateSteps(context, scope, jobProperty.Value); - break; - } - } - } - break; - } - } - } - - private void ValidateSteps( - TemplateContext context, - String scope, - TemplateToken token) - { - var nameBuilder = new ReferenceNameBuilder(); - var steps = token.AssertSequence("steps"); - var needsReferenceName = new List(); - foreach (var stepsItem in steps) - { - var step = stepsItem.AssertMapping("steps item"); - var isTemplateReference = false; - var hasReferenceName = false; - foreach (var stepProperty in step) - { - var stepPropertyKey = stepProperty.Key.AssertString("step property name"); - switch (stepPropertyKey.Value) - { - // Validate reference names - case PipelineTemplateConstants.Id: - var referenceNameLiteral = stepProperty.Value.AssertString("step ID"); - var referenceName = referenceNameLiteral.Value; - if (String.IsNullOrEmpty(referenceName)) - { - continue; - } - - if (!nameBuilder.TryAddKnownName(referenceName, out var error)) - { - context.Error(referenceNameLiteral, error); - } - - hasReferenceName = true; - break; - - case PipelineTemplateConstants.Template: - isTemplateReference = true; - break; - } - } - - // No reference name - if (isTemplateReference && !hasReferenceName) - { - needsReferenceName.Add(step); - } - - // Stamp the scope - if (!String.IsNullOrEmpty(scope)) - { - var scopePropertyName = new StringToken(null, null, null, PipelineTemplateConstants.Scope); - var scopePropertyValue = new StringToken(null, null, null, scope); - step.Add(scopePropertyName, scopePropertyValue); - context.Memory.AddBytes(scopePropertyName); - context.Memory.AddBytes(scopePropertyValue); - } - } - - // Generate reference names - if (needsReferenceName.Count > 0 && context.Errors.Count == 0) - { - foreach (var step in needsReferenceName) - { - // Get the template path - var templatePath = default(String); - foreach (var stepProperty in step) - { - var stepPropertyKey = stepProperty.Key.AssertString("step property name"); - switch (stepPropertyKey.Value) - { - case PipelineTemplateConstants.Template: - var templateStringToken = stepProperty.Value.AssertString("step template path"); - templatePath = templateStringToken.Value; - break; - } - } - - // Generate reference name - if (!String.IsNullOrEmpty(templatePath)) - { - nameBuilder.AppendSegment(templatePath); - var generatedIdPropertyName = new StringToken(null, null, null, PipelineTemplateConstants.GeneratedId); - var generatedIdPropertyValue = new StringToken(null, null, null, nameBuilder.Build()); - step.Add(generatedIdPropertyName, generatedIdPropertyValue); - context.Memory.AddBytes(generatedIdPropertyName); - context.Memory.AddBytes(generatedIdPropertyValue); - } - } - } - } - - /// - /// Cache of file content - /// - private readonly Dictionary m_cache = new Dictionary(StringComparer.OrdinalIgnoreCase); - - private readonly IFileProvider m_fileProvider; - - private readonly ParseOptions m_parseOptions; - - /// - /// Tracks unique file references - /// - private readonly HashSet m_referencedFiles = new HashSet(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PackageStore.cs b/src/Sdk/DTPipelines/Pipelines/PackageStore.cs deleted file mode 100644 index 20fc8704a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PackageStore.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - public interface IPackageResolver - { - IList GetPackages(String packageType); - } - - public class PackageStore : IPackageStore - { - public PackageStore(params PackageMetadata[] packages) - : this(packages, null) - { - } - - public PackageStore( - IEnumerable packages = null, - IPackageResolver resolver = null) - { - this.Resolver = resolver; - m_packages = packages?.GroupBy(x => x.Type).ToDictionary(x => x.Key, x => x.ToList(), StringComparer.OrdinalIgnoreCase) ?? - new Dictionary>(StringComparer.OrdinalIgnoreCase); - } - - public IPackageResolver Resolver - { - get; - } - - public PackageVersion GetLatestVersion(String packageType) - { - if (!m_packages.TryGetValue(packageType, out var existingPackages)) - { - var resolvedPackages = this.Resolver?.GetPackages(packageType); - if (resolvedPackages?.Count > 0) - { - existingPackages = resolvedPackages.ToList(); - m_packages[packageType] = existingPackages; - } - } - - return existingPackages?.OrderByDescending(x => x.Version).Select(x => x.Version).FirstOrDefault(); - } - - private Dictionary> m_packages; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ParallelExecutionOptions.cs b/src/Sdk/DTPipelines/Pipelines/ParallelExecutionOptions.cs deleted file mode 100644 index 5bd5be2c4..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ParallelExecutionOptions.cs +++ /dev/null @@ -1,315 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class ParallelExecutionOptions - { - public ParallelExecutionOptions() - { - } - - private ParallelExecutionOptions(ParallelExecutionOptions optionsToCopy) - { - this.Matrix = optionsToCopy.Matrix; - this.MaxConcurrency = optionsToCopy.MaxConcurrency; - } - - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter>>))] - public ExpressionValue>> Matrix - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue MaxConcurrency - { - get; - set; - } - - public ParallelExecutionOptions Clone() - { - return new ParallelExecutionOptions(this); - } - - internal JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String jobName, - Int32 attempt, - ExpressionValue container, - IDictionary> sidecarContainers, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory) - { - // perform regular expansion with a filter - var options = new JobExpansionOptions(jobName, attempt); - - return GenerateJobContexts( - context, - container, - sidecarContainers, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory, - options) - .FirstOrDefault(); - } - - internal ExpandPhaseResult Expand( - PhaseExecutionContext context, - ExpressionValue container, - IDictionary> sidecarContainers, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory, - JobExpansionOptions options) - { - var jobContexts = GenerateJobContexts( - context, - container, - sidecarContainers, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory, - options); - - var result = new ExpandPhaseResult(); - foreach (var c in jobContexts) - { - result.Jobs.Add(c.Job); - } - - // parse MaxConcurrency request - var numberOfJobs = jobContexts.Count; - var userProvidedValue = context.Evaluate( - name: nameof(MaxConcurrency), - expression: this.MaxConcurrency, - defaultValue: 0).Value; - - // setting max to 0 or less is shorthand for "unlimited" - if (userProvidedValue <= 0) - { - userProvidedValue = numberOfJobs; - } - - result.MaxConcurrency = userProvidedValue; - return result; - } - - internal IList GenerateJobContexts( - PhaseExecutionContext context, - ExpressionValue container, - IDictionary> sidecarContainers, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory, - JobExpansionOptions options) - { - // We don't want job variables to be set into the phase context so we create a child context for each unique configuration - var jobContexts = new List(); - void GenerateContext( - String displayName, - String configuration, - IDictionary configurationVariables = null, - String parallelExecutionType = null, - Int32 positionInPhase = 1, - Int32 totalJobsInPhase = 1) - { - // configurations should (eventually) follow configuration naming conventions - if (String.IsNullOrEmpty(configuration)) - { - configuration = PipelineConstants.DefaultJobName; - } - - // Determine attempt number. - // if we have a custom value, it wins. - // if we have previously attempted this configuration, - // the new attempt number is one greater than the previous. - // 1 is the minimum attempt number - var attemptNumber = options?.GetAttemptNumber(configuration) ?? -1; - if (attemptNumber < 1) - { - var previousAttempt = context.PreviousAttempt; - if (previousAttempt != null) - { - var jobInstance = context.PreviousAttempt?.Jobs.FirstOrDefault(x => x.Job.Name.Equals(configuration, StringComparison.OrdinalIgnoreCase)); - if (jobInstance != null) - { - attemptNumber = jobInstance.Job.Attempt + 1; - } - } - } - - if (attemptNumber < 1) - { - attemptNumber = 1; - } - - var jobContext = context.CreateJobContext( - name: configuration, - attempt: attemptNumber, - positionInPhase, - totalJobsInPhase); - - // add parallel execution type - if (parallelExecutionType != null) - { - jobContext.SetSystemVariables(new List - { - new Variable - { - Name = WellKnownDistributedTaskVariables.ParallelExecutionType, - Value = parallelExecutionType - } - }); - } - - if (configurationVariables != null) - { - jobContext.SetUserVariables(configurationVariables); - } - - // create job model from factory - jobContext.Job.Definition = jobFactory.CreateJob( - jobContext, - container, - sidecarContainers, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - displayName); - - jobContexts.Add(jobContext); - - if (jobContexts.Count > context.ExecutionOptions.MaxJobExpansion) - { - // Note: this is a little weird: it might be that the max concurrency is greater than the max expansion, - // but we only throw if we actually try to generate more jobs than the max expansion. - throw new MaxJobExpansionException(PipelineStrings.PhaseJobSlicingExpansionExceedLimit(jobContexts.Count.ToString(), context.ExecutionOptions.MaxJobExpansion)); - } - } - - if (this.Matrix != null) - { - var matrixValue = context.Evaluate(nameof(Matrix), this.Matrix, null, traceDefault: false).Value; - var numberOfConfigurations = matrixValue?.Count ?? 0; - if (numberOfConfigurations > 0) - { - var positionInPhase = 1; - foreach (var pair in matrixValue) - { - // user-provided configuration key - var configuration = pair.Key; - var refName = configuration; - if (!PipelineUtilities.IsLegalNodeName(refName)) - { - var legalNodeName = PipelineConstants.DefaultJobDisplayName + positionInPhase.ToString(); - context.Trace?.Info($"\"{refName}\" is not a legal node name; node will be named \"{legalNodeName}\"."); - if (context.ExecutionOptions.EnforceLegalNodeNames) - { - refName = legalNodeName; - } - } - - if (options == null || options.IsIncluded(refName)) - { - GenerateContext( - displayName: Phase.GenerateDisplayName(context.Phase.Definition, configuration), - configuration: refName, - configurationVariables: pair.Value, - parallelExecutionType: "MultiConfiguration", - positionInPhase: positionInPhase, - totalJobsInPhase: numberOfConfigurations); - } - - ++positionInPhase; - } - } - } - else if (this.MaxConcurrency is var maxConcurrencyPipelineValue && maxConcurrencyPipelineValue != null) - { - var maxConcurrency = context.Evaluate(nameof(maxConcurrencyPipelineValue), maxConcurrencyPipelineValue, 1).Value; - - //If the value of context.ExecutionOptions.MaxParallelism is set, we will enforce MaxConcurrency value to be not more than context.ExecutionOptions.MaxParallelism. - //context.ExecutionOptions.MaxParallelism is currently set if the current context is hosted and public, especially to avoid abuse of services. - if (maxConcurrency > context.ExecutionOptions.MaxParallelism) - { - maxConcurrency = context.ExecutionOptions.MaxParallelism.Value; - } - - if (maxConcurrency > 1) - { - if (options == null || options.Configurations == null || options.Configurations.Count == 0) - { - // generate all slices - for (var positionInPhase = 1; positionInPhase <= maxConcurrency; ++positionInPhase) - { - // NOTE: for historical reasons, the reference name of a slice is "Job" plus the slice number: "Job1" - var positionInPhaseString = positionInPhase.ToString(); - GenerateContext( - displayName: Phase.GenerateDisplayName(context.Phase.Definition, positionInPhaseString), - configuration: PipelineConstants.DefaultJobDisplayName + positionInPhaseString, - configurationVariables: null, - parallelExecutionType: "MultiMachine", - positionInPhase: positionInPhase, - totalJobsInPhase: maxConcurrency); - } - } - else - { - // generate only the requested slices - foreach (var configuration in options.Configurations.Keys) - { - // determine which slices are required by parsing the configuration name (see generation code above) - var prefix = PipelineConstants.DefaultJobDisplayName; - if (!configuration.StartsWith(prefix, StringComparison.OrdinalIgnoreCase) - || !int.TryParse(configuration.Substring(prefix.Length), out var positionInPhase)) - throw new PipelineValidationException(PipelineStrings.PipelineNotValid()); - - GenerateContext( - displayName: Phase.GenerateDisplayName(context.Phase.Definition, positionInPhase.ToString()), - configuration: configuration, - configurationVariables: null, - parallelExecutionType: "MultiMachine", - positionInPhase: positionInPhase, - totalJobsInPhase: maxConcurrency); - } - } - } - } - - // if no contexts are produced otherwise, create a default context. - if (jobContexts.Count == 0) - { - var configuration = PipelineConstants.DefaultJobName; - if (options == null || options.IsIncluded(configuration)) - { - // the default display name is just the JobFactory display name - GenerateContext( - displayName: Phase.GenerateDisplayName(context.Phase.Definition), - configuration: configuration); - } - } - - return jobContexts; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Phase.cs b/src/Sdk/DTPipelines/Pipelines/Phase.cs deleted file mode 100644 index 2f44e4afc..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Phase.cs +++ /dev/null @@ -1,1677 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.ObjectModel; -using System.ComponentModel; -using System.Diagnostics; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class Phase : PhaseNode, IJobFactory - { - public Phase() - { - } - - private Phase(Phase phaseToCopy) - : base(phaseToCopy) - { - if (phaseToCopy.m_steps != null && phaseToCopy.m_steps.Count > 0) - { - m_steps = new List(phaseToCopy.m_steps.Select(x => x.Clone())); - } - } - - /// - /// Gets the phase type. - /// - [DataMember(EmitDefaultValue = false)] - public override PhaseType Type => PhaseType.Phase; - - /// - /// Gets the list of steps associated with this phase. At runtime the steps will be used as a template for - /// the execution of a job. - /// - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - /// - /// Creates the specified job using the provided execution context and name. A new execution context is - /// returned which includes new variables set by the job. - /// - /// The execution context - /// The name of the job which should be created - /// A job and execution context if the specified name exists; otherwise, null - public JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String name, - Int32 attempt) - { - ArgumentUtility.CheckForNull(this.Target, nameof(this.Target)); - - // Create a copy of the context so the same root context may be used to create multiple jobs - // without impacting the input context. - return this.Target.CreateJobContext(context, name, attempt, this); - } - - /// - /// Creates a job context using the provided phase context and existing job instance. A new context is - /// returned which includes new variables set by the job. - /// - /// The execution context - /// The existing job instance - /// A job execution context - public JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - JobInstance jobInstance) - { - var jobContext = context.CreateJobContext(jobInstance); - jobContext.Job.Definition.Id = jobContext.GetInstanceId(); - - var options = new BuildOptions(); - var builder = new PipelineBuilder(context); - var result = builder.GetReferenceResources(jobInstance.Definition.Steps.OfType().ToList(), jobInstance.Definition.Target); - jobContext.ReferencedResources.MergeWith(result); - - // Update the execution context with referenced job containers - var containerAlias = (jobInstance.Definition.Container as DistributedTask.ObjectTemplating.Tokens.StringToken)?.Value; - if (!String.IsNullOrEmpty(containerAlias)) - { - UpdateJobContextReferencedContainers(jobContext, containerAlias); - } - var sidecarContainers = jobInstance.Definition.SidecarContainers; - if (sidecarContainers != null) - { - foreach (var sidecar in sidecarContainers) - { - // Sidecar is serviceName -> containerAlias, e.g. ngnix: containerAlias - UpdateJobContextReferencedContainers(jobContext, sidecar.Value); - } - } - // Update the execution context with the job-specific system variables - UpdateJobContextVariablesFromJob(jobContext, jobInstance.Definition); - - return jobContext; - } - - /// - /// Expands the template using the provided execution context and returns the list of jobs. - /// - /// The execution context - /// The expansion options to use - /// A list of jobs which should be executed for this phase - public ExpandPhaseResult Expand( - PhaseExecutionContext context, - JobExpansionOptions options = null) - { - ArgumentUtility.CheckForNull(this.Target, nameof(this.Target)); - - var result = this.Target.Expand(context, this, options); - if (result != null) - { - var runtimeValue = this.ContinueOnError?.GetValue(context); - result.ContinueOnError = runtimeValue?.Value ?? false; - } - - return result; - } - - internal static String GetErrorMessage( - String code, - params Object[] values) - { - var stageName = (String)values[0]; - if (String.IsNullOrEmpty(stageName) || - stageName.Equals(PipelineConstants.DefaultJobName, StringComparison.OrdinalIgnoreCase)) - { - switch (code) - { - case PipelineConstants.NameInvalid: - return PipelineStrings.PhaseNameInvalid(values[1]); - - case PipelineConstants.NameNotUnique: - return PipelineStrings.PhaseNamesMustBeUnique(values[1]); - - case PipelineConstants.StartingPointNotFound: - return PipelineStrings.PipelineNotValidNoStartingPhase(); - - case PipelineConstants.DependencyNotFound: - return PipelineStrings.PhaseDependencyNotFound(values[1], values[2]); - - case PipelineConstants.GraphContainsCycle: - return PipelineStrings.PhaseGraphCycleDetected(values[1], values[2]); - } - } - else - { - switch (code) - { - case PipelineConstants.NameInvalid: - return PipelineStrings.StagePhaseNameInvalid(values[0], values[1]); - - case PipelineConstants.NameNotUnique: - return PipelineStrings.StagePhaseNamesMustBeUnique(values[0], values[1]); - - case PipelineConstants.StartingPointNotFound: - return PipelineStrings.StageNotValidNoStartingPhase(values[0]); - - case PipelineConstants.DependencyNotFound: - return PipelineStrings.StagePhaseDependencyNotFound(values[0], values[1], values[2]); - - case PipelineConstants.GraphContainsCycle: - return PipelineStrings.StagePhaseGraphCycleDetected(values[0], values[1], values[2]); - } - } - - throw new NotSupportedException(); - } - - /// - /// Resolves external references and ensures the steps are compatible with the selected target. - /// - /// The validation context - public override void Validate( - PipelineBuildContext context, - ValidationResult result) - { - base.Validate(context, result); - - StepValidationResult phaseStepValidationResult = new StepValidationResult(); - // Require the latest agent version. - if (context.BuildOptions.DemandLatestAgent) - { - var latestPackageVersion = context.PackageStore?.GetLatestVersion(WellKnownPackageTypes.Agent); - if (latestPackageVersion == null) - { - throw new NotSupportedException("Unable to determine the latest agent package version"); - } - - phaseStepValidationResult.MinAgentVersion = latestPackageVersion.ToString(); - } - - if (context.EnvironmentVersion < 2) - { - // environment version 1 should has at most 1 checkout step, the position of the checkout task might not be the fisrt one of there is an Azure keyvault task - var checkoutStep = this.Steps.SingleOrDefault(x => x.IsCheckoutTask()); - if (checkoutStep != null) - { - if ((checkoutStep as TaskStep).Inputs[PipelineConstants.CheckoutTaskInputs.Repository] == PipelineConstants.NoneAlias) - { - this.Variables.Add(new Variable() { Name = "agent.source.skip", Value = Boolean.TrueString }); - } - - this.Steps.Remove(checkoutStep); - } - } - - ValidateSteps(context, this, Target, result, this.Steps, phaseStepValidationResult); - - // Resolve the target to ensure we have stable identifiers for the orchestration engine - // phase targets with expressions need to be evaluated against resolved job contexts. - bool validateTarget = false; - if (this.Target.Type == PhaseTargetType.Pool || this.Target.Type == PhaseTargetType.Server) - { - validateTarget = true; - } - else if (this.Target is AgentQueueTarget agentQueueTarget && agentQueueTarget.IsLiteral()) - { - validateTarget = true; - } - - if (validateTarget) - { - this.Target.Validate( - context, - context.BuildOptions, - result, - this.Steps, - phaseStepValidationResult.TaskDemands); - } - } - - // todo: merge JobFactory.cs and Phase.cs and then make this private - internal static void ValidateSteps( - PipelineBuildContext context, - PhaseNode phase, - PhaseTarget phaseTarget, - ValidationResult result, - IList steps, - StepValidationResult phaseStepValidationResult) - { - var stepsCopy = new List(); - foreach (var step in steps) - { - // Skip if not enabled on the definition. - if (!step.Enabled) - { - continue; - } - - if (step.Type == StepType.Task) - { - var taskErrors = ValidateTaskStep(context, phase, phaseTarget, result.ReferencedResources, result.UnauthorizedResources, (step as TaskStep), phaseStepValidationResult); - if (taskErrors.Count == 0) - { - stepsCopy.Add(step); - } - else - { - result.Errors.AddRange(taskErrors); - } - } - else if (step.Type == StepType.Group) - { - var groupErrors = ValidateGroupStep(context, phase, phaseTarget, result.ReferencedResources, result.UnauthorizedResources, (step as GroupStep), phaseStepValidationResult); - if (groupErrors.Count == 0) - { - stepsCopy.Add(step); - } - else - { - result.Errors.AddRange(groupErrors); - } - } - else if (step.Type == StepType.Action) - { - var actionErrors = ValidateActionStep(context, phase, step as ActionStep, phaseStepValidationResult); - if (actionErrors.Count == 0) - { - stepsCopy.Add(step); - } - else - { - result.Errors.AddRange(actionErrors); - } - } - else - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.StepNotSupported())); - } - } - - // Now replace the steps list with our updated list based on disabled/missing tasks - steps.Clear(); - steps.AddRange(stepsCopy); - - // Now go through any tasks which did not have a name specified and name them according to how many - // of that specific task is present. - if (phaseStepValidationResult.UnnamedSteps.Count > 0) - { - GenerateDefaultTaskNames(phaseStepValidationResult.KnownNames, phaseStepValidationResult.UnnamedSteps); - } - - // Make sure our computed minimum agent version is included with the task demands - if (phaseStepValidationResult.MinAgentVersion != null) - { - phaseStepValidationResult.TaskDemands.Add(new DemandMinimumVersion(PipelineConstants.AgentVersionDemandName, phaseStepValidationResult.MinAgentVersion)); - } - } - - private static List ValidateActionStep( - PipelineBuildContext context, - PhaseNode phase, - ActionStep actionStep, - StepValidationResult stepValidationResult) - { - List actionErrors = new List(); - - // We need an action reference to a contianer image or repository - if (actionStep.Reference == null) - { - // Stop checking further since we can't even find an action definition - actionErrors.Add(new PipelineValidationError(PipelineStrings.StepActionReferenceInvalid(phase.Name, actionStep.Name))); - return actionErrors; - } - - string defaultActionName = ""; - if (actionStep.Reference.Type == ActionSourceType.ContainerRegistry) - { - // action is reference to an image from container registry - var containerAction = actionStep.Reference as ContainerRegistryReference; - defaultActionName = NameValidation.Sanitize(containerAction.Image, context.BuildOptions.AllowHyphenNames); - } - else if (actionStep.Reference.Type == ActionSourceType.Repository) - { - // action is reference to dockerfile or action.js from a git repository - var repoAction = actionStep.Reference as RepositoryPathReference; - defaultActionName = NameValidation.Sanitize(repoAction.Name ?? PipelineConstants.SelfAlias, context.BuildOptions.AllowHyphenNames); - } - else if (actionStep.Reference.Type == ActionSourceType.Script) - { - defaultActionName = "run"; - } - else - { - actionErrors.Add(new PipelineValidationError(PipelineStrings.TaskStepReferenceInvalid(phase.Name, actionStep.Name, actionStep.Reference.Type))); - } - - // Validate task name - var stepNameError = ValidateStepName(context, phase, stepValidationResult, actionStep, defaultActionName); - if (stepNameError != null) - { - actionErrors.Add(stepNameError); - } - - return actionErrors; - } - - private static List ValidateTaskStep( - PipelineBuildContext context, - PhaseNode phase, - PhaseTarget phaseTarget, - PipelineResources referencedResources, - PipelineResources unauthorizedResources, - TaskStep taskStep, - StepValidationResult stepValidationResult) - { - List taskErrors = new List(); - - // We need either a task name or an identifier and a version. - if (taskStep.Reference == null || - taskStep.Reference.Version == null || - (taskStep.Reference.Id == Guid.Empty && String.IsNullOrEmpty(taskStep.Reference.Name))) - { - // Stop checking further since we can't even resolve task definition - taskErrors.Add(new PipelineValidationError(PipelineStrings.StepTaskReferenceInvalid(phase.Name, taskStep.Name))); - return taskErrors; - } - - // Try to resolve by the identifier first, then by name - TaskDefinition resolvedTask = null; - try - { - if (taskStep.Reference.Id != Guid.Empty) - { - resolvedTask = context.TaskStore?.ResolveTask(taskStep.Reference.Id, taskStep.Reference.Version); - } - else if (!String.IsNullOrEmpty(taskStep.Reference.Name)) - { - resolvedTask = context.TaskStore?.ResolveTask(taskStep.Reference.Name, taskStep.Reference.Version); - } - } - catch (AmbiguousTaskSpecificationException ex) - { - // Stop checking further since we can't even resolve task definition - taskErrors.Add(new PipelineValidationError(PipelineStrings.TaskStepReferenceInvalid(phase.Name, taskStep.Name, ex.Message))); - return taskErrors; - } - - // Make sure we were able to find the task with the provided reference data - if (resolvedTask == null || resolvedTask.Disabled) - { - // Stop checking further since we can't even resolve task definition - String name = taskStep.Reference.Id != Guid.Empty ? taskStep.Reference.Id.ToString() : taskStep.Reference.Name; - taskErrors.Add(new PipelineValidationError(PipelineStrings.TaskMissing(phase.Name, taskStep.Name, name, taskStep.Reference.Version))); - return taskErrors; - } - - // Make sure this step is compatible with the target used by this phase - if (phaseTarget.IsValid(resolvedTask) == false) - { - // Stop checking further since the task is not for valid for the target - taskErrors.Add(new PipelineValidationError(PipelineStrings.TaskInvalidForGivenTarget(phase.Name, taskStep.Name, resolvedTask.Name, resolvedTask.Version))); - return taskErrors; - } - - // Resolve the task version to pin a given task for the duration of the plan - taskStep.Reference.Id = resolvedTask.Id; - taskStep.Reference.Name = resolvedTask.Name; - taskStep.Reference.Version = resolvedTask.Version; - - // Make sure that we have valid syntax for a condition statement - var conditionError = ValidateStepCondition(context, phase, taskStep.Name, taskStep.Condition); - if (conditionError != null) - { - taskErrors.Add(conditionError); - } - - // Resolves values from inputs based on the provided validation options - var inputErrors = ResolveInputs(context, phase, referencedResources, unauthorizedResources, taskStep, resolvedTask); - if (inputErrors.Count > 0) - { - taskErrors.AddRange(inputErrors); - } - - // Task names do not have to correspond to the same rules as reference names, so we need to remove - // any characters which are considered invalid for a reference name from the task definition name. - var defaultTaskName = NameValidation.Sanitize(taskStep.Reference.Name, context.BuildOptions.AllowHyphenNames); - - // Validate task name - var stepNameError = ValidateStepName(context, phase, stepValidationResult, taskStep, defaultTaskName); - if (stepNameError != null) - { - taskErrors.Add(stepNameError); - } - - // Now union any demand which are satisifed by tasks within the job - stepValidationResult.TasksSatisfy.UnionWith(resolvedTask.Satisfies); - - stepValidationResult.MinAgentVersion = resolvedTask.GetMinimumAgentVersion(stepValidationResult.MinAgentVersion); - - // Add demands from task - var unsatisfiedDemands = resolvedTask.Demands.Where(d => !stepValidationResult.TasksSatisfy.Contains(d.Name)); - if (unsatisfiedDemands.Any()) - { - stepValidationResult.TaskDemands.UnionWith(unsatisfiedDemands); - } - - return taskErrors; - } - - private static List ValidateGroupStep( - PipelineBuildContext context, - PhaseNode phase, - PhaseTarget phaseTarget, - PipelineResources referencedResources, - PipelineResources unauthorizedResources, - GroupStep groupStep, - StepValidationResult stepValidationResult) - { - List groupErrors = new List(); - - // Make sure that we have valid syntax for a condition statement - var conditionError = ValidateStepCondition(context, phase, groupStep.Name, groupStep.Condition); - if (conditionError != null) - { - groupErrors.Add(conditionError); - } - - // ValidationResult for steps within group, since only steps within a group need to have unique task.name - StepValidationResult groupStepsValidationResult = new StepValidationResult(); - - var stepsCopy = new List(); - foreach (var step in groupStep.Steps) - { - // Skip if not enabled on the definition. - if (!step.Enabled) - { - continue; - } - - var taskErrors = ValidateTaskStep(context, phase, phaseTarget, referencedResources, unauthorizedResources, step, groupStepsValidationResult); - if (taskErrors.Count == 0) - { - stepsCopy.Add(step); - } - else - { - groupErrors.AddRange(taskErrors); - } - } - - // Now replace the steps list with our updated list based on disabled/missing tasks - groupStep.Steps.Clear(); - groupStep.Steps.AddRange(stepsCopy); - - // Merge group steps validation result - if (groupStepsValidationResult.UnnamedSteps.Count > 0) - { - // Now go through any tasks within a group which did not have a name specified and name them according to how many - // of that specific task is present. - GenerateDefaultTaskNames(groupStepsValidationResult.KnownNames, groupStepsValidationResult.UnnamedSteps); - } - - // If group min agent version > current min agent version - if (DemandMinimumVersion.CompareVersion(groupStepsValidationResult.MinAgentVersion, stepValidationResult.MinAgentVersion) > 0) - { - stepValidationResult.MinAgentVersion = groupStepsValidationResult.MinAgentVersion; - } - - // Add tasks satisfies provided by the group - stepValidationResult.TasksSatisfy.UnionWith(groupStepsValidationResult.TasksSatisfy); - - // Add demands come from tasks within the group - var unsatisfiedDemands = groupStepsValidationResult.TaskDemands.Where(d => !stepValidationResult.TasksSatisfy.Contains(d.Name)); - if (unsatisfiedDemands.Any()) - { - stepValidationResult.TaskDemands.UnionWith(unsatisfiedDemands); - } - - // Validate group name - var stepNameError = ValidateStepName(context, phase, stepValidationResult, groupStep, "group"); - if (stepNameError != null) - { - groupErrors.Add(stepNameError); - } - - return groupErrors; - } - - private static PipelineValidationError ValidateStepName( - PipelineBuildContext context, - PhaseNode phase, - StepValidationResult stepValidationResult, - JobStep step, - String defaultName) - { - if (String.IsNullOrEmpty(step.Name)) - { - List stepsToName; - if (!stepValidationResult.UnnamedSteps.TryGetValue(defaultName, out stepsToName)) - { - stepsToName = new List(); - stepValidationResult.UnnamedSteps.Add(defaultName, stepsToName); - } - - stepsToName.Add(step); - - if (String.IsNullOrEmpty(step.DisplayName)) - { - step.DisplayName = defaultName; - } - } - else - { - bool nameIsValid = NameValidation.IsValid(step.Name, context.BuildOptions.AllowHyphenNames); - if (!nameIsValid) - { - if (context.BuildOptions.ValidateStepNames) - { - return new PipelineValidationError(PipelineStrings.StepNameInvalid(phase.Name, step.Name)); - } - else - { - var sanitizedName = NameValidation.Sanitize(step.Name, context.BuildOptions.AllowHyphenNames); - if (String.IsNullOrEmpty(sanitizedName)) - { - sanitizedName = defaultName; - } - - step.Name = sanitizedName; - nameIsValid = true; - } - } - - if (nameIsValid && !stepValidationResult.KnownNames.Add(step.Name)) - { - if (context.BuildOptions.ValidateStepNames) - { - return new PipelineValidationError(PipelineStrings.StepNamesMustBeUnique(phase.Name, step.Name)); - } - else - { - List stepsToName; - if (!stepValidationResult.UnnamedSteps.TryGetValue(step.Name, out stepsToName)) - { - stepsToName = new List(); - stepValidationResult.UnnamedSteps.Add(step.Name, stepsToName); - } - - stepsToName.Add(step); - } - } - - // If the name was specified but the display name is empty, default the display name to the name - if (String.IsNullOrEmpty(step.DisplayName)) - { - step.DisplayName = step.Name; - } - } - - return null; - } - - private static PipelineValidationError ValidateStepCondition( - PipelineBuildContext context, - PhaseNode phase, - String stepName, - String stepCondition) - { - if (!String.IsNullOrEmpty(stepCondition)) - { - try - { - var parser = new DistributedTask.Expressions.ExpressionParser(); - parser.ValidateSyntax(stepCondition, null); - } - catch (ParseException ex) - { - return new PipelineValidationError(PipelineStrings.StepConditionIsNotValid(phase.Name, stepName, stepCondition, ex.Message)); - } - } - - return null; - } - - private static void GenerateDefaultTaskNames( - ISet knownNames, - IDictionary> unnamedTasks) - { - foreach (var unnamedTasksByName in unnamedTasks) - { - if (unnamedTasksByName.Value.Count == 1 && knownNames.Add(unnamedTasksByName.Key)) - { - unnamedTasksByName.Value[0].Name = unnamedTasksByName.Key; - } - else - { - Int32 taskCounter = 1; - foreach (var unnamedTask in unnamedTasksByName.Value) - { - var candidateName = $"{unnamedTasksByName.Key}{taskCounter}"; - while (!knownNames.Add(candidateName)) - { - taskCounter++; - candidateName = $"{unnamedTasksByName.Key}{taskCounter}"; - } - - taskCounter++; - unnamedTask.Name = candidateName; - } - } - } - } - - private static IList ResolveInputs( - PipelineBuildContext context, - PhaseNode phase, - PipelineResources referencedResources, - PipelineResources unauthorizedResources, - TaskStep step, - TaskDefinition taskDefinition) - { - IList errors = new List(); - foreach (var input in taskDefinition.Inputs) - { - // Resolve by alias - var inputAlias = ResolveAlias(context, step, input); - - // If the input isn't set then there is nothing else to do here - if (!step.Inputs.TryGetValue(input.Name, out String inputValue)) - { - continue; - } - - // If the caller requested input validation and the input provides a validation section then we - // should do a best-effort validation based on what is available in the environment. - errors.AddRange(ValidateInput(context, phase, step, input, inputAlias, inputValue)); - - // Now resolve any resources referenced by task inputs - errors.AddRange(ResolveResources(context, phase, context.BuildOptions, referencedResources, unauthorizedResources, step, input, inputAlias, inputValue, throwOnFailure: false)); - } - - return errors; - } - - private static String ResolveAlias( - PipelineBuildContext context, - TaskStep step, - TaskInputDefinition input) - { - var specifiedName = input.Name; - if (context.BuildOptions.ResolveTaskInputAliases && !step.Inputs.ContainsKey(input.Name)) - { - foreach (String alias in input.Aliases) - { - if (step.Inputs.TryGetValue(alias, out String aliasValue)) - { - specifiedName = alias; - step.Inputs.Remove(alias); - step.Inputs.Add(input.Name, aliasValue); - break; - } - } - } - return specifiedName; - } - - private static IEnumerable ResolveResources( - IPipelineContext context, - PhaseNode phase, - BuildOptions options, - PipelineResources referencedResources, - PipelineResources unauthorizedResources, - TaskStep step, - TaskInputDefinition input, - String inputAlias, - String inputValue, - Boolean throwOnFailure = false) - { - if (String.IsNullOrEmpty(inputValue)) - { - return Enumerable.Empty(); - } - - var errors = new List(); - if (input.InputType.StartsWith(c_endpointInputTypePrefix, StringComparison.OrdinalIgnoreCase)) - { - var resolvedEndpoints = new List(); - var endpointType = input.InputType.Remove(0, c_endpointInputTypePrefix.Length); - var resolvedInputValues = inputValue.Split(',').Select(x => x.Trim()).Where(x => !String.IsNullOrEmpty(x)); - foreach (var value in resolvedInputValues) - { - var replacedValue = context.ExpandVariables(value); - referencedResources.AddEndpointReference(replacedValue); - - // Validate the resource using the provided store if desired - if (options.ValidateResources) - { - var endpoint = context.ResourceStore.GetEndpoint(replacedValue); - if (endpoint == null) - { - if (throwOnFailure) - { - throw new ResourceNotFoundException(PipelineStrings.ServiceEndpointNotFoundForInput(phase.Name, step.Name, inputAlias, replacedValue)); - } - else - { - resolvedEndpoints.Add(replacedValue); - unauthorizedResources?.AddEndpointReference(replacedValue); - errors.Add(new PipelineValidationError(PipelineStrings.ServiceEndpointNotFoundForInput(phase.Name, step.Name, inputAlias, replacedValue))); - } - } - else - { - if (!String.IsNullOrEmpty(endpointType)) - { - var endpointTypeSegments = endpointType.Split(new[] { ':' }, StringSplitOptions.RemoveEmptyEntries).Select(x => x.Trim()).ToList(); - if (endpointTypeSegments.Count >= 1) - { - var endpointTypeName = endpointTypeSegments[0]; - if (!endpointTypeName.Equals(endpoint.Type, StringComparison.OrdinalIgnoreCase)) - { - if (throwOnFailure) - { - throw new PipelineValidationException(PipelineStrings.StepInputEndpointTypeMismatch(phase.Name, step.Name, inputAlias, endpointTypeName, endpoint.Name, endpoint.Type)); - } - else - { - errors.Add(new PipelineValidationError(PipelineStrings.StepInputEndpointTypeMismatch(phase.Name, step.Name, inputAlias, endpointTypeName, endpoint.Name, endpoint.Type))); - } - } - else if (endpointTypeSegments.Count > 1 && !String.IsNullOrEmpty(endpoint.Authorization?.Scheme)) - { - var supportedAuthSchemes = endpointTypeSegments[1]?.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries).Select(x => x.Trim()).ToList(); - if (supportedAuthSchemes?.Count > 0 && !supportedAuthSchemes.Any(x => x.Equals(endpoint.Authorization.Scheme, StringComparison.OrdinalIgnoreCase))) - { - if (throwOnFailure) - { - throw new PipelineValidationException(PipelineStrings.StepInputEndpointAuthSchemeMismatch(phase.Name, step.Name, inputAlias, endpointTypeName, endpointTypeSegments[1], endpoint.Name, endpoint.Type, endpoint.Authorization.Scheme)); - } - else - { - errors.Add(new PipelineValidationError(PipelineStrings.StepInputEndpointAuthSchemeMismatch(phase.Name, step.Name, inputAlias, endpointTypeName, endpointTypeSegments[1], endpoint.Name, endpoint.Type, endpoint.Authorization.Scheme))); - } - } - } - } - } - - resolvedEndpoints.Add(endpoint.Id.ToString("D")); - } - } - else - { - // Always add the value back so we can update the input below. - resolvedEndpoints.Add(replacedValue); - } - } - - step.Inputs[input.Name] = String.Join(",", resolvedEndpoints); - } - else if (input.InputType.Equals(c_secureFileInputType, StringComparison.OrdinalIgnoreCase)) - { - var resolvedFiles = new List(); - var resolvedInputValues = inputValue.Split(',').Select(x => x.Trim()).Where(x => !String.IsNullOrEmpty(x)); - foreach (var value in resolvedInputValues) - { - var replacedValue = context.ExpandVariables(value); - referencedResources.AddSecureFileReference(replacedValue); - - // Validate the resource using the provided store if desired - if (options.ValidateResources) - { - var secureFile = context.ResourceStore.GetFile(replacedValue); - if (secureFile == null) - { - if (throwOnFailure) - { - throw new ResourceNotFoundException(PipelineStrings.SecureFileNotFoundForInput(phase.Name, step.Name, inputAlias, replacedValue)); - } - else - { - resolvedFiles.Add(replacedValue); - unauthorizedResources?.AddSecureFileReference(replacedValue); - errors.Add(new PipelineValidationError(PipelineStrings.SecureFileNotFoundForInput(phase.Name, step.Name, inputAlias, replacedValue))); - } - } - else - { - resolvedFiles.Add(secureFile.Id.ToString("D")); - } - } - else - { - // Always add the value back so we can update the input below. - resolvedFiles.Add(replacedValue); - } - } - - step.Inputs[input.Name] = String.Join(",", resolvedFiles); - } - else if (input.InputType.Equals(TaskInputType.Repository, StringComparison.OrdinalIgnoreCase)) - { - // Ignore repository alias None - if (!String.Equals(inputValue, PipelineConstants.NoneAlias)) - { - var repository = context.ResourceStore.Repositories.Get(inputValue); - if (repository == null) - { - if (options.ValidateResources) - { - // repository should always be there as full object - if (throwOnFailure) - { - throw new ResourceNotFoundException(PipelineStrings.RepositoryResourceNotFound(inputValue)); - } - else - { - errors.Add(new PipelineValidationError(PipelineStrings.RepositoryResourceNotFound(inputValue))); - } - } - } - else - { - referencedResources.Repositories.Add(repository); - - // Add the endpoint - if (repository.Endpoint != null) - { - referencedResources.AddEndpointReference(repository.Endpoint); - - if (options.ValidateResources) - { - var repositoryEndpoint = context.ResourceStore.GetEndpoint(repository.Endpoint); - if (repositoryEndpoint == null) - { - if (throwOnFailure) - { - throw new ResourceNotFoundException(PipelineStrings.ServiceEndpointNotFound(repository.Endpoint)); - } - else - { - unauthorizedResources?.AddEndpointReference(repository.Endpoint); - errors.Add(new PipelineValidationError(PipelineStrings.ServiceEndpointNotFound(repository.Endpoint))); - } - } - else - { - repository.Endpoint = new ServiceEndpointReference() { Id = repositoryEndpoint.Id }; - } - } - } - } - } - else - { - // always add self repo with checkout: none - var selfRepository = context.ResourceStore.Repositories.Get(PipelineConstants.SelfAlias); - if (selfRepository != null) - { - referencedResources.Repositories.Add(selfRepository); - if (selfRepository.Endpoint != null) - { - referencedResources.AddEndpointReference(selfRepository.Endpoint); - if (options.ValidateResources) - { - var repositoryEndpoint = context.ResourceStore.GetEndpoint(selfRepository.Endpoint); - if (repositoryEndpoint == null) - { - if (throwOnFailure) - { - throw new ResourceNotFoundException(PipelineStrings.ServiceEndpointNotFound(selfRepository.Endpoint)); - } - else - { - unauthorizedResources?.AddEndpointReference(selfRepository.Endpoint); - errors.Add(new PipelineValidationError(PipelineStrings.ServiceEndpointNotFound(selfRepository.Endpoint))); - } - } - else - { - selfRepository.Endpoint = new ServiceEndpointReference() { Id = repositoryEndpoint.Id }; - } - } - } - } - } - } - - return errors; - } - - private String ResolveContainerResource(JobExecutionContext context, String inputAlias) - { - var outputAlias = inputAlias; - // Check if container is an image spec, not an alias - if (inputAlias.Contains(":")) - { - var resource = context.ResourceStore?.Containers.GetAll().FirstOrDefault(x => - x.Endpoint == null && - x.Properties.Count == 1 && - String.Equals(x.Image, inputAlias, StringComparison.Ordinal)); - if (resource == null) - { - resource = new ContainerResource - { - Alias = Guid.NewGuid().ToString("N"), - Image = inputAlias, - }; - context.ResourceStore?.Containers.Add(resource); - } - outputAlias = resource.Alias; - } - - return outputAlias; - } - - private void UpdateJobContextReferencedContainers(JobExecutionContext context, string containerAlias) - { - // Look up the container by alias, and add dereferenced container to ReferencedResources - var containerResource = context.ResourceStore?.Containers.Get(containerAlias); - if (containerResource == null) - { - throw new ResourceNotFoundException(PipelineStrings.ContainerResourceNotFound(containerAlias)); - } - context.ReferencedResources.Containers.Add(containerResource); - if (containerResource.Endpoint != null) - { - context.ReferencedResources.AddEndpointReference(containerResource.Endpoint); - var serviceEndpoint = context.ResourceStore?.GetEndpoint(containerResource.Endpoint); - if (serviceEndpoint == null) - { - throw new ResourceNotFoundException(PipelineStrings.ContainerEndpointNotFound(containerAlias, containerResource.Endpoint)); - } - } - } - - private static IEnumerable ValidateInput( - PipelineBuildContext context, - PhaseNode phase, - TaskStep step, - TaskInputDefinition input, - String inputAlias, - String value) - { - if (!context.BuildOptions.ValidateTaskInputs || input.Validation == null) - { - return Enumerable.Empty(); - } - - // We cannot perform useful validation if the value didn't expand, it may not be populated until it - // executes on the target. If we still have variables we just let it go through optimistically. - var expandedInputValue = context.ExpandVariables(value); - if (VariableUtility.IsVariable(expandedInputValue)) - { - return Enumerable.Empty(); - } - - var inputContext = new InputValidationContext - { - Evaluate = true, - EvaluationOptions = new DistributedTask.Expressions.EvaluationOptions(), - Expression = input.Validation.Expression, - SecretMasker = context.SecretMasker, - TraceWriter = null, - Value = expandedInputValue, - }; - - // Make sure to track any input validation errors encountered - var validationResult = context.InputValidator.Validate(inputContext); - if (validationResult.IsValid) - { - return Enumerable.Empty(); - } - else - { - // Make sure we do not expose secrets when logging errors about expanded input values - var maskedValue = context.SecretMasker.MaskSecrets(expandedInputValue); - var reason = validationResult.Reason ?? input.Validation.Message; - return new[] { new PipelineValidationError(PipelineStrings.StepTaskInputInvalid(phase.Name, step.Name, inputAlias, maskedValue, inputContext.Expression, reason)) }; - } - } - - /// - /// Produces the official display name for this job. - /// Optionally include any of the path components you want to consider. - /// - internal static String GenerateDisplayName( - Stage stage = null, - PhaseNode phase = null, - Job job = null) - { - var stageName = default(string); - if (stage != null) - { - stageName = stage.DisplayName ?? stage.Name; - } - - var factoryName = default(string); - if (phase != null) - { - factoryName = phase.DisplayName ?? phase.Name; - } - - var jobName = default(string); - if (job != null) - { - jobName = job.DisplayName ?? job.Name; - } - - return GenerateDisplayName(stageName, factoryName, jobName); - } - - /// - /// Produces the official display name for this job. - /// Optionally include any of the path components you want to consider. - /// - internal static String GenerateDisplayName( - PhaseNode factory, - String configuration = null) - { - var factoryDisplayName = factory == null - ? String.Empty - : factory.DisplayName ?? factory.Name; - return GenerateDisplayName(factoryDisplayName, configuration); - } - - /// - /// Produces the official display name for this job. - /// Optionally include any of the path components you want to consider. - /// Removes any occurrence of the default node name (the reference name used for default nodes, - /// or when users do not specify any name) - /// - internal static String GenerateDisplayName(params string[] tokens) - { - if (tokens == null) - { - return string.Empty; - } - - var defaultNodeName = PipelineConstants.DefaultJobName; - var l = defaultNodeName.Length; - var formattedTokens = tokens - .Where(x => !string.IsNullOrWhiteSpace(x)) - .Select(x => (x.StartsWith(defaultNodeName) ? x.Substring(l) : x).Trim()) - .Where(x => !string.IsNullOrWhiteSpace(x)); - var result = string.Join(" ", formattedTokens); - - return string.IsNullOrWhiteSpace(result) - ? PipelineConstants.DefaultJobDisplayName - : result; - } - - public Job CreateJob( - JobExecutionContext context, - ExpressionValue container, - IDictionary> sidecarContainers, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - String displayName = null) - { - // default display name is based on the phase. - if (string.IsNullOrWhiteSpace(displayName)) - { - displayName = Phase.GenerateDisplayName(context.Phase.Definition); - } - - var job = new Job - { - Id = context.GetInstanceId(), - Name = context.Job.Name, - DisplayName = displayName, - ContinueOnError = continueOnError, - TimeoutInMinutes = timeoutInMinutes, - CancelTimeoutInMinutes = cancelTimeoutInMinutes - }; - - if (context.ExecutionOptions.EnableResourceExpressions) - { - job.Target = GenerateJobSpecificTarget(context); - } - - if (job.Target == null) - { - ArgumentUtility.CheckForNull(this.Target, nameof(this.Target)); - job.Target = this.Target.Clone(); - } - - if (context.EnvironmentVersion > 1) - { - // always add self or designer repo to repository list - RepositoryResource defaultRepo = null; - var selfRepo = context.ResourceStore?.Repositories.Get(PipelineConstants.SelfAlias); - if (selfRepo == null) - { - var designerRepo = context.ResourceStore?.Repositories.Get(PipelineConstants.DesignerRepo); - if (designerRepo != null) - { - defaultRepo = designerRepo; - } - else - { - Debug.Fail("Repositories are not filled in."); - } - } - else - { - defaultRepo = selfRepo; - } - - if (defaultRepo != null) - { - context.ReferencedResources.Repositories.Add(defaultRepo); - - // Add the endpoint - if (defaultRepo.Endpoint != null) - { - context.ReferencedResources.AddEndpointReference(defaultRepo.Endpoint); - var repositoryEndpoint = context.ResourceStore?.GetEndpoint(defaultRepo.Endpoint); - if (repositoryEndpoint == null) - { - throw new ResourceNotFoundException(PipelineStrings.ServiceEndpointNotFound(defaultRepo.Endpoint)); - } - } - } - } - - // Expand short-syntax inline-containers, resolve resource references and add to new job and context - if (container != null) - { - var containerAlias = container.GetValue(context).Value; - var outputAlias = ResolveContainerResource(context, containerAlias); - job.Container = new DistributedTask.ObjectTemplating.Tokens.StringToken(null, null, null, outputAlias); - UpdateJobContextReferencedContainers(context, outputAlias); - } - if (sidecarContainers != null) - { - foreach (var sidecar in sidecarContainers) - { - var sidecarContainerAlias = sidecar.Value.GetValue(context).Value; - var outputAlias = ResolveContainerResource(context, sidecarContainerAlias); - job.SidecarContainers.Add(sidecar.Key, outputAlias); - UpdateJobContextReferencedContainers(context, outputAlias); - } - } - - // Update the execution context with the job-specific system variables - UpdateJobContextVariablesFromJob(context, job); - - var steps = new List(); - var identifier = context.GetInstanceName(); - foreach (var step in this.Steps) - { - if (step.Type == StepType.Task) - { - // We don't need to add to demands here since they are already part of the plan. - steps.Add(CreateJobTaskStep(context, this, identifier, step as TaskStep)); - } - else if (step.Type == StepType.Group) - { - steps.Add(CreateJobStepGroup(context, this, identifier, step as GroupStep)); - } - else if (step.Type == StepType.Action) - { - steps.Add(CreateJobActionStep(context, identifier, step as ActionStep)); - } - else - { - // Should never happen. - Debug.Fail(step.Type.ToString()); - } - } - - // TODO: remove the whole concept of step providers. - // this work should happen during compilation. -zacox. - // - // This is not ideal but we need to set the job on the context before calling the step providers below. - // This method returns the job and it gets set after. We need to clean this up when we do refactoring. - context.Job.Definition = job; - - var stepProviderDemands = new HashSet(); - - // Add the system-injected tasks before inserting the user tasks. This currently does not handle injecting - // min agent version demands if appropriate. - var systemSteps = new List(); - if (context.StepProviders != null) - { - var jobSteps = new ReadOnlyCollection(steps); - - foreach (IStepProvider stepProvider in context.StepProviders) - { - systemSteps.AddRange(stepProvider.GetPreSteps(context, jobSteps)); - } - } - - if (systemSteps?.Count > 0) - { - for (Int32 i = 0; i < systemSteps.Count; i++) - { - systemSteps[i].Name = $"__system_{i + 1}"; - - IList resolvedSteps = new List(); - if (ResolveTaskStep(context, this, identifier, systemSteps[i], out resolvedSteps, stepProviderDemands)) - { - job.Steps.AddRange(resolvedSteps); - } - else - { - job.Steps.Add(CreateJobTaskStep(context, this, identifier, systemSteps[i], stepProviderDemands)); - } - } - } - - // Resolving user steps - foreach (var step in steps) - { - IList resolvedSteps = new List(); - if (ResolveTaskStep(context, this, identifier, step, out resolvedSteps)) - { - job.Steps.AddRange(resolvedSteps); - } - else - { - job.Steps.Add(step); - } - } - - // Add post job steps, if there are any. - // These are added after the user tasks. - var postJobSteps = new List(); - if (context.StepProviders != null) - { - var jobSteps = new ReadOnlyCollection(job.Steps); - - foreach (IStepProvider stepProvider in context.StepProviders) - { - postJobSteps.AddRange(stepProvider.GetPostSteps(context, jobSteps)); - } - } - - if (postJobSteps?.Count > 0) - { - for (Int32 i = 0; i < postJobSteps.Count; i++) - { - postJobSteps[i].Name = $"__system_post_{i + 1}"; - job.Steps.Add(CreateJobTaskStep(context, this, identifier, postJobSteps[i], stepProviderDemands)); - } - } - - // Add post checkout tasks - // We need to do this after all other tasks are added since checkout could be injected from pre steps or phase steps. - var postCheckoutSteps = new Dictionary>(); - if (context.StepProviders != null) - { - var jobSteps = new ReadOnlyCollection(steps); - - foreach (IStepProvider stepProvider in context.StepProviders) - { - // This will flatten into 1 dictionary of guids to insert after and the tasks to insert - Dictionary> toAdd = stepProvider.GetPostTaskSteps(context, jobSteps); - - foreach (var key in toAdd.Keys) - { - if (!postCheckoutSteps.ContainsKey(key)) - { - postCheckoutSteps[key] = new List(); - } - - postCheckoutSteps[key].AddRange(toAdd[key]); - } - } - } - - if (postCheckoutSteps?.Keys.Count > 0) - { - foreach (var pair in postCheckoutSteps) - { - Int32? indexOfLastInstanceOfTask = null; - for (int i = job.Steps.Count - 1; i >= 0; i--) - { - var taskStep = job.Steps[i] as TaskStep; - - if (taskStep != null && taskStep.Reference.Id.Equals(pair.Key)) - { - indexOfLastInstanceOfTask = i; - break; - } - } - - // This will not insert after if the task doesn't exist. - if (indexOfLastInstanceOfTask.HasValue) - { - for (Int32 i = 0; i < pair.Value.Count; i++) - { - // This is so that we know this was a system injected task. - pair.Value[i].Name = $"__system_postcheckout_{i + 1}"; - - job.Steps.Insert(indexOfLastInstanceOfTask.Value + i + 1, CreateJobTaskStep(context, this, identifier, pair.Value[i], stepProviderDemands)); - } - } - } - } - - // create unique set of job demands - AddDemands(context, job, stepProviderDemands); - AddDemands(context, job, this.Target?.Demands); - - // Copy context variables into job, since job will be saved and read back later before agent job message is sent - foreach (var variable in context.Variables) - { - context.Job.Definition.Variables.Add(new Variable - { - Name = variable.Key, - Value = variable.Value.IsSecret ? null : variable.Value.Value, - Secret = variable.Value.IsSecret - }); - } - - return job; - } - - private void AddDemands( - JobExecutionContext context, - Job job, - ISet demands) - { - if (context == null || job == null || demands == null) - { - return; - } - - var mergedDemands = job.Demands; - foreach (var d in demands) - { - if (d == null) - { - continue; - } - - var demandValue = d.Value; - if (String.IsNullOrEmpty(demandValue)) - { - // if a demand has no value, add it - mergedDemands.Add(d.Clone()); - } - else - { - // if a demand has a non-empty value, any problems encountered while evaluating - // macros should be promoted into PipelineValidationExceptions - var expandedValue = context.ExpandVariables(demandValue, maskSecrets: true); - try - { - var resolvedDemand = d.Clone(); - resolvedDemand.Update(expandedValue); - mergedDemands.Add(resolvedDemand); - } - catch (Exception e) - { - throw new PipelineValidationException(PipelineStrings.DemandExpansionInvalid(d.ToString(), d.Value, expandedValue), e); - } - } - } - } - - private Boolean ResolveTaskStep( - JobExecutionContext context, - PhaseNode phase, - String identifier, - JobStep step, - out IList resolvedSteps, - HashSet resolvedDemands = null) - { - Boolean handled = false; - IList resultSteps = new List(); - resolvedSteps = new List(); - - if (context.ResourceStore?.ResolveStep(context, step, out resultSteps) ?? false) - { - foreach (TaskStep resultStep in resultSteps) - { - resolvedSteps.Add(CreateJobTaskStep(context, phase, identifier, resultStep, resolvedDemands)); - } - - handled = true; - } - - return handled; - } - - /// - /// Evaluate runtime expressions - /// Queue targets are allowed use runtime expressions. - /// Resolve all expressions and produce a literal QueueTarget for execution. - /// - private AgentQueueTarget GenerateJobSpecificTarget(JobExecutionContext context) - { - var phase = context?.Phase?.Definition as Phase; - if (phase == null) - { - return null; - } - - if (!(phase.Target is AgentQueueTarget agentQueueTarget)) - { - return null; - } - - if (agentQueueTarget.IsLiteral()) - { - return null; - } - - // create a clone containing only literals and validate referenced resources - var validationResult = new Validation.ValidationResult(); - var literalTarget = agentQueueTarget.Evaluate(context, validationResult); - literalTarget?.Validate( - context: context, - result: validationResult, - buildOptions: new BuildOptions - { - EnableResourceExpressions = true, - ValidateResources = true, - ValidateExpressions = true, // all expressions must resolve - AllowEmptyQueueTarget = false - }, - steps: new List(), - taskDemands: new HashSet()); - - if (validationResult.Errors.Count > 0) - { - throw new PipelineValidationException(validationResult.Errors); - } - - return literalTarget; - } - - // todo: merge JobFactory.cs and Phase.cs and then make this private - internal static ActionStep CreateJobActionStep( - JobExecutionContext context, - String jobIdentifier, - ActionStep action) - { - var jobStep = (ActionStep)action.Clone(); - - // Setup the identifier based on our current context - var actionIdentifier = context.IdGenerator.GetInstanceName(jobIdentifier, action.Name); - jobStep.Id = context.IdGenerator.GetInstanceId(actionIdentifier); - - // Update the display name of task steps - jobStep.DisplayName = jobStep.DisplayName; - - return jobStep; - } - - // todo: merge JobFactory.cs and Phase.cs and then make this private - internal static TaskStep CreateJobTaskStep( - JobExecutionContext context, - PhaseNode phase, - String jobIdentifier, - TaskStep task, - HashSet resolvedDemands = null) - { - var jobStep = (TaskStep)task.Clone(); - - // Setup the identifier based on our current context - var taskIdentifier = context.IdGenerator.GetInstanceName(jobIdentifier, task.Name); - jobStep.Id = context.IdGenerator.GetInstanceId(taskIdentifier); - - // Update the display name of task steps - jobStep.DisplayName = context.ExpandVariables(jobStep.DisplayName, maskSecrets: true); - - // Now resolve any resources referenced by inputs - var taskDefinition = context.TaskStore.ResolveTask(jobStep.Reference.Id, jobStep.Reference.Version); - if (taskDefinition != null) - { - foreach (var input in taskDefinition.Inputs) - { - if (task.Inputs.TryGetValue(input.Name, out String value)) - { - ResolveResources(context, phase, BuildOptions.None, context.ReferencedResources, null, jobStep, input, input.Name, value, throwOnFailure: true); - } - } - - // Add demands - if (resolvedDemands != null) - { - resolvedDemands.AddRange(taskDefinition.Demands); - - if (!String.IsNullOrEmpty(taskDefinition.MinimumAgentVersion)) - { - resolvedDemands.Add(new DemandMinimumVersion(PipelineConstants.AgentVersionDemandName, taskDefinition.MinimumAgentVersion)); - } - } - } - else - { - throw new TaskDefinitionNotFoundException(PipelineStrings.TaskMissing(phase.Name, jobStep.Name, jobStep.Reference.Id, jobStep.Reference.Version)); - } - - return jobStep; - } - - // todo: merge JobFactory.cs and Phase.cs and then make this private - internal static GroupStep CreateJobStepGroup( - JobExecutionContext context, - PhaseNode phase, - String jobIdentifier, - GroupStep group) - { - var groupStep = (GroupStep)group.Clone(); - - var groupIdentifier = context.IdGenerator.GetInstanceName(jobIdentifier, group.Name); - groupStep.Id = context.IdGenerator.GetInstanceId(groupIdentifier); - - // Update the display name of step group - groupStep.DisplayName = context.ExpandVariables(groupStep.DisplayName, maskSecrets: true); - - // Now resolve every task steps within step group - var stepsCopy = new List(); - foreach (var task in groupStep.Steps) - { - stepsCopy.Add(CreateJobTaskStep(context, phase, groupIdentifier, task)); - } - - groupStep.Steps.Clear(); - groupStep.Steps.AddRange(stepsCopy); - - return groupStep; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_steps?.Count == 0) - { - m_steps = null; - } - } - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private IList m_steps; - - private const String c_secureFileInputType = "secureFile"; - private const String c_endpointInputTypePrefix = "connectedService:"; - - // todo: merge JobFactory.cs and Phase.cs and then make this private - internal class StepValidationResult - { - public String MinAgentVersion { get; set; } - - public HashSet TaskDemands - { - get - { - if (m_taskDemands == null) - { - m_taskDemands = new HashSet(); - } - - return m_taskDemands; - } - } - - public HashSet KnownNames - { - get - { - if (m_knownNames == null) - { - m_knownNames = new HashSet(StringComparer.OrdinalIgnoreCase); - } - - return m_knownNames; - } - } - - public HashSet TasksSatisfy - { - get - { - if (m_tasksSatisfy == null) - { - m_tasksSatisfy = new HashSet(StringComparer.OrdinalIgnoreCase); - } - - return m_tasksSatisfy; - } - } - - public Dictionary> UnnamedSteps - { - get - { - if (m_unnamedSteps == null) - { - m_unnamedSteps = new Dictionary>(StringComparer.OrdinalIgnoreCase); - } - - return m_unnamedSteps; - } - } - - HashSet m_taskDemands; - HashSet m_knownNames; - HashSet m_tasksSatisfy; - Dictionary> m_unnamedSteps; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PhaseCondition.cs b/src/Sdk/DTPipelines/Pipelines/PhaseCondition.cs deleted file mode 100644 index eae3ddb45..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PhaseCondition.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PhaseCondition : GraphCondition - { - public PhaseCondition(String condition) - : base(condition) - { - } - - public ConditionResult Evaluate(PhaseExecutionContext context) - { - var traceWriter = new ConditionTraceWriter(); - var evaluationResult = m_parsedCondition.Evaluate(traceWriter, context.SecretMasker, context, context.ExpressionOptions); - return new ConditionResult() { Value = evaluationResult.IsTruthy, Trace = traceWriter.Trace }; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PhaseDependency.cs b/src/Sdk/DTPipelines/Pipelines/PhaseDependency.cs deleted file mode 100644 index 3cccfaeac..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PhaseDependency.cs +++ /dev/null @@ -1,56 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PhaseDependency - { - [JsonConstructor] - public PhaseDependency() - { - } - - private PhaseDependency(PhaseDependency dependencyToCopy) - { - this.Scope = dependencyToCopy.Scope; - this.Event = dependencyToCopy.Event; - } - - [DataMember] - public String Scope - { - get; - set; - } - - [DataMember] - public String Event - { - get; - set; - } - - /// - /// Implicitly converts a Phase to a PhaseDependency to enable easier modeling of graphs. - /// - /// The phase which should be converted to a dependency - public static implicit operator PhaseDependency(Phase dependency) - { - return PhaseCompleted(dependency.Name); - } - - public static PhaseDependency PhaseCompleted(String name) - { - return new PhaseDependency { Scope = name, Event = "Completed" }; - } - - internal PhaseDependency Clone() - { - return new PhaseDependency(this); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PhaseNode.cs b/src/Sdk/DTPipelines/Pipelines/PhaseNode.cs deleted file mode 100644 index 70c9fa3f5..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PhaseNode.cs +++ /dev/null @@ -1,421 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Internal; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [ClientIgnore] - [EditorBrowsable(EditorBrowsableState.Never)] - public enum PhaseType - { - [EnumMember] - Phase, - - [EnumMember] - Provider, - - [EnumMember] - JobFactory, - } - - [DataContract] - [KnownType(typeof(Phase))] - [KnownType(typeof(ProviderPhase))] - [KnownType(typeof(JobFactory))] - [JsonConverter(typeof(PhaseNodeJsonConverter))] - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PhaseNode : IGraphNode - { - protected PhaseNode() - { - } - - protected PhaseNode(PhaseNode nodeToCopy) - { - this.Name = nodeToCopy.Name; - this.DisplayName = nodeToCopy.DisplayName; - this.Condition = nodeToCopy.Condition; - this.ContinueOnError = nodeToCopy.ContinueOnError; - this.Target = nodeToCopy.Target?.Clone(); - - if (nodeToCopy.m_dependsOn?.Count > 0) - { - m_dependsOn = new HashSet(nodeToCopy.m_dependsOn, StringComparer.OrdinalIgnoreCase); - } - - if (nodeToCopy.m_variables != null && nodeToCopy.m_variables.Count > 0) - { - m_variables = new List(nodeToCopy.m_variables); - } - } - - /// - /// Gets the type of this phase. - /// - [DataMember(EmitDefaultValue = false)] - public abstract PhaseType Type { get; } - - /// - /// Gets or sets the name for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Gets or sets the display name for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public String DisplayName - { - get; - set; - } - - /// - /// Gets or sets a condition which is evaluated after all dependencies have been satisfied and determines - /// whether or not the jobs within this phase should be executed or skipped. - /// - [DataMember(EmitDefaultValue = false)] - public String Condition - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not failed jobs are considered a termination condition for - /// the phase. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue ContinueOnError - { - get; - set; - } - - /// - /// Gets the set of phases which must complete before this phase begins execution. - /// - public ISet DependsOn - { - get - { - if (m_dependsOn == null) - { - m_dependsOn = new HashSet(StringComparer.OrdinalIgnoreCase); - } - return m_dependsOn; - } - } - - /// - /// Gets or sets the target for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public PhaseTarget Target - { - get; - set; - } - - /// - /// Gets the set of variables which will be provided to the phase steps. - /// - public IList Variables - { - get - { - if (m_variables == null) - { - m_variables = new List(); - } - return m_variables; - } - } - - /// - /// Resolves external references and ensures the steps are compatible with the selected target. - /// - /// The validation context - public virtual void Validate( - PipelineBuildContext context, - ValidationResult result) - { - // Ensure we have a target - if (this.Target == null) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.PhaseTargetRequired(this.Name))); - return; - } - - if (this.Target.Type != PhaseTargetType.Queue && this.Target.Type != PhaseTargetType.Server && this.Target.Type != PhaseTargetType.Pool) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.UnsupportedTargetType(this.Name, this.Target.Type))); - return; - } - - // Default the condition to something reasonable if none is specified - if (String.IsNullOrEmpty(this.Condition)) - { - this.Condition = PhaseCondition.Default; - } - else - { - // Simply construct the condition and make sure the syntax and functions used are valid - var parsedCondition = new PhaseCondition(this.Condition); - } - - if (m_variables?.Count > 0) - { - var variablesCopy = new List(); - foreach (var variable in this.Variables) - { - if (variable is Variable simpleVariable) - { - // Do not allow phase overrides for certain variables. - if (s_nonOverridableVariables.Contains(simpleVariable.Name)) - { - continue; - } - } - else if (variable is VariableGroupReference groupVariable) - { - if (context.EnvironmentVersion < 2) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.PhaseVariableGroupNotSupported(this.Name, groupVariable))); - continue; - } - - result.ReferencedResources.VariableGroups.Add(groupVariable); - - if (context.BuildOptions.ValidateResources) - { - var variableGroup = context.ResourceStore.VariableGroups.Get(groupVariable); - if (variableGroup == null) - { - result.UnauthorizedResources.VariableGroups.Add(groupVariable); - result.Errors.Add(new PipelineValidationError(PipelineStrings.VariableGroupNotFoundForPhase(this.Name, groupVariable))); - } - } - } - - variablesCopy.Add(variable); - } - - m_variables.Clear(); - m_variables.AddRange(variablesCopy); - } - } - - protected virtual void UpdateJobContextVariablesFromJob(JobExecutionContext jobContext, Job job) - { - jobContext.Variables[WellKnownDistributedTaskVariables.JobDisplayName] = job.DisplayName; - jobContext.Variables[WellKnownDistributedTaskVariables.JobId] = job.Id.ToString("D"); - jobContext.Variables[WellKnownDistributedTaskVariables.JobName] = job.Name; - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (m_dependencies?.Count > 0) - { - m_dependsOn = new HashSet(m_dependencies.Select(x => x.Scope), StringComparer.OrdinalIgnoreCase); - m_dependencies = null; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_dependsOn?.Count == 0) - { - m_dependsOn = null; - } - - if (m_variables?.Count == 0) - { - m_variables = null; - } - } - - internal readonly static HashSet s_nonOverridableVariables = new HashSet(new[] - { - WellKnownDistributedTaskVariables.AccessTokenScope, - WellKnownDistributedTaskVariables.JobParallelismTag - }, StringComparer.OrdinalIgnoreCase); - - [JsonConverter(typeof(PhaseVariablesJsonConverter))] - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private List m_variables; - - [DataMember(Name = "Dependencies", EmitDefaultValue = false)] - private List m_dependencies; - - [DataMember(Name = "DependsOn", EmitDefaultValue = false)] - private HashSet m_dependsOn; - - private class PhaseVariablesJsonConverter : JsonConverter - { - public PhaseVariablesJsonConverter() - { - } - - public override Boolean CanConvert(Type objectType) - { - return true; - } - - public override Boolean CanWrite => true; - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType == JsonToken.StartArray) - { - return serializer.Deserialize>(reader); - } - else if (reader.TokenType == JsonToken.StartObject) - { - var dictionary = serializer.Deserialize>(reader); - if (dictionary?.Count > 0) - { - return dictionary.Select(x => new Variable { Name = x.Key, Value = x.Value }).Cast().ToList(); - } - } - - return null; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - var variables = value as IList; - if (variables?.Count > 0) - { - if (variables.Any(x => x is VariableGroupReference)) - { - serializer.Serialize(writer, variables); - } - else - { - // This format is only here for back compat with the previous serialization format - var dictionary = new Dictionary(StringComparer.OrdinalIgnoreCase); - foreach (var variable in variables.OfType()) - { - dictionary[variable.Name] = variable.Value; - } - - serializer.Serialize(writer, dictionary); - } - } - } - } - } - - internal sealed class PhaseNodeJsonConverter : VssSecureJsonConverter - { - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(PhaseNode).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - PhaseType? phaseType = null; - JObject value = JObject.Load(reader); - if (!value.TryGetValue("Type", StringComparison.OrdinalIgnoreCase, out JToken phaseTypeValue)) - { - phaseType = PhaseType.Phase; - } - else - { - if (phaseTypeValue.Type == JTokenType.Integer) - { - phaseType = (PhaseType)(Int32)phaseTypeValue; - } - else if (phaseTypeValue.Type == JTokenType.String) - { - PhaseType parsedType; - if (Enum.TryParse((String)phaseTypeValue, ignoreCase: true, result: out parsedType)) - { - phaseType = parsedType; - } - } - } - - if (phaseType == null) - { - return existingValue; - } - - Object newValue = null; - switch (phaseType) - { - case PhaseType.Phase: - newValue = new Phase(); - break; - - case PhaseType.Provider: - newValue = new ProviderPhase(); - break; - - case PhaseType.JobFactory: - newValue = new JobFactory(); - break; - } - - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PhaseTarget.cs b/src/Sdk/DTPipelines/Pipelines/PhaseTarget.cs deleted file mode 100644 index 37f424d73..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PhaseTarget.cs +++ /dev/null @@ -1,260 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [KnownType(typeof(AgentQueueTarget))] - [KnownType(typeof(AgentPoolTarget))] - [KnownType(typeof(ServerTarget))] - [KnownType(typeof(DeploymentGroupTarget))] - [JsonConverter(typeof(PhaseTargetJsonConverter))] - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PhaseTarget - { - protected PhaseTarget(PhaseTargetType type) - { - this.Type = type; - } - - protected PhaseTarget(PhaseTarget targetToClone) - { - this.Type = targetToClone.Type; - this.ContinueOnError = targetToClone.ContinueOnError; - this.TimeoutInMinutes = targetToClone.TimeoutInMinutes; - this.CancelTimeoutInMinutes = targetToClone.CancelTimeoutInMinutes; - if (targetToClone.m_demands?.Count > 0) - { - m_demands = new HashSet(targetToClone.m_demands.Select(x => x.Clone())); - } - } - - /// - /// Get the type of target. - /// - [DataMember] - public PhaseTargetType Type - { - get; - private set; - } - - /// - /// Gets or sets a value which determines whether or not to treat errors as terminal. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue ContinueOnError - { - get; - set; - } - - /// - /// Gets or sets a value which determines the maximum amount of time a job is allowed to execute. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue TimeoutInMinutes - { - get; - set; - } - - /// - /// Gets or sets a value which determines the maximum amount of time a job is allowed for cancellation. - /// - [DataMember(EmitDefaultValue = false)] - [JsonConverter(typeof(ExpressionValueJsonConverter))] - public ExpressionValue CancelTimeoutInMinutes - { - get; - set; - } - - /// - /// Gets the demands which determine where this job may be run. - /// - public ISet Demands - { - get - { - if (m_demands == null) - { - m_demands = new HashSet(); - } - return m_demands; - } - } - - /// - /// Creates a deep copy of the current instance. - /// - /// A new PhaseTarget instance of the current type - public abstract PhaseTarget Clone(); - - /// - /// Indicates whether the task definition can run on the target. - /// - public abstract Boolean IsValid(TaskDefinition task); - - internal abstract JobExecutionContext CreateJobContext(PhaseExecutionContext context, String jobName, Int32 attempt, Boolean continueOnError, Int32 timeoutInMinutes, Int32 cancelTimeoutInMinutes, IJobFactory jobFactory); - - internal void Validate( - IPipelineContext context, - BuildOptions buildOptions, - ValidationResult result) - { - this.Validate(context, buildOptions, result, new List(), new HashSet()); - } - - internal abstract ExpandPhaseResult Expand(PhaseExecutionContext context, Boolean continueOnError, Int32 timeoutInMinutes, Int32 cancelTimeoutInMinutes, IJobFactory jobFactory, JobExpansionOptions options); - - internal virtual void Validate( - IPipelineContext context, - BuildOptions buildOptions, - ValidationResult result, - IList steps, - ISet taskDemands) - { - } - - internal JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String jobName, - Int32 attempt, - IJobFactory jobFactory) - { - var continueOnError = context.Evaluate(nameof(ContinueOnError), this.ContinueOnError, false).Value; - var timeoutInMinutes = context.Evaluate(nameof(TimeoutInMinutes), this.TimeoutInMinutes, PipelineConstants.DefaultJobTimeoutInMinutes).Value; - var cancelTimeoutInMinutes = context.Evaluate(nameof(CancelTimeoutInMinutes), this.CancelTimeoutInMinutes, PipelineConstants.DefaultJobCancelTimeoutInMinutes).Value; - return this.CreateJobContext(context, jobName, attempt, continueOnError, timeoutInMinutes, cancelTimeoutInMinutes, jobFactory); - } - - internal ExpandPhaseResult Expand( - PhaseExecutionContext context, - IJobFactory jobFactory, - JobExpansionOptions options) - { - var continueOnError = context.Evaluate(nameof(ContinueOnError), this.ContinueOnError, false).Value; - var timeoutInMinutes = context.Evaluate(nameof(TimeoutInMinutes), this.TimeoutInMinutes, PipelineConstants.DefaultJobTimeoutInMinutes).Value; - var cancelTimeoutInMinutes = context.Evaluate(nameof(CancelTimeoutInMinutes), this.CancelTimeoutInMinutes, PipelineConstants.DefaultJobCancelTimeoutInMinutes).Value; - return this.Expand(context, continueOnError, timeoutInMinutes, cancelTimeoutInMinutes, jobFactory, options); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_demands?.Count == 0) - { - m_demands = null; - } - } - - [DataMember(Name = "Demands", EmitDefaultValue = false)] - private ISet m_demands; - } - - internal sealed class PhaseTargetJsonConverter : VssSecureJsonConverter - { - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(PhaseTarget).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - PhaseTargetType? targetType = null; - JObject value = JObject.Load(reader); - if (!value.TryGetValue("Type", StringComparison.OrdinalIgnoreCase, out JToken targetTypeValue)) - { - return existingValue; - } - else - { - if (targetTypeValue.Type == JTokenType.Integer) - { - targetType = (PhaseTargetType)(Int32)targetTypeValue; - } - else if (targetTypeValue.Type == JTokenType.String) - { - PhaseTargetType parsedType; - if (Enum.TryParse((String)targetTypeValue, ignoreCase: true, result: out parsedType)) - { - targetType = parsedType; - } - } - } - - if (targetType == null) - { - return existingValue; - } - - Object newValue = null; - switch (targetType) - { - case PhaseTargetType.DeploymentGroup: - newValue = new DeploymentGroupTarget(); - break; - - case PhaseTargetType.Server: - newValue = new ServerTarget(); - break; - - case PhaseTargetType.Queue: - newValue = new AgentQueueTarget(); - break; - - case PhaseTargetType.Pool: - newValue = new AgentPoolTarget(); - break; - } - - if (value != null) - { - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PhaseTargetType.cs b/src/Sdk/DTPipelines/Pipelines/PhaseTargetType.cs deleted file mode 100644 index 3163e0b93..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PhaseTargetType.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [ClientIgnore] - [EditorBrowsable(EditorBrowsableState.Never)] - public enum PhaseTargetType - { - [EnumMember] - Queue, - - [EnumMember] - Server, - - [EnumMember] - DeploymentGroup, - - [EnumMember] - Pool, - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineBuildContext.cs b/src/Sdk/DTPipelines/Pipelines/PipelineBuildContext.cs deleted file mode 100644 index 828bf64ac..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineBuildContext.cs +++ /dev/null @@ -1,182 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PipelineBuildContext : PipelineContextBase - { - public PipelineBuildContext() - : this(new BuildOptions()) - { - } - - public PipelineBuildContext( - IPipelineContext context, - BuildOptions options) - : base(context) - { - m_buildOptions = options ?? new BuildOptions(); - } - - public PipelineBuildContext( - BuildOptions buildOptions, - DictionaryContextData data = null, - ICounterStore counterStore = null, - IResourceStore resourceStore = null, - IList stepProviders = null, - ITaskStore taskStore = null, - IPackageStore packageStore = null, - IInputValidator inputValidator = null, - IPipelineTraceWriter trace = null, - EvaluationOptions expressionOptions = null, - IList phaseProviders = null) - : base(data, counterStore, packageStore, resourceStore, taskStore, stepProviders, null, trace, expressionOptions) - { - m_buildOptions = buildOptions ?? new BuildOptions(); - m_inputValidator = inputValidator; - m_phaseProviders = phaseProviders; - } - - public BuildOptions BuildOptions - { - get - { - return m_buildOptions; - } - } - - public IInputValidator InputValidator - { - get - { - return m_inputValidator; - } - } - - public IReadOnlyList PhaseProviders - { - get - { - return m_phaseProviders.ToList(); - } - } - - internal ValidationResult Validate(PipelineProcess process) - { - var result = new ValidationResult(); - - // If requested to do so, validate the container resource to ensure it was specified properly. This will - // also handle endpoint authorization if the container requires access to a docker registry. - if (this.ResourceStore != null) - { - foreach (var container in this.ResourceStore.Containers.GetAll().Where(x => x.Endpoint != null)) - { - result.ReferencedResources.AddEndpointReference(container.Endpoint); - - if (this.BuildOptions.ValidateResources) - { - var endpoint = this.ResourceStore.GetEndpoint(container.Endpoint); - if (endpoint == null) - { - result.UnauthorizedResources.AddEndpointReference(container.Endpoint); - result.Errors.Add(new PipelineValidationError(PipelineStrings.ServiceEndpointNotFound(container.Endpoint))); - } - else - { - if (!endpoint.Type.Equals(ServiceEndpointTypes.Docker, StringComparison.OrdinalIgnoreCase)) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.ContainerResourceInvalidRegistryEndpointType(container.Alias, endpoint.Type, endpoint.Name))); - } - else - { - container.Endpoint = new ServiceEndpointReference - { - Id = endpoint.Id, - }; - } - } - } - } - - foreach (var repository in this.ResourceStore.Repositories.GetAll()) - { - var expandedProperties = new Dictionary(StringComparer.OrdinalIgnoreCase); - foreach (var property in repository.Properties.GetItems()) - { - expandedProperties[property.Key] = this.ExpandVariables(property.Value); - } - - foreach (var expandedProperty in expandedProperties) - { - repository.Properties.Set(expandedProperty.Key, expandedProperty.Value); - } - } - - if (this.EnvironmentVersion > 1) - { - // always add self or designer repo to repository list - RepositoryResource defaultRepo = null; - var selfRepo = this.ResourceStore.Repositories.Get(PipelineConstants.SelfAlias); - if (selfRepo == null) - { - var designerRepo = this.ResourceStore.Repositories.Get(PipelineConstants.DesignerRepo); - if (designerRepo != null) - { - defaultRepo = designerRepo; - } - else - { - System.Diagnostics.Debug.Fail("Repositories are not filled in."); - } - } - else - { - defaultRepo = selfRepo; - } - - if (defaultRepo != null) - { - result.ReferencedResources.Repositories.Add(defaultRepo); - - // Add the endpoint - if (defaultRepo.Endpoint != null) - { - result.ReferencedResources.AddEndpointReference(defaultRepo.Endpoint); - - if (this.BuildOptions.ValidateResources) - { - var repositoryEndpoint = this.ResourceStore.GetEndpoint(defaultRepo.Endpoint); - if (repositoryEndpoint == null) - { - result.UnauthorizedResources?.AddEndpointReference(defaultRepo.Endpoint); - result.Errors.Add(new PipelineValidationError(PipelineStrings.ServiceEndpointNotFound(defaultRepo.Endpoint))); - } - else - { - defaultRepo.Endpoint = new ServiceEndpointReference() { Id = repositoryEndpoint.Id }; - } - } - } - } - } - } - - // Validate the graph of stages - GraphValidator.Validate(this, result, PipelineStrings.StageNameWhenNoNameIsProvided, null, process.Stages, Stage.GetErrorMessage); - - return result; - } - - private IInputValidator m_inputValidator; - private IList m_phaseProviders; - private BuildOptions m_buildOptions; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineBuildResult.cs b/src/Sdk/DTPipelines/Pipelines/PipelineBuildResult.cs deleted file mode 100644 index 817946bc6..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineBuildResult.cs +++ /dev/null @@ -1,73 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineBuildResult - { - public PipelineBuildResult( - PipelineEnvironment environment, - PipelineProcess process, - ValidationResult result) - { - this.Environment = environment; - this.Process = process; - m_validationResult = result; - } - - /// - /// Gets the environment which was generated by the builder. - /// - public PipelineEnvironment Environment - { - get; - private set; - } - - /// - /// Gets the process which was generated by the builder. - /// - public PipelineProcess Process - { - get; - private set; - } - - /// - /// Gets the list of errors which occurred while building the pipeline. - /// - public IList Errors - { - get - { - return m_validationResult.Errors; - } - } - - /// - /// Gets the set of all resources which are referenced by the pipeline. - /// - public PipelineResources ReferencedResources - { - get - { - return m_validationResult.ReferencedResources; - } - } - - /// - /// Gets the set of unauthorized resources, if any, which are referenced by the pipeline. - /// - public PipelineResources UnauthorizedResources - { - get - { - return m_validationResult.UnauthorizedResources; - } - } - - private readonly ValidationResult m_validationResult; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineBuilder.cs b/src/Sdk/DTPipelines/Pipelines/PipelineBuilder.cs deleted file mode 100644 index 40095be9b..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineBuilder.cs +++ /dev/null @@ -1,411 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Diagnostics; -using System.Linq; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism for customization of pipeline construction by different hosting environments. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineBuilder - { - /// - /// Initializes a new PipelineBuilder instance with default service implementations. - /// - public PipelineBuilder() - : this(null, null, null, null, null, null, null, null, null) - { - } - - /// - /// Initilaizes a new PipelineBuilder instance with the specified services used for resolution of - /// resources available to pipelines. - /// - /// The resources available for use within a pipeline - /// The tasks available for use within a pipeline - /// The secret stores available for use within a pipeline - public PipelineBuilder( - EvaluationOptions expressionOptions = null, - ICounterStore counterStore = null, - IPackageStore packageStore = null, - IResourceStore resourceStore = null, - IList stepProviders = null, - ITaskStore taskStore = null, - ITaskTemplateStore templateStore = null, - IPipelineIdGenerator idGenerator = null, - IList phaseProviders = null) - : this(new PipelineContextBuilder(counterStore, packageStore, resourceStore, stepProviders, taskStore, idGenerator, expressionOptions, phaseProviders), templateStore) - { - } - - /// - /// Initializes a new PipelineBuilder instance for the specified context. - /// - /// The context which should be used for validation - internal PipelineBuilder(IPipelineContext context) - : this(new PipelineContextBuilder(context)) - { - } - - private PipelineBuilder( - PipelineContextBuilder contextBuilder, - ITaskTemplateStore templateStore = null) - { - ArgumentUtility.CheckForNull(contextBuilder, nameof(contextBuilder)); - - m_contextBuilder = contextBuilder; - m_templateStore = templateStore; - } - - /// - /// Gets or sets the default queue which is assigned automatically to phases with no target and existing agent - /// queue targets without a queue specified. - /// - public AgentQueueReference DefaultQueue - { - get; - set; - } - - /// - /// Gets or sets the default agent specification which is assigned automatically to phases with no target and existing agent - /// queue targets without an agent specification specified. - /// - public JObject DefaultAgentSpecification - { - get; - set; - } - - /// - /// Gets or sets the default checkout options which are propagated to all repository resources defined - /// within a pipeline if explicit options are not provided at checkout. - /// - public CheckoutOptions DefaultCheckoutOptions - { - get; - set; - } - - /// - /// Gets or sets the default workspace options which are propagated to all agent jobs which do not explicitly - /// define overrides. - /// - public WorkspaceOptions DefaultWorkspaceOptions - { - get; - set; - } - - /// - /// Gets or sets the environment version which should be used. - /// - public Int32 EnvironmentVersion - { - get - { - return m_contextBuilder.EnvironmentVersion; - } - set - { - m_contextBuilder.EnvironmentVersion = value; - } - } - - /// - /// Gets the counter store configured for this builder. - /// - public ICounterStore CounterStore => m_contextBuilder.CounterStore; - - /// - /// Gets the ID generator configured for this builder. - /// - public IPipelineIdGenerator IdGenerator => m_contextBuilder.IdGenerator; - - /// - /// Gets the package store configured for this builder. - /// - public IPackageStore PackageStore => m_contextBuilder.PackageStore; - - /// - /// Gets the resource store configured for this builder. - /// - public IResourceStore ResourceStore => m_contextBuilder.ResourceStore; - - /// - /// Gets the user variables which have been set for this builder. - /// - public IList UserVariables => m_contextBuilder.UserVariables; - - /// - /// Gets the system variables which have been set for this builder. - /// - public IDictionary SystemVariables => m_contextBuilder.SystemVariables; - - /// - /// Builds a new PipelineProcess instance using the specified environment. - /// - /// A list of phases which should be used to build the process - /// The validation which should be performed on the pipeline - /// A PipelineBuildResult which contains a runnable pipeline process - public PipelineBuildResult Build( - IList phases, - BuildOptions options = null) - { - ArgumentUtility.CheckEnumerableForEmpty(phases, nameof(phases)); - - options = options ?? BuildOptions.None; - - var stage = new Stage - { - Name = PipelineConstants.DefaultJobName, - }; - - stage.Phases.AddRange(phases); - return Build(new[] { stage }, options); - } - - /// - /// Builds a new PipelineProcess instance. - /// - /// A list of stages which should be used to build the process - /// The validation which should be performed on the pipeline - /// A PipelineBuildResult which contains a runnable pipeline process - public PipelineBuildResult Build( - IList stages, - BuildOptions options = null, - TemplateToken environmentVariables = null) - { - var context = CreateBuildContext(options); - - if (this.DefaultCheckoutOptions != null) - { - foreach (var repository in context.ResourceStore.Repositories.GetAll()) - { - if (!repository.Properties.TryGetValue(RepositoryPropertyNames.CheckoutOptions, out _)) - { - repository.Properties.Set(RepositoryPropertyNames.CheckoutOptions, this.DefaultCheckoutOptions.Clone()); - } - } - } - - // First gather any validation errors and all referenced resources - var process = CreateProcess(context, stages); - var result = context.Validate(process); - - // Output the environment - var environment = result.Environment = new PipelineEnvironment(); - environment.Version = context.EnvironmentVersion; - environment.Counters.AddRange(context.CounterStore.Counters); - environment.Resources.MergeWith(context.ResourceStore.GetAuthorizedResources()); - environment.UserVariables.AddRange(m_contextBuilder.UserVariables); - environment.SystemVariables.AddRange(m_contextBuilder.SystemVariables); - environment.EnvironmentVariables = environmentVariables; - - return new PipelineBuildResult(result.Environment, process, result); - } - - public PipelineBuildContext CreateBuildContext( - BuildOptions options, - Boolean includeSecrets = false) - { - return m_contextBuilder.CreateBuildContext(options, this.PackageStore, includeSecrets); - } - - public PhaseExecutionContext CreatePhaseExecutionContext( - StageInstance stage, - PhaseInstance phase, - PipelineState state = PipelineState.InProgress, - DictionaryContextData data = null, - Boolean includeSecrets = false, - IPipelineTraceWriter trace = null, - ExecutionOptions executionOptions = null) - { - return m_contextBuilder.CreatePhaseExecutionContext(stage, phase, state, data, includeSecrets, trace, executionOptions); - } - - public StageExecutionContext CreateStageExecutionContext( - StageInstance stage, - PipelineState state = PipelineState.InProgress, - DictionaryContextData data = null, - Boolean includeSecrets = false, - IPipelineTraceWriter trace = null, - ExecutionOptions executionOptions = null) - { - return m_contextBuilder.CreateStageExecutionContext(stage, state, data, includeSecrets, trace, executionOptions); - } - - public IList Validate( - PipelineProcess process, - BuildOptions options = null) - { - ArgumentUtility.CheckForNull(process, nameof(process)); - - var context = CreateBuildContext(options); - return context.Validate(process).Errors; - } - - public IList Validate( - IList steps, - PhaseTarget target = null, - BuildOptions options = null) - { - ArgumentUtility.CheckForNull(steps, nameof(steps)); - - var phase = new Phase(); - phase.Steps.AddRange(steps); - phase.Target = target; - - var stage = new Stage(PipelineConstants.DefaultJobName, new[] { phase }); - - var context = CreateBuildContext(options); - var process = CreateProcess(context, new[] { stage }); - return context.Validate(process).Errors; - } - - public PipelineResources GetReferenceResources( - IList steps, - PhaseTarget target = null) - { - ArgumentUtility.CheckForNull(steps, nameof(steps)); - - var phase = new Phase(); - phase.Steps.AddRange(steps); - phase.Target = target; - - var stage = new Stage(PipelineConstants.DefaultJobName, new[] { phase }); - - var context = CreateBuildContext(new BuildOptions()); - var process = CreateProcess(context, new[] { stage }); - return context.Validate(process).ReferencedResources; - } - - private PipelineProcess CreateProcess( - PipelineBuildContext context, - IList stages) - { - ArgumentUtility.CheckForNull(context, nameof(context)); - ArgumentUtility.CheckEnumerableForEmpty(stages, nameof(stages)); - - // Now inject the tasks into each appropriate phase - foreach (var stage in stages) - { - foreach (var phaseNode in stage.Phases) - { - // Set the default target to be a queue target and leave it up to the hosting environment to - // specify a default in the resource store. - if (phaseNode.Target == null) - { - phaseNode.Target = new AgentQueueTarget(); - } - - // Agent queues are the default target type - if (phaseNode.Target.Type == PhaseTargetType.Queue && this.DefaultQueue != null) - { - var queueTarget = phaseNode.Target as AgentQueueTarget; - var useDefault = false; - var queue = queueTarget.Queue; - if (queue == null) - { - useDefault = true; - } - else if (queue.Id == 0) - { - var name = queue.Name; - if (name == null || (name.IsLiteral && String.IsNullOrEmpty(name.Literal))) - { - useDefault = true; - } - } - - if (useDefault) - { - queueTarget.Queue = this.DefaultQueue.Clone(); - if (queueTarget.AgentSpecification == null) - { - queueTarget.AgentSpecification = (JObject)DefaultAgentSpecification?.DeepClone(); - } - } - } - - // Set default workspace options - if (phaseNode.Target.Type == PhaseTargetType.Queue && this.DefaultWorkspaceOptions != null) - { - var queueTarget = phaseNode.Target as AgentQueueTarget; - if (queueTarget.Workspace == null) - { - queueTarget.Workspace = this.DefaultWorkspaceOptions.Clone(); - } - } - - var steps = default(IList); - if (phaseNode.Type == PhaseType.Phase) - { - steps = (phaseNode as Phase).Steps; - } - else if (phaseNode.Type == PhaseType.JobFactory) - { - steps = (phaseNode as JobFactory).Steps; - } - - if (steps != null) - { - var resolvedSteps = new List(); - foreach (var step in steps.Where(x => x.Enabled)) - { - if (step.Type == StepType.Task) - { - var taskStep = step as TaskStep; - resolvedSteps.Add(taskStep); - } - else if (step.Type == StepType.Group) - { - var taskStepGroup = step as GroupStep; - resolvedSteps.Add(taskStepGroup); - } - else if (step.Type == StepType.Action) - { - var actionStep = step as ActionStep; - resolvedSteps.Add(actionStep); - } - else if (step.Type == StepType.TaskTemplate) - { - var templateStep = step as TaskTemplateStep; - if (m_templateStore == null) - { - throw new ArgumentException(PipelineStrings.TemplateStoreNotProvided(templateStep.Name, nameof(ITaskTemplateStore))); - } - - var resolvedTasks = m_templateStore.ResolveTasks(templateStep); - resolvedSteps.AddRange(resolvedTasks); - } - else - { - // We should never be here. - Debug.Fail(step.Type.ToString()); - } - } - - steps.Clear(); - steps.AddRange(resolvedSteps); - } - } - } - - return new PipelineProcess(stages); - } - - private readonly ITaskTemplateStore m_templateStore; - private readonly PipelineContextBuilder m_contextBuilder; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineConstants.cs b/src/Sdk/DTPipelines/Pipelines/PipelineConstants.cs index 323f0fee5..2d599dd9c 100644 --- a/src/Sdk/DTPipelines/Pipelines/PipelineConstants.cs +++ b/src/Sdk/DTPipelines/Pipelines/PipelineConstants.cs @@ -1,8 +1,5 @@ using System; -using System.Collections.Generic; using System.ComponentModel; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json.Linq; namespace GitHub.DistributedTask.Pipelines { @@ -12,18 +9,8 @@ namespace GitHub.DistributedTask.Pipelines [EditorBrowsable(EditorBrowsableState.Never)] public static class PipelineConstants { - /// - /// The minimum agent version when performing an advanced checkout. This demand - /// is required when multiple checkout steps are used, when the checkout step - /// is not the first step, or when any repository is checked out other than self - /// or none. - /// - public static readonly String AdvancedCheckoutMinAgentVersion = "2.137.0"; - public static readonly String AgentVersionDemandName = "Runner.Version"; - public static readonly String AgentName = "Agent.Name"; - /// /// The default job cancel timeout in minutes. /// @@ -50,21 +37,11 @@ namespace GitHub.DistributedTask.Pipelines /// public static readonly Int32 MaxNodeNameLength = 100; - /// - /// The repository alias to use for dont-sync-sources. - /// - public static readonly String NoneAlias = "none"; - /// /// Alias for the self repository. /// public static readonly String SelfAlias = "self"; - /// - /// Alias for the repository coming from designer build definition. - /// - public static readonly String DesignerRepo = "__designer_repo"; - /// /// Error code during graph validation. /// @@ -90,9 +67,6 @@ namespace GitHub.DistributedTask.Pipelines /// internal const String StartingPointNotFound = nameof(StartingPointNotFound); - internal const String CheckpointNodeInstanceNameClaimKey = "nodeInstanceName"; - internal const String CheckpointIdClaimKey = "checkpointId"; - public static class CheckoutTaskInputs { public static readonly String Repository = "repository"; @@ -120,102 +94,5 @@ namespace GitHub.DistributedTask.Pipelines public static readonly String Resources = "resources"; public static readonly String All = "all"; } - - public static class EnvironmentVariables - { - public static readonly String EnvironmentId = "Environment.Id"; - public static readonly String EnvironmentName = "Environment.Name"; - public static readonly String EnvironmentResourceId = "Environment.ResourceId"; - public static readonly String EnvironmentResourceName = "Environment.ResourceName"; - } - - public static readonly TaskDefinition CheckoutTask = new TaskDefinition - { - Id = new Guid("6d15af64-176c-496d-b583-fd2ae21d4df4"), - Name = "Checkout", - FriendlyName = "Get sources", - Author = "Microsoft", - RunsOn = { TaskRunsOnConstants.RunsOnAgent }, - Version = new TaskVersion("1.0.0"), - Description = "Get sources from a repository. Supports Git, TfsVC, and SVN repositories.", - HelpMarkDown = "[More Information](https://github.com)", - Inputs = { - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.Repository, - Required = true, - InputType = TaskInputType.Repository - }, - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.Clean, - Required = false, - DefaultValue = Boolean.TrueString, - InputType = TaskInputType.Boolean - }, - // Git - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.Submodules, // True or Recursive - Required = false, - InputType = TaskInputType.String - }, - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.Lfs, // Checkout lfs object - Required = false, - DefaultValue = Boolean.FalseString, - InputType = TaskInputType.Boolean - }, - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.FetchDepth, // Enable shallow fetch - Required = false, - InputType = TaskInputType.String - }, - new TaskInputDefinition() - { - Name = CheckoutTaskInputs.PersistCredentials, // Allow script git - Required = false, - DefaultValue = Boolean.FalseString, - InputType = TaskInputType.Boolean - }, - }, - Execution = - { - { - "agentPlugin", - JObject.FromObject(new Dictionary(){ { "target", "Agent.Plugins.Repository.CheckoutTask, Agent.Plugins"} }) - } - }, - PostJobExecution = - { - { - "agentPlugin", - JObject.FromObject(new Dictionary(){ { "target", "Agent.Plugins.Repository.CleanupTask, Agent.Plugins"} }) - } - } - }; - - public static class ScriptStepInputs - { - public static readonly String Script = "script"; - public static readonly String WorkingDirectory = "workingDirectory"; - public static readonly String Shell = "shell"; - } - - public static Boolean IsCheckoutTask(this Step step) - { - if (step is TaskStep task && - task.Reference.Id == PipelineConstants.CheckoutTask.Id && - task.Reference.Version == PipelineConstants.CheckoutTask.Version) - { - return true; - } - else - { - return false; - } - } } } diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineContextBase.cs b/src/Sdk/DTPipelines/Pipelines/PipelineContextBase.cs deleted file mode 100644 index 4daecff3f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineContextBase.cs +++ /dev/null @@ -1,439 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Logging; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides base functionality for all contexts used during build and execution if a pipeline. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PipelineContextBase : IPipelineContext - { - private protected PipelineContextBase(IPipelineContext context) - { - this.EnvironmentVersion = context.EnvironmentVersion; - this.SystemVariableNames.UnionWith(context.SystemVariableNames); - this.Variables.AddRange(context.Variables); - m_referencedResources = context.ReferencedResources?.Clone(); - - this.CounterStore = context.CounterStore; - this.IdGenerator = context.IdGenerator ?? new PipelineIdGenerator(); - this.PackageStore = context.PackageStore; - this.ResourceStore = context.ResourceStore; - this.TaskStore = context.TaskStore; - this.Trace = context.Trace; - m_secretMasker = new Lazy(() => CreateSecretMasker()); - - // This is a copy, don't dynamically set pipeline decorators, they are already set. - this.StepProviders = context.StepProviders; - - if (context.Data?.Count > 0) - { - m_data = new DictionaryContextData(); - foreach (var pair in context.Data) - { - m_data[pair.Key] = pair.Value; - } - } - } - - private protected PipelineContextBase( - DictionaryContextData data, - ICounterStore counterStore, - IPackageStore packageStore, - IResourceStore resourceStore, - ITaskStore taskStore, - IList stepProviders, - IPipelineIdGenerator idGenerator = null, - IPipelineTraceWriter trace = null, - EvaluationOptions expressionOptions = null) - { - m_data = data; - this.CounterStore = counterStore; - this.ExpressionOptions = expressionOptions ?? new EvaluationOptions(); - this.IdGenerator = idGenerator ?? new PipelineIdGenerator(); - this.PackageStore = packageStore; - this.ResourceStore = resourceStore; - this.TaskStore = taskStore; - this.Trace = trace; - m_secretMasker = new Lazy(() => CreateSecretMasker()); - - // Setup pipeline decorators - var aggregatedStepProviders = new List(); - - // Add resources first - if (this.ResourceStore != null) - { - aggregatedStepProviders.Add(this.ResourceStore); - } - - // Add custom pipeline decorators - if (stepProviders != null) - { - aggregatedStepProviders.AddRange(stepProviders); - } - - this.StepProviders = aggregatedStepProviders; - } - - /// - /// Gets the counter store for the current context - /// - public ICounterStore CounterStore - { - get; - } - - // Gets the available context when evaluating expressions - public DictionaryContextData Data - { - get - { - if (m_data == null) - { - m_data = new DictionaryContextData(); - } - return m_data; - } - } - - /// - /// Gets or sets the version of the environment - /// - public Int32 EnvironmentVersion - { - get; - internal set; - } - - /// - /// Gets the expression evaluation options for this context. - /// - public EvaluationOptions ExpressionOptions - { - get; - } - - /// - /// Gets the id generator configured for this context. - /// - public IPipelineIdGenerator IdGenerator - { - get; - } - - /// - /// Gets the package store configured for this context. - /// - public IPackageStore PackageStore - { - get; - } - - /// - /// Gets the resources referenced within this context. - /// - public PipelineResources ReferencedResources - { - get - { - if (m_referencedResources == null) - { - m_referencedResources = new PipelineResources(); - } - return m_referencedResources; - } - } - - /// - /// Gets the resource store for the current context - /// - public IResourceStore ResourceStore - { - get; - } - - /// - /// Gets the step providers for the current context - /// - public IReadOnlyList StepProviders - { - get; - } - - /// - /// Gets the secret masker for the current context - /// - public ISecretMasker SecretMasker - { - get - { - return m_secretMasker.Value; - } - } - - /// - /// Gets the task store for the current context - /// - public ITaskStore TaskStore - { - get; - } - - /// - /// Gets the trace for the current context - /// - public IPipelineTraceWriter Trace - { - get; - } - - /// - /// Gets the system variable names for the current context - /// - public ISet SystemVariableNames - { - get - { - if (m_systemVariables == null) - { - m_systemVariables = new HashSet(StringComparer.OrdinalIgnoreCase); - } - return m_systemVariables; - } - } - - /// - /// Gets the variables configured on the context - /// - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new VariablesDictionary(); - } - return m_variables; - } - } - - /// - /// Gets a value indicating if secret variables have been accessed - /// - protected virtual Boolean SecretsAccessed - { - get - { - return m_variables?.SecretsAccessed.Count > 0; - } - } - - public virtual ISecretMasker CreateSecretMasker() - { - var secretMasker = new SecretMasker(); - - // Add variable secrets - if (m_variables?.Count > 0) - { - foreach (var variable in m_variables.Values.Where(x => x.IsSecret)) - { - secretMasker.AddValue(variable.Value); - } - } - - return secretMasker; - } - - /// - /// Expand macros of the format $(variableName) using the current context. - /// - /// The value which contains macros to expand - /// True if secrets should be replaced with '***'; otherwise, false - /// The evaluated value with all defined macros expanded to the value in the current context - public String ExpandVariables( - String value, - Boolean maskSecrets = false) - { - if (!String.IsNullOrEmpty(value) && m_variables?.Count > 0) - { - return VariableUtility.ExpandVariables(value, m_variables, false, maskSecrets); - } - else - { - return value; - } - } - - /// - /// Expand macros of the format $(variableName) using the current context. - /// - /// The JToken value which contains macros to expand - /// The evaluated value with all defined macros expanded to the value in the current context - public JToken ExpandVariables(JToken value) - { - if (value != null && m_variables?.Count > 0) - { - return VariableUtility.ExpandVariables(value, m_variables, false); - } - else - { - return value; - } - } - - /// - /// Expand all variables and macros present as values (not keys) in a given JObject. - /// Conditionally record unresolved expressions or macros as errors. - /// - public ExpressionResult Evaluate(JObject value) - { - if (value == null) - { - return null; - } - - var containsSecrets = false; - String ResolveExpression(String s) - { - if (!ExpressionValue.IsExpression(s)) - { - return s; - } - - String resolvedValue = null; - try - { - var expressionResult = Evaluate(ExpressionValue.TrimExpression(s)); - containsSecrets |= expressionResult.ContainsSecrets; - resolvedValue = expressionResult.Value; - } - catch (ExpressionException) - { - return s; - } - - if (!String.IsNullOrEmpty(resolvedValue)) - { - return resolvedValue; - } - - return s; - } - - // recurse through object - var resolvedSpec = new JObject(); - foreach (var pair in value) - { - var v = pair.Value; - switch (v.Type) - { - case JTokenType.Object: - // recurse - var expressionResult = Evaluate(v.Value()); - containsSecrets |= expressionResult.ContainsSecrets; - resolvedSpec[pair.Key] = expressionResult.Value; - break; - case JTokenType.String: - // resolve - resolvedSpec[pair.Key] = ExpandVariables(ResolveExpression(v.Value())); - break; - default: - // no special handling - resolvedSpec[pair.Key] = v; - break; - } - } - - return new ExpressionResult(resolvedSpec, containsSecrets); - } - - /// - /// Evalutes the provided expression using the current context. - /// - /// The type of result expected - /// The expression string to evaluate - /// A value indicating the evaluated result and whether or not secrets were accessed during evaluation - public ExpressionResult Evaluate(String expression) - { - if (!m_parsedExpressions.TryGetValue(expression, out IExpressionNode parsedExpression)) - { - parsedExpression = new ExpressionParser().CreateTree(expression, this.Trace, this.GetSupportedNamedValues(), this.GetSupportedFunctions()); - m_parsedExpressions.Add(expression, parsedExpression); - } - - this.ResetSecretsAccessed(); - var evaluationResult = parsedExpression.Evaluate(this.Trace, this.SecretMasker, this, this.ExpressionOptions); - throw new NotSupportedException(); - } - - protected virtual void ResetSecretsAccessed() - { - m_variables?.SecretsAccessed.Clear(); - } - - protected virtual IEnumerable GetSupportedFunctions() - { - return Enumerable.Empty(); - } - - protected virtual IEnumerable GetSupportedNamedValues() - { - return Enumerable.Empty(); - } - - internal void SetSystemVariables(IEnumerable variables) - { - foreach (var variable in variables) - { - this.SystemVariableNames.Add(variable.Name); - this.Variables[variable.Name] = new VariableValue(variable.Value, variable.Secret); - } - } - - internal void SetUserVariables(IEnumerable variables) - { - foreach (var variable in variables.Where(x=>!x.Name.StartsWith("system.", StringComparison.OrdinalIgnoreCase) && !this.SystemVariableNames.Contains(x.Name))) - { - this.Variables[variable.Name] = new VariableValue(variable.Value, variable.Secret); - } - } - - internal void SetUserVariables(IDictionary variables) - { - // Do not allow user variables to override system variables which were set at a higher scope. In this case - // the system variable should always win rather than the most specific variable winning. - foreach (var variable in variables.Where(x => !x.Key.StartsWith("system.", StringComparison.OrdinalIgnoreCase) && !this.SystemVariableNames.Contains(x.Key))) - { - this.Variables[variable.Key] = variable.Value; - } - } - - internal void SetSystemVariables(IDictionary variables) - { - if (variables?.Count > 0) - { - foreach (var variable in variables) - { - this.SystemVariableNames.Add(variable.Key); - this.Variables[variable.Key] = variable.Value?.Clone(); - } - } - } - - private DictionaryContextData m_data; - private VariablesDictionary m_variables; - private HashSet m_systemVariables; - private Lazy m_secretMasker; - private PipelineResources m_referencedResources; - private Dictionary m_parsedExpressions = new Dictionary(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineContextBuilder.cs b/src/Sdk/DTPipelines/Pipelines/PipelineContextBuilder.cs deleted file mode 100644 index 79f3939a0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineContextBuilder.cs +++ /dev/null @@ -1,562 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - internal sealed class PipelineContextBuilder - { - public PipelineContextBuilder() - : this(null, null, null, null, null) - { - } - - public PipelineContextBuilder( - ICounterStore counterStore = null, - IPackageStore packageStore = null, - IResourceStore resourceStore = null, - IList stepProviders = null, - ITaskStore taskStore = null, - IPipelineIdGenerator idGenerator = null, - EvaluationOptions expressionOptions = null, - IList phaseProviders = null) - { - this.EnvironmentVersion = 2; - this.CounterStore = counterStore ?? new CounterStore(); - this.IdGenerator = idGenerator ?? new PipelineIdGenerator(); - this.PackageStore = packageStore ?? new PackageStore(); - this.ResourceStore = resourceStore ?? new ResourceStore(); - this.StepProviders = stepProviders ?? new List(); - this.TaskStore = taskStore ?? new TaskStore(); - this.ExpressionOptions = expressionOptions ?? new EvaluationOptions(); - this.PhaseProviders = phaseProviders ?? new List(); - } - - internal PipelineContextBuilder(IPipelineContext context) - : this(context.CounterStore, context.PackageStore, context.ResourceStore, context.StepProviders.ToList(), context.TaskStore, context.IdGenerator, context.ExpressionOptions) - { - m_context = context; - - var userVariables = new List(); - var systemVariables = new VariablesDictionary(); - foreach (var variable in context.Variables) - { - if (context.SystemVariableNames.Contains(variable.Key)) - { - systemVariables[variable.Key] = variable.Value.Clone(); - } - else - { - var userVariable = new Variable - { - Name = variable.Key, - Secret = variable.Value?.IsSecret ?? false, - Value = variable.Value?.Value, - }; - - userVariables.Add(userVariable); - } - } - - // For simplicity the variables are currently marked as read-only for the explicit - // context scenario. - m_userVariables = userVariables.AsReadOnly(); - m_systemVariables = systemVariables.AsReadOnly(); - } - - /// - /// Gets the counter store configured for the builder. - /// - public ICounterStore CounterStore - { - get; - } - - public IEnvironmentStore EnvironmentStore - { - get; - } - - /// - /// Gets or sets the environment version, controlling behaviors related to variable groups and step injection. - /// - public Int32 EnvironmentVersion - { - get; - set; - } - - /// - /// Gets the generator for pipeline identifiers. - /// - public IPipelineIdGenerator IdGenerator - { - get; - } - - /// - /// Gets the package store configured for the builder. - /// - public IPackageStore PackageStore - { - get; - } - - /// - /// Gets the resource store configured for the builder. - /// - public IResourceStore ResourceStore - { - get; - } - - /// - /// Gets the list of step providers configured for the builder. - /// - public IList StepProviders - { - get; - } - - public IList PhaseProviders - { - get; - } - - /// - /// Gets the task store configured for the builder. - /// - public ITaskStore TaskStore - { - get; - } - - /// - /// Gets the expression evaluation options configured for the builder. - /// - public EvaluationOptions ExpressionOptions - { - get; - } - - /// - /// Gets a list of variable sets included in the pipeline. - /// - public IList UserVariables - { - get - { - if (m_userVariables == null) - { - m_userVariables = new List(); - } - return m_userVariables; - } - } - - /// - /// Gets the system variables included in the pipeline. - /// - public IDictionary SystemVariables - { - get - { - if (m_systemVariables == null) - { - m_systemVariables = new VariablesDictionary(); - } - return m_systemVariables; - } - } - - public PipelineBuildContext CreateBuildContext( - BuildOptions options, - IPackageStore packageStore = null, - Boolean includeSecrets = false) - { - PipelineBuildContext context = null; - if (m_context == null) - { - context = new PipelineBuildContext(options, null, this.CounterStore, this.ResourceStore, this.StepProviders, this.TaskStore, packageStore, new InputValidator(), null, this.ExpressionOptions, this.PhaseProviders); - SetVariables(context, includeSecrets: includeSecrets); - context.EnvironmentVersion = this.EnvironmentVersion; - } - else - { - context = new PipelineBuildContext(m_context, options); - } - - return context; - } - - public StageExecutionContext CreateStageExecutionContext( - StageInstance stage, - PipelineState state = PipelineState.InProgress, - DictionaryContextData data = null, - Boolean includeSecrets = false, - IPipelineTraceWriter trace = null, - ExecutionOptions executionOptions = null) - { - if (m_context != null) - { - throw new NotSupportedException(); - } - - var context = new StageExecutionContext(stage, state, data, this.CounterStore, this.PackageStore, this.ResourceStore, this.TaskStore, this.StepProviders, this.IdGenerator, trace, this.ExpressionOptions, executionOptions); - SetVariables(context, stage, includeSecrets: includeSecrets); - context.EnvironmentVersion = this.EnvironmentVersion; - return context; - } - - public PhaseExecutionContext CreatePhaseExecutionContext( - StageInstance stage, - PhaseInstance phase, - PipelineState state = PipelineState.InProgress, - DictionaryContextData data = null, - Boolean includeSecrets = false, - IPipelineTraceWriter trace = null, - ExecutionOptions executionOptions = null) - { - if (m_context != null) - { - throw new NotSupportedException(); - } - - var context = new PhaseExecutionContext(stage, phase, state, data, this.CounterStore, this.PackageStore, this.ResourceStore, this.TaskStore, this.StepProviders, this.IdGenerator, trace, this.ExpressionOptions, executionOptions); - SetVariables(context, stage, phase, includeSecrets); - context.EnvironmentVersion = this.EnvironmentVersion; - return context; - } - - private void SetVariables( - IPipelineContext context, - StageInstance stage = null, - PhaseInstance phase = null, - Boolean includeSecrets = false) - { - // Next merge variables specified from alternative sources in the order they are presented. This may - // be specified by build/release definitions or lower constructs, or may be specified by the user as - // input variables to override other values. - var referencedVariableGroups = new Dictionary(StringComparer.OrdinalIgnoreCase); - var expressionsToEvaluate = new Dictionary>(StringComparer.OrdinalIgnoreCase); - if (m_userVariables?.Count > 0 || stage?.Definition?.Variables.Count > 0 || phase?.Definition?.Variables.Count > 0) - { - var userVariables = this.UserVariables.Concat(stage?.Definition?.Variables ?? Enumerable.Empty()).Concat(phase?.Definition?.Variables ?? Enumerable.Empty()); - foreach (var variable in userVariables) - { - if (variable is Variable inlineVariable) - { - if (ExpressionValue.TryParse(inlineVariable.Value, out var expression)) - { - expressionsToEvaluate[inlineVariable.Name] = expression; - } - - if (context.Variables.TryGetValue(inlineVariable.Name, out VariableValue existingValue)) - { - existingValue.Value = inlineVariable.Value; - existingValue.IsSecret |= inlineVariable.Secret; - - // Remove the reference to the variable group - referencedVariableGroups.Remove(inlineVariable.Name); - } - else - { - context.Variables[inlineVariable.Name] = new VariableValue(inlineVariable.Value, inlineVariable.Secret); - } - } - else if (variable is VariableGroupReference groupReference) - { - var variableGroup = this.ResourceStore.VariableGroups.Get(groupReference); - if (variableGroup == null) - { - throw new ResourceNotFoundException(PipelineStrings.VariableGroupNotFound(variableGroup)); - } - - // A pre-computed list of keys wins if it is present, otherwise we compute it dynamically - if (groupReference.SecretStore?.Keys.Count > 0) - { - foreach (var key in groupReference.SecretStore.Keys) - { - // Ignore the key if it isn't present in the variable group - if (!variableGroup.Variables.TryGetValue(key, out var variableGroupEntry)) - { - continue; - } - - // Variable groups which have secrets providers use delayed resolution depending on targets - // being invoked, etc. - if (context.Variables.TryGetValue(key, out VariableValue existingValue)) - { - existingValue.Value = variableGroupEntry.Value; - existingValue.IsSecret |= variableGroupEntry.IsSecret; - referencedVariableGroups[key] = variableGroup; - } - else - { - var clonedValue = variableGroupEntry.Clone(); - clonedValue.Value = variableGroupEntry.Value; - context.Variables[key] = clonedValue; - referencedVariableGroups[key] = variableGroup; - } - } - } - else - { - foreach (var variableGroupEntry in variableGroup.Variables.Where(v => v.Value != null)) - { - // Variable groups which have secrets providers use delayed resolution depending on targets - // being invoked, etc. - if (context.Variables.TryGetValue(variableGroupEntry.Key, out VariableValue existingValue)) - { - existingValue.Value = variableGroupEntry.Value.Value; - existingValue.IsSecret |= variableGroupEntry.Value.IsSecret; - referencedVariableGroups[variableGroupEntry.Key] = variableGroup; - } - else - { - var clonedValue = variableGroupEntry.Value.Clone(); - clonedValue.Value = variableGroupEntry.Value.Value; - context.Variables[variableGroupEntry.Key] = clonedValue; - referencedVariableGroups[variableGroupEntry.Key] = variableGroup; - } - } - } - } - } - } - - // System variables get applied last as they always win - if (m_systemVariables?.Count > 0 || stage != null || phase != null) - { - // Start with system variables specified in the pipeline and then overlay scopes in order - var systemVariables = m_systemVariables == null - ? new VariablesDictionary() - : new VariablesDictionary(m_systemVariables); - - // Setup stage variables - if (stage != null) - { - systemVariables[WellKnownDistributedTaskVariables.StageDisplayName] = stage.Definition?.DisplayName ?? stage.Name; - systemVariables[WellKnownDistributedTaskVariables.StageId] = this.IdGenerator.GetStageInstanceId(stage.Name, stage.Attempt).ToString("D"); - systemVariables[WellKnownDistributedTaskVariables.StageName] = stage.Name; - systemVariables[WellKnownDistributedTaskVariables.StageAttempt] = stage.Attempt.ToString(); - } - - // Setup phase variables - if (phase != null) - { - systemVariables[WellKnownDistributedTaskVariables.PhaseDisplayName] = phase.Definition?.DisplayName ?? phase.Name; - systemVariables[WellKnownDistributedTaskVariables.PhaseId] = this.IdGenerator.GetPhaseInstanceId(stage?.Name, phase.Name, phase.Attempt).ToString("D"); - systemVariables[WellKnownDistributedTaskVariables.PhaseName] = phase.Name; - systemVariables[WellKnownDistributedTaskVariables.PhaseAttempt] = phase.Attempt.ToString(); - } - - foreach (var systemVariable in systemVariables) - { - referencedVariableGroups.Remove(systemVariable.Key); - context.Variables[systemVariable.Key] = systemVariable.Value?.Clone(); - - if (ExpressionValue.TryParse(systemVariable.Value?.Value, out var expression)) - { - expressionsToEvaluate[systemVariable.Key] = expression; - } - - context.SystemVariableNames.Add(systemVariable.Key); - } - } - - if (referencedVariableGroups.Count > 0 || expressionsToEvaluate.Count > 0) - { - context.Trace?.EnterProperty("Variables"); - } - - // Now populate the environment with variable group resources which are needed for execution - if (referencedVariableGroups.Count > 0) - { - foreach (var variableGroupData in referencedVariableGroups.GroupBy(x => x.Value, x => x.Key, s_comparer.Value)) - { - // If our variable group accesses an external service via a service endpoint we need to ensure - // that is also tracked as a required resource to execute this pipeline. - var groupReference = ToGroupReference(variableGroupData.Key, variableGroupData.ToList()); - if (groupReference?.SecretStore != null) - { - // Add the variable group reference to the list of required resources - context.ReferencedResources.VariableGroups.Add(groupReference); - - // Add this resource as authorized for use by this pipeline since the variable group requires - // it to function and the variable group was successfully authorized. - if (groupReference.SecretStore.Endpoint != null) - { - this.ResourceStore.Endpoints.Authorize(groupReference.SecretStore.Endpoint); - context.ReferencedResources.Endpoints.Add(groupReference.SecretStore.Endpoint); - } - - if (groupReference.SecretStore.Keys.Count == 0) - { - continue; - } - - // Make sure we don't unnecessarily retrieve values - var valueProvider = this.ResourceStore.VariableGroups.GetValueProvider(groupReference); - if (valueProvider == null) - { - continue; - } - - var variableGroup = this.ResourceStore.GetVariableGroup(groupReference); - ServiceEndpoint endpoint = null; - if (groupReference.SecretStore.Endpoint != null) - { - endpoint = this.ResourceStore.GetEndpoint(groupReference.SecretStore.Endpoint); - if (endpoint == null) - { - throw new DistributedTaskException(PipelineStrings.ServiceConnectionUsedInVariableGroupNotValid(groupReference.SecretStore.Endpoint, groupReference.Name)); - } - } - - if (!valueProvider.ShouldGetValues(context)) - { - // This will ensure that no value is provided by the server since we expect it to be set by a task - foreach (var key in groupReference.SecretStore.Keys) - { - context.Trace?.Info($"{key}: $[ variablegroups.{variableGroup.Name}.{key} ]"); - expressionsToEvaluate.Remove(key); - context.Variables[key] = new VariableValue(null, true); - } - } - else - { - var values = valueProvider.GetValues(variableGroup, endpoint, groupReference.SecretStore.Keys, includeSecrets); - if (values != null) - { - foreach (var value in values) - { - context.Trace?.Info($"{value.Key}: $[ variablegroups.{variableGroup.Name}.{value.Key} ]"); - expressionsToEvaluate.Remove(value.Key); - - if (includeSecrets || !value.Value.IsSecret) - { - context.Variables[value.Key] = value.Value; - } - else - { - context.Variables[value.Key].Value = null; - } - } - } - } - } - } - } - - // Now resolve the expressions discovered earlier - if (expressionsToEvaluate.Count > 0) - { - foreach (var variableExpression in expressionsToEvaluate) - { - context.Trace?.EnterProperty(variableExpression.Key); - var result = variableExpression.Value.GetValue(context); - context.Trace?.LeaveProperty(variableExpression.Key); - - if (context.Variables.TryGetValue(variableExpression.Key, out VariableValue existingValue)) - { - existingValue.Value = result.Value; - existingValue.IsSecret |= result.ContainsSecrets; - } - else - { - context.Variables[variableExpression.Key] = new VariableValue(result.Value, result.ContainsSecrets); - } - } - } - - // Filter out secret variables if we are not supposed to include them in the context - if (!includeSecrets) - { - foreach (var secretValue in context.Variables.Values.Where(x => x.IsSecret)) - { - secretValue.Value = null; - } - } - - if (referencedVariableGroups.Count > 0 || expressionsToEvaluate.Count > 0) - { - context.Trace?.LeaveProperty("Variables"); - } - } - - private static VariableGroupReference ToGroupReference( - VariableGroup group, - IList keys) - { - if (group == null || keys == null || keys.Count == 0) - { - return null; - } - - var storeConfiguration = ToSecretStoreConfiguration(group, keys); - return new VariableGroupReference - { - Id = group.Id, - Name = group.Name, - GroupType = group.Type, - SecretStore = storeConfiguration, - }; - } - - private static SecretStoreConfiguration ToSecretStoreConfiguration( - VariableGroup group, - IList keys) - { - if (keys.Count == 0) - { - return null; - } - - var keyVaultData = group.ProviderData as AzureKeyVaultVariableGroupProviderData; - var configuration = new SecretStoreConfiguration - { - StoreName = keyVaultData?.Vault ?? group.Name, - }; - - if (keyVaultData != null && keyVaultData.ServiceEndpointId != Guid.Empty) - { - configuration.Endpoint = new ServiceEndpointReference - { - Id = keyVaultData.ServiceEndpointId, - }; - } - - configuration.Keys.AddRange(keys); - return configuration; - } - - private sealed class VariableGroupComparer : IEqualityComparer - { - public Boolean Equals( - VariableGroup x, - VariableGroup y) - { - return x?.Id == y?.Id; - } - - public Int32 GetHashCode(VariableGroup obj) - { - return obj.Id.GetHashCode(); - } - } - - private IList m_userVariables; - private VariablesDictionary m_systemVariables; - private readonly IPipelineContext m_context; - private static readonly Lazy s_comparer = new Lazy(() => new VariableGroupComparer()); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineEnvironment.cs b/src/Sdk/DTPipelines/Pipelines/PipelineEnvironment.cs deleted file mode 100644 index a774b4c56..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineEnvironment.cs +++ /dev/null @@ -1,212 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PipelineEnvironment : IOrchestrationEnvironment - { - public PipelineEnvironment() - { - this.Version = 1; - } - - /// - /// Gets the resources available for use within the environment. - /// - public PipelineResources Resources - { - get - { - if (m_resources == null) - { - m_resources = new PipelineResources(); - } - return m_resources; - } - set - { - m_resources = value; - } - } - - /// - /// Gets the counter values, by prefix, which have been allocated for this environment. - /// - public IDictionary Counters - { - get - { - if (m_counters == null) - { - m_counters = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_counters; - } - } - - /// - /// Gets or sets the data value for any context needed to be passed down to the agent - /// - public IDictionary Data - { - get - { - if (m_data == null) - { - m_data = new Dictionary(); - } - return m_data; - } - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken EnvironmentVariables - { - get; - set; - } - - /// - /// Gets or sets the user variables collection. Variables are applied in order, meaning if variable names - /// appear more than once the last value will be represented in the environment. - /// - public IList UserVariables - { - get - { - if (m_userVariables == null) - { - m_userVariables = new List(); - } - return m_userVariables; - } - } - - /// - /// Gets the system variables collection. System variables are always applied last in order to enforce - /// precedence. - /// - public IDictionary SystemVariables - { - get - { - if (m_systemVariables == null) - { - m_systemVariables = new VariablesDictionary(); - } - return m_systemVariables; - } - } - - /// - /// Gets the explicit variables defined for use within the pipeline. - /// - [Obsolete("This property is obsolete. Use UserVariables and/or SystemVariables instead")] - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new VariablesDictionary(); - } - return m_variables; - } - } - - /// - /// Gets the execution options for this pipeline. - /// - public ExecutionOptions Options - { - get - { - return m_options; - } - } - - /// - /// Gets the version of the environment. - /// - [DefaultValue(1)] - [DataMember(Name = "Version", EmitDefaultValue = false)] - public Int32 Version - { - get; - set; - } - - OrchestrationProcessType IOrchestrationEnvironment.ProcessType - { - get - { - return m_processType; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_resources?.Count == 0) - { - m_resources = null; - } - - if (m_counters?.Count == 0) - { - m_counters = null; - } - - if (m_data?.Count == 0) - { - m_data = null; - } - - if (m_userVariables?.Count == 0) - { - m_userVariables = null; - } - - if (m_systemVariables?.Count == 0) - { - m_systemVariables = null; - } - - if (m_variables?.Count == 0) - { - m_variables = null; - } - } - - [DataMember(Name = "Counters", EmitDefaultValue = false)] - private Dictionary m_counters; - - [DataMember(Name = "Data", EmitDefaultValue = false)] - private Dictionary m_data; - - [DataMember(Name = "Options")] - private ExecutionOptions m_options = new ExecutionOptions(); - - [DataMember(Name = "ProcessType")] - private OrchestrationProcessType m_processType = OrchestrationProcessType.Pipeline; - - [DataMember(Name = "Resources", EmitDefaultValue = false)] - private PipelineResources m_resources; - - [DataMember(Name = "SystemVariables", EmitDefaultValue = false)] - private VariablesDictionary m_systemVariables; - - [DataMember(Name = "UserVariables", EmitDefaultValue = false)] - private IList m_userVariables; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private VariablesDictionary m_variables; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineException.cs b/src/Sdk/DTPipelines/Pipelines/PipelineException.cs deleted file mode 100644 index 1e54cdb84..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineException.cs +++ /dev/null @@ -1,297 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineException : VssServiceException - { - public PipelineException(String message) - : base(message) - { - } - - public PipelineException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - /// - /// Initializes an exception from serialized data - /// - /// object holding the serialized data - /// context info about the source or destination - protected PipelineException( - SerializationInfo info, - StreamingContext context) - : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class AmbiguousResourceSpecificationException : PipelineException - { - public AmbiguousResourceSpecificationException(String message) - : base(message) - { - } - - public AmbiguousResourceSpecificationException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected AmbiguousResourceSpecificationException( - SerializationInfo info, - StreamingContext context) : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class AmbiguousTaskSpecificationException : PipelineException - { - public AmbiguousTaskSpecificationException(String message) - : base(message) - { - } - - public AmbiguousTaskSpecificationException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected AmbiguousTaskSpecificationException( - SerializationInfo info, - StreamingContext context) : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class InvalidPipelineOperationException : PipelineException - { - public InvalidPipelineOperationException(String message) : base(message) - { - } - - public InvalidPipelineOperationException( - String message, - Exception innerException) : base(message, innerException) - { - } - - protected InvalidPipelineOperationException( - SerializationInfo info, - StreamingContext context) : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class ResourceNotFoundException : PipelineException - { - public ResourceNotFoundException(String message) - : base(message) - { - } - - public ResourceNotFoundException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected ResourceNotFoundException( - SerializationInfo info, - StreamingContext context) : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class ResourceNotAuthorizedException : PipelineException - { - public ResourceNotAuthorizedException(String message) - : base(message) - { - } - - public ResourceNotAuthorizedException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected ResourceNotAuthorizedException( - SerializationInfo info, - StreamingContext context) : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class ResourceValidationException : PipelineException - { - public ResourceValidationException(String message) - : base(message) - { - } - - public ResourceValidationException( - String message, - String propertyName) - : base(message) - { - this.PropertyName = propertyName; - } - - public ResourceValidationException( - String message, - String propertyName, - Exception innerException) - : base(message, innerException) - { - this.PropertyName = propertyName; - } - - public ResourceValidationException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected ResourceValidationException( - SerializationInfo info, - StreamingContext context) - : base(info, context) - { - } - - /// - /// Gets the property name of the resource which caused the error. - /// - public String PropertyName - { - get; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class StageNotFoundException : PipelineException - { - public StageNotFoundException(String message) - : base(message) - { - } - - public StageNotFoundException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - protected StageNotFoundException( - SerializationInfo info, - StreamingContext context) - : base(info, context) - { - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineValidationException : PipelineException - { - public PipelineValidationException() - : this(PipelineStrings.PipelineNotValid()) - { - } - - // Report first 2 error messages, due to space limit on printing this error message in UI - public PipelineValidationException(IEnumerable errors) - : this(PipelineStrings.PipelineNotValidWithErrors(string.Join(",", (errors ?? Enumerable.Empty()).Take(2).Select(e => e.Message)))) - { - m_errors = new List(errors ?? Enumerable.Empty()); - } - - public PipelineValidationException(String message) - : base(message) - { - } - - public PipelineValidationException( - String message, - Exception innerException) - : base(message, innerException) - { - } - - public IList Errors - { - get - { - if (m_errors == null) - { - m_errors = new List(); - } - return m_errors; - } - } - - /// - /// Initializes an exception from serialized data - /// - /// object holding the serialized data - /// context info about the source or destination - protected PipelineValidationException( - SerializationInfo info, - StreamingContext context) - : base(info, context) - { - } - - private List m_errors; - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public class MaxJobExpansionException : PipelineValidationException - { - public MaxJobExpansionException(IEnumerable errors) - : base(errors) - { - } - - public MaxJobExpansionException(String message) - : base(message) - { - } - - public MaxJobExpansionException( - String message, - Exception innerException) - : base(message, innerException) - { - } - protected MaxJobExpansionException( - SerializationInfo info, - StreamingContext context) - : base(info, context) - { - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineIdGenerator.cs b/src/Sdk/DTPipelines/Pipelines/PipelineIdGenerator.cs deleted file mode 100644 index 79d63183c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineIdGenerator.cs +++ /dev/null @@ -1,114 +0,0 @@ -using System; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineIdGenerator : IPipelineIdGenerator - { - public PipelineIdGenerator(Boolean preserveCase = false) - { - m_preserveCase = preserveCase; - } - - public Guid GetInstanceId(params String[] segments) - { - return PipelineUtilities.GetInstanceId(GetInstanceName(segments), m_preserveCase); - } - - public String GetInstanceName(params String[] segments) - { - return PipelineUtilities.GetInstanceName(segments); - } - - public String GetStageIdentifier(String stageName) - { - return PipelineUtilities.GetStageIdentifier(stageName); - } - - public Guid GetStageInstanceId( - String stageName, - Int32 attempt) - { - return PipelineUtilities.GetStageInstanceId(stageName, attempt, m_preserveCase); - } - - public String GetStageInstanceName( - String stageName, - Int32 attempt) - { - return PipelineUtilities.GetStageInstanceName(stageName, attempt); - } - - public String GetPhaseIdentifier( - String stageName, - String phaseName) - { - return PipelineUtilities.GetPhaseIdentifier(stageName, phaseName); - } - - public Guid GetPhaseInstanceId( - String stageName, - String phaseName, - Int32 attempt) - { - return PipelineUtilities.GetPhaseInstanceId(stageName, phaseName, attempt, m_preserveCase); - } - - public String GetPhaseInstanceName( - String stageName, - String phaseName, - Int32 attempt) - { - return PipelineUtilities.GetPhaseInstanceName(stageName, phaseName, attempt); - } - - public String GetJobIdentifier( - String stageName, - String phaseName, - String jobName) - { - return PipelineUtilities.GetJobIdentifier(stageName, phaseName, jobName); - } - - public Guid GetJobInstanceId( - String stageName, - String phaseName, - String jobName, - Int32 attempt) - { - return PipelineUtilities.GetJobInstanceId(stageName, phaseName, jobName, attempt, m_preserveCase); - } - - public String GetJobInstanceName( - String stageName, - String phaseName, - String jobName, - Int32 attempt) - { - return PipelineUtilities.GetJobInstanceName(stageName, phaseName, jobName, attempt); - } - - public String GetTaskInstanceName( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt, - String taskName) - { - return PipelineUtilities.GetTaskInstanceName(stageName, phaseName, jobName, jobAttempt, taskName); - } - - public Guid GetTaskInstanceId( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt, - String taskName) - { - return PipelineUtilities.GetTaskInstanceId(stageName, phaseName, jobName, jobAttempt, taskName, m_preserveCase); - } - - private Boolean m_preserveCase; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineProcess.cs b/src/Sdk/DTPipelines/Pipelines/PipelineProcess.cs deleted file mode 100644 index d423203f9..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineProcess.cs +++ /dev/null @@ -1,115 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineProcess : IOrchestrationProcess - { - [JsonConstructor] - public PipelineProcess() - { - } - - public PipelineProcess(IList phases) - { - var stage = CreateDefaultStage(); - stage.Phases.AddRange(phases ?? Enumerable.Empty()); - this.Stages.Add(stage); - } - - public PipelineProcess(IList stages) - { - if (stages?.Count > 0) - { - m_stages = new List(stages); - } - } - - public IList Stages - { - get - { - if (m_stages == null) - { - m_stages = new List(); - } - return m_stages; - } - } - - OrchestrationProcessType IOrchestrationProcess.ProcessType - { - get - { - return OrchestrationProcessType.Pipeline; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_stages?.Count == 1 && String.Equals(m_stages[0].Name, PipelineConstants.DefaultJobName, StringComparison.OrdinalIgnoreCase)) - { - m_phases = new List(m_stages[0].Phases); - m_stages = null; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (m_phases?.Count > 0) - { - var stage = CreateDefaultStage(); - stage.Phases.AddRange(m_phases); - - m_phases = null; - this.Stages.Add(stage); - } - } - - private static Stage CreateDefaultStage() - { - return new Stage { Name = PipelineConstants.DefaultJobName }; - } - - /// - /// return the node at the given path - /// - public IGraphNode GetNodeAtPath(IList path) - { - var length = path?.Count(); - var node = default(IGraphNode); - if (length > 0) - { - // find stage - node = this.Stages.FirstOrDefault(x => string.Equals(x.Name, path[0], StringComparison.OrdinalIgnoreCase) - || string.Equals(x.Name, PipelineConstants.DefaultJobName, StringComparison.OrdinalIgnoreCase)); - if (length > 1 && node != null) - { - // find phase - node = (node as Stage).Phases.FirstOrDefault(x => string.Equals(x.Name, path[1], StringComparison.OrdinalIgnoreCase) - || string.Equals(x.Name, PipelineConstants.DefaultJobName, StringComparison.OrdinalIgnoreCase)); - - // NOTE: jobs / phase configurations are not IGraphNodes yet - } - } - - return node; - } - - [DataMember(Name = "Stages", EmitDefaultValue = false)] - private List m_stages; - - [DataMember(Name = "Phases", EmitDefaultValue = false)] - private List m_phases; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineResource.cs b/src/Sdk/DTPipelines/Pipelines/PipelineResource.cs deleted file mode 100644 index cb3d34324..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineResource.cs +++ /dev/null @@ -1,57 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class PipelinePropertyNames - { - public static readonly String Artifacts = "artifacts"; - public static readonly String Branch = "branch"; - public static readonly String DefinitionId = "definitionId"; - public static readonly String PipelineId = "pipelineId"; - public static readonly String Project = "project"; - public static readonly String ProjectId = "projectId"; - public static readonly String Source = "source"; - public static readonly String Tags = "tags"; - public static readonly String Version = "version"; - } - - /// - /// Provides a data contract for a pipeline resource referenced by a pipeline. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineResource : Resource - { - public PipelineResource() - { - } - - protected PipelineResource(PipelineResource resourceToCopy) - : base(resourceToCopy) - { - } - - /// - /// Gets or sets the version of the build resource. - /// - public String Version - { - get - { - return this.Properties.Get(PipelinePropertyNames.Version); - } - set - { - this.Properties.Set(PipelinePropertyNames.Version, value); - } - } - - public PipelineResource Clone() - { - return new PipelineResource(this); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineResources.cs b/src/Sdk/DTPipelines/Pipelines/PipelineResources.cs deleted file mode 100644 index fa0d6f7e5..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineResources.cs +++ /dev/null @@ -1,570 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides collections of securable resources available for use within a pipeline. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PipelineResources - { - /// - /// Initializes a new PipelineResources instance with empty resource collections. - /// - public PipelineResources() - { - } - - private PipelineResources(PipelineResources resourcesToCopy) - { - if (resourcesToCopy.m_builds?.Count > 0) - { - m_builds = new HashSet(resourcesToCopy.m_builds.Select(x => x.Clone()), new ResourceComparer()); - } - - if (resourcesToCopy.m_containers?.Count > 0) - { - m_containers = new HashSet(resourcesToCopy.m_containers.Select(x => x.Clone()), new ResourceComparer()); - } - - if (resourcesToCopy.m_endpoints?.Count > 0) - { - m_endpoints = new HashSet(resourcesToCopy.m_endpoints.Select(x => x.Clone()), new EndpointComparer()); - } - - if (resourcesToCopy.m_environments?.Count > 0) - { - m_environments = new HashSet(resourcesToCopy.m_environments.Select(x => x.Clone()), new EnvironmentComparer()); - } - - if (resourcesToCopy.m_files?.Count > 0) - { - m_files = new HashSet(resourcesToCopy.m_files.Select(x => x.Clone()), new FileComparer()); - } - - if (resourcesToCopy.m_pipelines?.Count > 0) - { - m_pipelines = new HashSet(resourcesToCopy.m_pipelines.Select(x => x.Clone()), new ResourceComparer()); - } - - if (resourcesToCopy.m_queues?.Count > 0) - { - m_queues = new HashSet(resourcesToCopy.m_queues.Select(x => x.Clone()), new QueueComparer()); - } - - if (resourcesToCopy.m_pools?.Count > 0) - { - m_pools = new HashSet(resourcesToCopy.m_pools.Select(x => x.Clone()), new PoolComparer()); - } - - if (resourcesToCopy.m_repositories?.Count > 0) - { - m_repositories = new HashSet(resourcesToCopy.m_repositories.Select(x => x.Clone()), new ResourceComparer()); - } - - if (resourcesToCopy.m_variableGroups?.Count > 0) - { - m_variableGroups = new HashSet(resourcesToCopy.m_variableGroups.Select(x => x.Clone()), new VariableGroupComparer()); - } - } - - /// - /// Gets the total count of resources. - /// - public Int32 Count => (m_builds?.Count ?? 0) + - (m_containers?.Count ?? 0) + - (m_endpoints?.Count ?? 0) + - (m_environments?.Count ?? 0) + - (m_files?.Count ?? 0) + - (m_pipelines?.Count ?? 0) + - (m_queues?.Count ?? 0) + - (m_pools?.Count ?? 0) + - (m_repositories?.Count ?? 0) + - (m_variableGroups?.Count ?? 0); - - /// - /// List of all resources that need to be sent to PolicyService - /// - public IEnumerable GetSecurableResources() - { - foreach (var resourceCollection in new IEnumerable[] { - m_endpoints, - m_environments, - m_files, - m_queues, - m_pools, - m_variableGroups - }) - { - if (resourceCollection != null) - { - foreach (var r in resourceCollection) - { - if (r != null) - { - yield return r; - } - } - } - } - } - - /// - /// Gets the collection of build resources defined in the pipeline. - /// - public ISet Builds - { - get - { - if (m_builds == null) - { - m_builds = new HashSet(new ResourceComparer()); - } - return m_builds; - } - } - - /// - /// Gets the collection of container resources defined in the pipeline. - /// - public ISet Containers - { - get - { - if (m_containers == null) - { - m_containers = new HashSet(new ResourceComparer()); - } - return m_containers; - } - } - - /// - /// Gets the collection of endpoint references available in the resources of a pipeline. - /// - public ISet Endpoints - { - get - { - if (m_endpoints == null) - { - m_endpoints = new HashSet(new EndpointComparer()); - } - return m_endpoints; - } - } - - /// - /// Gets the collection of environments listed with deployment job in pipeline. - /// - public ISet Environments - { - get - { - if (m_environments == null) - { - m_environments = new HashSet(new EnvironmentComparer()); - } - return m_environments; - } - } - - /// - /// Gets the collection of secure file references available in the resources of a pipeline. - /// - public ISet Files - { - get - { - if (m_files == null) - { - m_files = new HashSet(new FileComparer()); - } - return m_files; - } - } - - /// - /// Gets the collection of pipeline resources defined in the pipeline. - /// - public ISet Pipelines - { - get - { - if (m_pipelines == null) - { - m_pipelines = new HashSet(new ResourceComparer()); - } - return m_pipelines; - } - } - - /// - /// Gets the collection of agent queue references available in the resources of a pipeline. - /// - public ISet Queues - { - get - { - if (m_queues == null) - { - m_queues = new HashSet(new QueueComparer()); - } - return m_queues; - } - } - - /// - /// Gets the collection of agent pool references available in the resources of a pipeline. - /// - public ISet Pools - { - get - { - if (m_pools == null) - { - m_pools = new HashSet(new PoolComparer()); - } - return m_pools; - } - } - - /// - /// Gets the collection of repository resources defined in the pipeline. - /// - public ISet Repositories - { - get - { - if (m_repositories == null) - { - m_repositories = new HashSet(new ResourceComparer()); - } - return m_repositories; - } - } - - /// - /// Gets the collection of variable group references available in the resources of a pipeline. - /// - public ISet VariableGroups - { - get - { - if (m_variableGroups == null) - { - m_variableGroups = new HashSet(new VariableGroupComparer()); - } - return m_variableGroups; - } - } - - public PipelineResources Clone() - { - return new PipelineResources(this); - } - - public void MergeWith(PipelineResources resources) - { - if (resources != null) - { - this.Builds.UnionWith(resources.Builds); - this.Containers.UnionWith(resources.Containers); - this.Endpoints.UnionWith(resources.Endpoints); - this.Environments.UnionWith(resources.Environments); - this.Files.UnionWith(resources.Files); - this.Pipelines.UnionWith(resources.Pipelines); - this.Queues.UnionWith(resources.Queues); - this.Pools.UnionWith(resources.Pools); - this.Repositories.UnionWith(resources.Repositories); - this.VariableGroups.UnionWith(resources.VariableGroups); - } - } - - internal void AddEndpointReference(String endpointId) - { - if (Guid.TryParse(endpointId, out Guid endpointIdValue)) - { - this.Endpoints.Add(new ServiceEndpointReference { Id = endpointIdValue }); - } - else - { - this.Endpoints.Add(new ServiceEndpointReference { Name = endpointId }); - } - } - - internal void AddEndpointReference(ServiceEndpointReference reference) - { - this.Endpoints.Add(reference); - } - - internal void AddSecureFileReference(String fileId) - { - if (Guid.TryParse(fileId, out Guid fileIdValue)) - { - this.Files.Add(new SecureFileReference { Id = fileIdValue }); - } - else - { - this.Files.Add(new SecureFileReference { Name = fileId }); - } - } - - internal void AddSecureFileReference(SecureFileReference reference) - { - this.Files.Add(reference); - } - - internal void AddAgentQueueReference(AgentQueueReference reference) - { - this.Queues.Add(reference); - } - - internal void AddAgentPoolReference(AgentPoolReference reference) - { - this.Pools.Add(reference); - } - - internal void AddVariableGroupReference(VariableGroupReference reference) - { - this.VariableGroups.Add(reference); - } - - internal void AddEnvironmentReference(EnvironmentReference reference) - { - this.Environments.Add(reference); - } - - internal void Clear() - { - m_builds?.Clear(); - m_containers?.Clear(); - m_endpoints?.Clear(); - m_files?.Clear(); - m_pipelines?.Clear(); - m_queues?.Clear(); - m_pools?.Clear(); - m_repositories?.Clear(); - m_variableGroups?.Clear(); - m_environments?.Clear(); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_builds?.Count == 0) - { - m_builds = null; - } - - if (m_containers?.Count == 0) - { - m_containers = null; - } - - if (m_endpoints?.Count == 0) - { - m_endpoints = null; - } - - if (m_files?.Count == 0) - { - m_files = null; - } - - if (m_pipelines?.Count == 0) - { - m_pipelines = null; - } - - if (m_queues?.Count == 0) - { - m_queues = null; - } - - if (m_pools?.Count == 0) - { - m_pools = null; - } - - if (m_repositories?.Count == 0) - { - m_repositories = null; - } - - if (m_variableGroups?.Count == 0) - { - m_variableGroups = null; - } - - if (m_environments?.Count == 0) - { - m_environments = null; - } - } - - [DataMember(Name = "Builds", EmitDefaultValue = false)] - private HashSet m_builds; - - [DataMember(Name = "Containers", EmitDefaultValue = false)] - private HashSet m_containers; - - [DataMember(Name = "Endpoints", EmitDefaultValue = false)] - private HashSet m_endpoints; - - [DataMember(Name = "Files", EmitDefaultValue = false)] - private HashSet m_files; - - [DataMember(Name = "Pipelines", EmitDefaultValue = false)] - private HashSet m_pipelines; - - [DataMember(Name = "Queues", EmitDefaultValue = false)] - private HashSet m_queues; - - [DataMember(Name = "Pools", EmitDefaultValue = false)] - private HashSet m_pools; - - [DataMember(Name = "Repositories", EmitDefaultValue = false)] - private HashSet m_repositories; - - [DataMember(Name = "VariableGroups", EmitDefaultValue = false)] - private HashSet m_variableGroups; - - [DataMember(Name = "Environments", EmitDefaultValue = false)] - private HashSet m_environments; - - internal abstract class ResourceReferenceComparer : IEqualityComparer where TResource : ResourceReference - { - protected ResourceReferenceComparer(IEqualityComparer idComparer) - { - m_idComparer = idComparer; - } - - public abstract TId GetId(TResource resource); - - public Boolean Equals( - TResource left, - TResource right) - { - if (left == null && right == null) - { - return true; - } - - if ((left != null && right == null) || (left == null && right != null)) - { - return false; - } - - var leftId = GetId(left); - var rightId = GetId(right); - if (m_idComparer.Equals(leftId, default(TId)) && m_idComparer.Equals(rightId, default(TId))) - { - return StringComparer.OrdinalIgnoreCase.Equals(left.Name, right.Name); - } - else - { - return m_idComparer.Equals(leftId, rightId); - } - } - - public Int32 GetHashCode(TResource obj) - { - var identifier = GetId(obj); - if (!m_idComparer.Equals(identifier, default(TId))) - { - return identifier.GetHashCode(); - } - else - { - return StringComparer.OrdinalIgnoreCase.GetHashCode(obj.Name); - } - } - - private readonly IEqualityComparer m_idComparer; - } - - internal class EndpointComparer : ResourceReferenceComparer - { - public EndpointComparer() - : base(EqualityComparer.Default) - { - } - - public override Guid GetId(ServiceEndpointReference resource) - { - return resource.Id; - } - } - - private class FileComparer : ResourceReferenceComparer - { - public FileComparer() - : base(EqualityComparer.Default) - { - } - - public override Guid GetId(SecureFileReference resource) - { - return resource.Id; - } - } - - private class QueueComparer : ResourceReferenceComparer - { - public QueueComparer() - : base(EqualityComparer.Default) - { - } - - public override Int32 GetId(AgentQueueReference resource) - { - return resource.Id; - } - } - - private class PoolComparer : ResourceReferenceComparer - { - public PoolComparer() - : base(EqualityComparer.Default) - { - } - - public override Int32 GetId(AgentPoolReference resource) - { - return resource.Id; - } - } - - private class VariableGroupComparer : ResourceReferenceComparer - { - public VariableGroupComparer() - : base(EqualityComparer.Default) - { - } - - public override Int32 GetId(VariableGroupReference resource) - { - return resource.Id; - } - } - - private class EnvironmentComparer : ResourceReferenceComparer - { - public EnvironmentComparer() - : base(EqualityComparer.Default) - { - } - - public override Int32 GetId(EnvironmentReference resource) - { - return resource.Id; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineState.cs b/src/Sdk/DTPipelines/Pipelines/PipelineState.cs deleted file mode 100644 index f280ef337..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineState.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public enum PipelineState - { - [EnumMember] - NotStarted, - - [EnumMember] - InProgress, - - [EnumMember] - Canceling, - - [EnumMember] - Completed, - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineStepsTemplate.cs b/src/Sdk/DTPipelines/Pipelines/PipelineStepsTemplate.cs deleted file mode 100644 index 04ce0759e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineStepsTemplate.cs +++ /dev/null @@ -1,55 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineStepsTemplate - { - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - public IList Errors - { - get - { - if (m_errors == null) - { - m_errors = new List(); - } - return m_errors; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_steps?.Count == 0) - { - m_steps = null; - } - - if (m_errors?.Count == 0) - { - m_errors = null; - } - } - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private List m_steps; - - [DataMember(Name = "Errors", EmitDefaultValue = false)] - private List m_errors; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineTemplate.cs b/src/Sdk/DTPipelines/Pipelines/PipelineTemplate.cs deleted file mode 100644 index b2ca72349..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineTemplate.cs +++ /dev/null @@ -1,147 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.ObjectTemplating.Tokens; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineTemplate - { - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public PipelineResources Resources - { - get - { - if (m_resources == null) - { - m_resources = new PipelineResources(); - } - return m_resources; - } - } - - [DataMember(EmitDefaultValue = false)] - public TemplateToken EnvironmentVariables - { - get; - set; - } - - public IList Variables - { - get - { - if (m_variables == null) - { - m_variables = new List(); - } - return m_variables; - } - } - - public IList Stages - { - get - { - if (m_stages == null) - { - m_stages = new List(); - } - return m_stages; - } - } - - public IList Triggers - { - get - { - if (m_triggers == null) - { - m_triggers = new List(); - } - return m_triggers; - } - } - - public IList Errors - { - get - { - if (m_errors == null) - { - m_errors = new List(); - } - return m_errors; - } - } - - [DataMember(EmitDefaultValue = false)] - public String InitializationLog - { - get; - set; - } - - public void CheckErrors() - { - if (m_errors?.Count > 0) - { - throw new PipelineValidationException(m_errors); - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_stages?.Count == 0) - { - m_stages = null; - } - - if (m_errors?.Count == 0) - { - m_errors = null; - } - - if (m_triggers?.Count == 0) - { - m_triggers = null; - } - - if (m_resources?.Count == 0) - { - m_resources = null; - } - - if (m_variables?.Count == 0) - { - m_variables = null; - } - } - - [DataMember(Name = "Stages", EmitDefaultValue = false)] - private List m_stages; - - [DataMember(Name = "Errors", EmitDefaultValue = false)] - private List m_errors; - - [DataMember(Name = "Triggers", EmitDefaultValue = false)] - private List m_triggers; - - [DataMember(Name = "Resources", EmitDefaultValue = false)] - private PipelineResources m_resources; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private List m_variables; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineTrigger.cs b/src/Sdk/DTPipelines/Pipelines/PipelineTrigger.cs deleted file mode 100644 index a4f900ae5..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineTrigger.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PipelineTrigger - { - public PipelineTrigger(PipelineTriggerType triggerType) - { - TriggerType = triggerType; - } - - /// - /// The type of the trigger. - /// - public PipelineTriggerType TriggerType - { - get; - private set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineTriggerType.cs b/src/Sdk/DTPipelines/Pipelines/PipelineTriggerType.cs deleted file mode 100644 index 4b88d9385..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineTriggerType.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public enum PipelineTriggerType - { - /// - /// A pipeline should be started for each changeset. - /// - ContinuousIntegration = 2, - - /// - /// A pipeline should be triggered when a GitHub pull request is created or updated. - /// - PullRequest = 64, - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineUtilities.cs b/src/Sdk/DTPipelines/Pipelines/PipelineUtilities.cs deleted file mode 100644 index ff9a7db7e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineUtilities.cs +++ /dev/null @@ -1,407 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Text; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class PipelineUtilities - { - public static Guid GetInstanceId( - String identifier, - Boolean preserveCase = false) - { - if (preserveCase) - { - return TimelineRecordIdGenerator.GetId(identifier); - } - else - { - return TimelineRecordIdGenerator.GetId(identifier?.ToLowerInvariant()); - } - } - - /// - /// This is the format for producing "instance names" - /// Instance names are defined to be node "identifiers" (the logical path to the node in the graph) - /// plus a single attempt number suffixed at the end. - /// Identifiers are constant accross different attempts of the same node. - /// Instance names are not, but will differ only in attempt number. - /// - public static String GetInstanceName(params String[] segments) - { - return String.Join(".", segments.Where(x => !String.IsNullOrEmpty(x)).Select(x => x.Trim('.'))); - } - - public static String GetName(String identifier) - { - ArgumentUtility.CheckStringForNullOrEmpty(identifier, nameof(identifier)); - - var separatorIndex = identifier.LastIndexOf('.'); - return separatorIndex >= 0 ? identifier.Substring(separatorIndex + 1) : identifier; - } - - public static Guid GetStageInstanceId( - StageInstance stage, - Boolean preserveCase = false) - { - return GetStageInstanceId(stage.Name, stage.Attempt, preserveCase); - } - - public static String GetStageIdentifier(StageInstance stage) - { - return GetStageIdentifier(stage.Name); - } - - public static String GetStageIdentifier(String stageName) - { - return GetStageInstanceName(stageName, 1); - } - - public static String GetStageInstanceName(StageInstance stage) - { - return GetStageInstanceName(stage.Name, stage.Attempt); - } - - public static Guid GetStageInstanceId( - String stageName, - Int32 stageAttempt, - Boolean preserveCase = false) - { - return GetInstanceId(GetStageInstanceName(stageName, stageAttempt, true), preserveCase); - } - - public static String GetStageInstanceName( - String stageName, - Int32 stageAttempt) - { - return GetStageInstanceName(stageName, stageAttempt, true); - } - - public static String GetStageInstanceName( - String stageName, - Int32 stageAttempt, - Boolean includeDefault) - { - if (!String.IsNullOrEmpty(stageName) && - (includeDefault || !stageName.Equals(PipelineConstants.DefaultJobName, StringComparison.OrdinalIgnoreCase))) - { - var instanceName = stageName; - if (stageAttempt > 1) - { - instanceName = $"{stageName}.{stageAttempt}"; - } - - return instanceName; - } - - return String.Empty; - } - - public static String GetPhaseIdentifier( - StageInstance stage, - PhaseInstance phase) - { - return GetPhaseIdentifier(stage?.Name, phase.Name); - } - - public static String GetPhaseIdentifier( - String stageName, - String phaseName) - { - return GetPhaseInstanceName(stageName, phaseName, 1); - } - - public static Guid GetPhaseInstanceId( - StageInstance stage, - PhaseInstance phase, - Boolean preserveCase = false) - { - return GetPhaseInstanceId(stage?.Name, phase.Name, phase.Attempt, preserveCase); - } - - public static Guid GetPhaseInstanceId( - String stageName, - String phaseName, - Int32 phaseAttempt, - Boolean preserveCase = false) - { - return GetInstanceId(GetPhaseInstanceName(stageName, phaseName, phaseAttempt), preserveCase); - } - - /// - /// The phase "instance name" is the phase identifier suffixed with the phase attempt. - /// - public static String GetPhaseInstanceName( - StageInstance stage, - PhaseInstance phase) - { - var sb = new StringBuilder(GetStageInstanceName(stage?.Name, stageAttempt: 1, false)); - if (sb.Length > 0) - { - sb.Append("."); - } - - sb.Append($"{phase.Name}"); - if (phase.Attempt > 1) - { - sb.Append($".{phase.Attempt}"); - } - - return sb.ToString(); - } - - public static String GetPhaseInstanceName( - String stageName, - String phaseName, - Int32 phaseAttempt) - { - var sb = new StringBuilder(GetStageInstanceName(stageName, stageAttempt: 1, false)); - if (sb.Length > 0) - { - sb.Append("."); - } - - sb.Append($"{phaseName}"); - if (phaseAttempt > 1) - { - sb.Append($".{phaseAttempt}"); - } - - return sb.ToString(); - } - - public static String GetJobIdentifier( - StageInstance stage, - PhaseInstance phase, - JobInstance job) - { - return GetJobIdentifier(stage?.Name, phase.Name, job.Name); - } - - public static String GetJobIdentifier( - String stageName, - String phaseName, - String jobName) - { - return GetJobInstanceName(stageName, phaseName, jobName, 1); - } - - public static Guid GetJobInstanceId( - StageInstance stage, - PhaseInstance phase, - JobInstance job, - Boolean preserveCase = false) - { - return GetJobInstanceId(stage?.Name, phase.Name, job.Name, job.Attempt, preserveCase); - } - - public static Guid GetJobInstanceId( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt, - Boolean preserveCase = false) - { - return GetInstanceId(GetJobInstanceName(stageName, phaseName, jobName, jobAttempt), preserveCase); - } - - public static String GetJobInstanceName( - StageInstance stage, - PhaseInstance phase, - JobInstance job) - { - return GetJobInstanceName(stage?.Name, phase.Name, job.Name, job.Attempt); - } - - public static String GetJobInstanceName( - String jobIdentifier, - Int32 jobAttempt) - { - var sb = new StringBuilder(jobIdentifier); - if (jobAttempt > 1) - { - sb.Append($".{jobAttempt}"); - } - - return sb.ToString(); - } - - public static String GetJobInstanceName(TimelineRecord job) - { - if (job.Attempt <= 1) - { - return job.Identifier; - } - else - { - return $"{job.Identifier}.{job.Attempt}"; - } - } - - public static String GetJobInstanceName( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt) - { - var sb = new StringBuilder(GetPhaseInstanceName(stageName, phaseName, 1)); - sb.Append($".{jobName}"); - if (jobAttempt > 1) - { - sb.Append($".{jobAttempt}"); - } - - return sb.ToString(); - } - - public static Guid GetTaskInstanceId( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt, - String taskName, - Boolean preserveCase = false) - { - return GetInstanceId(GetTaskInstanceName(stageName, phaseName, jobName, jobAttempt, taskName), preserveCase); - } - - public static String GetTaskInstanceName( - String stageName, - String phaseName, - String jobName, - Int32 jobAttempt, - String taskName) - { - return $"{GetJobInstanceName(stageName, phaseName, jobName, jobAttempt)}.{taskName}"; - } - - public static String GetTaskInstanceName( - TimelineRecord jobRecord, - TimelineRecord taskRecord) - { - return $"{GetJobInstanceName(jobRecord)}.{taskRecord.RefName}"; - } - - public static TaskResult MergeResult( - TaskResult result, - TaskResult childResult) - { - // If the final status is already failed then we can't get any worse - if (result == TaskResult.Canceled || result == TaskResult.Failed) - { - return result; - } - - switch (childResult) - { - case TaskResult.Canceled: - result = TaskResult.Canceled; - break; - - case TaskResult.Failed: - case TaskResult.Abandoned: - result = TaskResult.Failed; - break; - - case TaskResult.SucceededWithIssues: - if (result == TaskResult.Succeeded) - { - result = TaskResult.SucceededWithIssues; - } - break; - } - - return result; - } - - public static TaskResult AggregateResult(IEnumerable results) - { - var result = TaskResult.Succeeded; - if (results == default) - { - return result; - } - foreach (var r in results) - { - result = MergeResult(result, r); - } - return result; - } - - /// - /// returns the node path from pipeline root to instance node - /// - public static IList GetPathComponents(String instanceName) - { - var result = new List(); - if (!String.IsNullOrEmpty(instanceName)) - { - var tokens = instanceName.Split('.'); - var i = 0; - if (Guid.TryParse(tokens[i], out var _)) - { - // first parameter might be a guid - i = 1; - } - - // ignore attempt numbers -- these are not meaningful as path components - for (var end = tokens.Length; i < end; ++i) - { - var t = tokens[i]; - - // node names may only contain numbers, letters, and '_' - // node names must begin with at letter. - result.AddIf(!Int32.TryParse(t, out var _), t); - } - } - - return result; - } - - /// - /// A legal node name starts with a letter or '_', and is entirely - /// comprised of alphanumeric characters or the ['_', '-'] characters. - /// - public static Boolean IsLegalNodeName(string name) - { - if (string.IsNullOrWhiteSpace(name)) - { - return false; - } - - if (name.Length > PipelineConstants.MaxNodeNameLength) - { - return false; - } - - if (!char.IsLetter(name[0])) - { - return false; - } - - foreach (var c in name) - { - if (!char.IsLetterOrDigit(c) && c != '_') - { - return false; - } - } - - return true; - } - - public static String GetOrchestrationInstanceId( - Guid planId, - String nodeIdentifier) - { - return PipelineUtilities.GetInstanceName(planId.ToString("D"), nodeIdentifier); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineValidationError.cs b/src/Sdk/DTPipelines/Pipelines/PipelineValidationError.cs deleted file mode 100644 index 539913ebe..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineValidationError.cs +++ /dev/null @@ -1,60 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides information about an error which occurred during pipeline validation. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineValidationError - { - public PipelineValidationError() - { - } - - public PipelineValidationError(String message) - : this(null, message) - { - } - - public PipelineValidationError( - String code, - String message) - { - Code = code; - Message = message; - } - - [DataMember(EmitDefaultValue = false)] - public String Code - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Message - { - get; - set; - } - - public static IEnumerable Create(Exception exception) - { - for (int i = 0; i < 50; i++) - { - yield return new PipelineValidationError(exception.Message); - if (exception.InnerException == null) - { - break; - } - - exception = exception.InnerException; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PipelineValidationErrors.cs b/src/Sdk/DTPipelines/Pipelines/PipelineValidationErrors.cs deleted file mode 100644 index 6ffed4043..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PipelineValidationErrors.cs +++ /dev/null @@ -1,99 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides information about an error which occurred during pipeline validation. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PipelineValidationErrors : IEnumerable - { - public PipelineValidationErrors() - { - } - - public PipelineValidationErrors( - Int32 maxErrors, - Int32 maxMessageLength) - { - m_maxErrors = maxErrors; - m_maxMessageLength = maxMessageLength; - } - - public Int32 Count => m_errors.Count; - - public void Add(String message) - { - Add(new PipelineValidationError(message)); - } - - public void Add(Exception ex) - { - Add(null, ex); - } - - public void Add(String messagePrefix, Exception ex) - { - for (int i = 0; i < 50; i++) - { - String message = !String.IsNullOrEmpty(messagePrefix) ? $"{messagePrefix} {ex.Message}" : ex.Message; - Add(new PipelineValidationError(message)); - if (ex.InnerException == null) - { - break; - } - - ex = ex.InnerException; - } - } - - public void Add(IEnumerable errors) - { - foreach (var error in errors) - { - Add(error); - } - } - - public void Add(PipelineValidationError error) - { - // Check max errors - if (m_maxErrors <= 0 || - m_errors.Count < m_maxErrors) - { - // Check max message length - if (m_maxMessageLength > 0 && - error.Message?.Length > m_maxMessageLength) - { - error = new PipelineValidationError(error.Code, error.Message.Substring(0, m_maxMessageLength) + "[...]"); - } - - m_errors.Add(error); - } - } - - public void Clear() - { - m_errors.Clear(); - } - - public IEnumerator GetEnumerator() - { - return (m_errors as IEnumerable).GetEnumerator(); - } - - IEnumerator IEnumerable.GetEnumerator() - { - return (m_errors as IEnumerable).GetEnumerator(); - } - - private readonly List m_errors = new List(); - private readonly Int32 m_maxErrors; - private readonly Int32 m_maxMessageLength; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ProviderPhase.cs b/src/Sdk/DTPipelines/Pipelines/ProviderPhase.cs deleted file mode 100644 index 1cc116a51..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ProviderPhase.cs +++ /dev/null @@ -1,227 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ProviderPhase : PhaseNode - { - public ProviderPhase() - { - } - - private ProviderPhase(ProviderPhase phaseToCopy) - : base(phaseToCopy) - { - } - - /// - /// Gets the phase type. - /// - [DataMember(EmitDefaultValue = false)] - public override PhaseType Type => PhaseType.Provider; - - /// - /// Gets or sets the environment target for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public EnvironmentDeploymentTarget EnvironmentTarget - { - get; - set; - } - - /// - /// Gets or sets the provider for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public String Provider - { - get; - set; - } - - /// - /// Gets or sets the strategy for this phase. - /// - [DataMember(EmitDefaultValue = false)] - public Dictionary Strategy - { - get; - set; - } - - /// - /// Resolves external references and ensures the steps are compatible with the selected target. - /// - /// The validation context - public override void Validate( - PipelineBuildContext context, - ValidationResult result) - { - base.Validate(context, result); - - var provider = context.PhaseProviders.FirstOrDefault(x => String.Equals(x.Provider, this.Provider, StringComparison.OrdinalIgnoreCase)); - if (provider == null) - { - result.Errors.Add(new PipelineValidationError($"'{this.Provider}' phase '{this.Name}' is not supported.")); - } - else - { - var providerPhaseResult = provider.Validate(context, this); - if (providerPhaseResult != null) - { - foreach (var error in providerPhaseResult.Errors) - { - result.Errors.Add(error); - } - - result.ReferencedResources.MergeWith(providerPhaseResult.ReferencedResources); - - foreach (var endpointReference in providerPhaseResult.ReferencedResources.Endpoints) - { - var endpoint = context.ResourceStore.GetEndpoint(endpointReference); - if (endpoint == null) - { - result.UnauthorizedResources.AddEndpointReference(endpointReference); - } - } - - foreach (var fileReference in providerPhaseResult.ReferencedResources.Files) - { - var file = context.ResourceStore.GetFile(fileReference); - if (file == null) - { - result.UnauthorizedResources.AddSecureFileReference(fileReference); - } - } - - foreach (var queueReference in providerPhaseResult.ReferencedResources.Queues) - { - var queue = context.ResourceStore.GetQueue(queueReference); - if (queue == null) - { - result.UnauthorizedResources.AddAgentQueueReference(queueReference); - } - } - - foreach (var variableReference in providerPhaseResult.ReferencedResources.VariableGroups) - { - var variableGroup = context.ResourceStore.GetVariableGroup(variableReference); - if (variableGroup == null) - { - result.UnauthorizedResources.AddVariableGroupReference(variableReference); - } - } - } - } - - if (!(this.Target is AgentQueueTarget agentQueueTarget) || agentQueueTarget.IsLiteral()) - { - this.Target?.Validate(context, context.BuildOptions, result); - } - } - public JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - JobInstance jobInstance) - { - var jobContext = context.CreateJobContext(jobInstance); - jobContext.Job.Definition.Id = jobContext.GetInstanceId(); - - var options = new BuildOptions(); - var builder = new PipelineBuilder(context); - var result = builder.GetReferenceResources(jobInstance.Definition.Steps.OfType().ToList(), jobInstance.Definition.Target); - jobContext.ReferencedResources.MergeWith(result); - - // Update the execution context with the job-specific system variables - UpdateJobContextVariablesFromJob(jobContext, jobInstance.Definition); - - return jobContext; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class ProviderPhaseRequest - { - [DataMember(IsRequired = true)] - public Guid PlanId { get; set; } - - [DataMember(IsRequired = true)] - public String PlanType { get; set; } - - [DataMember(IsRequired = true)] - public Guid ServiceOwner { get; set; } - - [DataMember(IsRequired = true)] - public String PhaseOrchestrationId { get; set; } - - [DataMember(EmitDefaultValue = false)] - public ProviderPhase ProviderPhase { get; set; } - - [DataMember(EmitDefaultValue = false)] - public ProjectReference Project { get; set; } - - [DataMember(EmitDefaultValue = false)] - public TaskOrchestrationOwner Pipeline { get; set; } - - [DataMember(EmitDefaultValue = false)] - public TaskOrchestrationOwner Run { get; set; } - - [DataMember(EmitDefaultValue = false)] - public PipelineGraphNodeReference Stage { get; set; } - - [DataMember(EmitDefaultValue = false)] - public PipelineGraphNodeReference Phase { get; set; } - - [DataMember(EmitDefaultValue = false)] - public IDictionary Variables { get; set; } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class PipelineGraphNodeReference - { - public PipelineGraphNodeReference() - { - } - - public PipelineGraphNodeReference(String id, String name, Int32 attempt = 0) - { - this.Id = id; - this.Name = name; - this.Attempt = attempt; - } - - public PipelineGraphNodeReference(Guid id, String name, Int32 attempt = 0) - { - this.Id = id.ToString("D"); - this.Name = name; - this.Attempt = attempt; - } - - public PipelineGraphNodeReference(Int32 id, String name, Int32 attempt = 0) - { - this.Id = id.ToString(); - this.Name = name; - this.Attempt = attempt; - } - - [DataMember(IsRequired = true)] - public String Id { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - - [DataMember(EmitDefaultValue = false)] - public Int32 Attempt { get; set; } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/PullRequestTrigger.cs b/src/Sdk/DTPipelines/Pipelines/PullRequestTrigger.cs deleted file mode 100644 index 91af1aba8..000000000 --- a/src/Sdk/DTPipelines/Pipelines/PullRequestTrigger.cs +++ /dev/null @@ -1,83 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class PullRequestTrigger : PipelineTrigger - { - public PullRequestTrigger() - : base(PipelineTriggerType.PullRequest) - { - Enabled = true; - AutoCancel = true; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean Enabled - { - get; - set; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean AutoCancel - { - get; - set; - } - - /// - /// A list of filters that describe which branches will trigger pipelines. - /// - public IList BranchFilters - { - get - { - if (m_branchFilters == null) - { - m_branchFilters = new List(); - } - return m_branchFilters; - } - } - - /// - /// A list of filters that describe which paths will trigger pipelines. - /// - public IList PathFilters - { - get - { - if (m_pathFilters == null) - { - m_pathFilters = new List(); - } - return m_pathFilters; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_branchFilters?.Count == 0) - { - m_branchFilters = null; - } - - if (m_pathFilters?.Count == 0) - { - m_pathFilters = null; - } - } - - [DataMember(Name = "BranchFilters", EmitDefaultValue = false)] - private List m_branchFilters; - - [DataMember(Name = "PathFilters", EmitDefaultValue = false)] - private List m_pathFilters; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/RepositoryResource.cs b/src/Sdk/DTPipelines/Pipelines/RepositoryResource.cs index 5a70cfa80..67e861f88 100644 --- a/src/Sdk/DTPipelines/Pipelines/RepositoryResource.cs +++ b/src/Sdk/DTPipelines/Pipelines/RepositoryResource.cs @@ -9,70 +9,9 @@ namespace GitHub.DistributedTask.Pipelines public static class RepositoryPropertyNames { public static readonly String Id = "id"; - public static readonly String Mappings = "mappings"; - public static readonly String Name = "name"; - public static readonly String Ref = "ref"; public static readonly String Type = "type"; public static readonly String Url = "url"; public static readonly String Version = "version"; - public static readonly String VersionInfo = "versionInfo"; - public static readonly String VersionSpec = "versionSpec"; - public static readonly String Shelveset = "shelveset"; - public static readonly String Project = "project"; - public static readonly String Path = "path"; - public static readonly String CheckoutOptions = "checkoutOptions"; - public static readonly String DefaultBranch = "defaultBranch"; - public static readonly String ExternalId = "externalId"; - public static readonly String IsJustInTimeRepository = "isJustInTimeRepository"; - } - - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class VersionInfo - { - [DataMember(EmitDefaultValue = false)] - public String Author { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Message { get; set; } - } - - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class CheckoutOptions - { - [JsonConstructor] - public CheckoutOptions() - { } - - private CheckoutOptions(CheckoutOptions optionsToCopy) - { - this.Clean = optionsToCopy.Clean; - this.FetchDepth = optionsToCopy.FetchDepth; - this.Lfs = optionsToCopy.Lfs; - this.Submodules = optionsToCopy.Submodules; - this.PersistCredentials = optionsToCopy.PersistCredentials; - } - - [DataMember(EmitDefaultValue = false)] - public String Clean{ get; set; } - - [DataMember(EmitDefaultValue = false)] - public String FetchDepth{ get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Lfs { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String Submodules { get; set; } - - [DataMember(EmitDefaultValue = false)] - public String PersistCredentials { get; set; } - - public CheckoutOptions Clone() - { - return new CheckoutOptions(this); - } } /// diff --git a/src/Sdk/DTPipelines/Pipelines/RepositoryTypes.cs b/src/Sdk/DTPipelines/Pipelines/RepositoryTypes.cs index e0f46ea5c..8b224f7a9 100644 --- a/src/Sdk/DTPipelines/Pipelines/RepositoryTypes.cs +++ b/src/Sdk/DTPipelines/Pipelines/RepositoryTypes.cs @@ -4,12 +4,6 @@ namespace GitHub.DistributedTask.Pipelines { public static class RepositoryTypes { - public static readonly String Bitbucket = nameof(Bitbucket); - public static readonly String ExternalGit = nameof(ExternalGit); - public static readonly String Git = nameof(Git); public static readonly String GitHub = nameof(GitHub); - public static readonly String GitHubEnterprise = nameof(GitHubEnterprise); - public static readonly String Tfvc = nameof(Tfvc); - public static readonly String Svn = nameof(Svn); } } diff --git a/src/Sdk/DTPipelines/Pipelines/ResourceComparer.cs b/src/Sdk/DTPipelines/Pipelines/ResourceComparer.cs deleted file mode 100644 index 76aa7eabe..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ResourceComparer.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.Pipelines -{ - internal sealed class ResourceComparer : IEqualityComparer - { - public Boolean Equals( - Resource x, - Resource y) - { - return String.Equals(x?.Alias, y?.Alias, StringComparison.OrdinalIgnoreCase); - } - - public Int32 GetHashCode(Resource obj) - { - return obj?.Alias?.GetHashCode() ?? 0; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ResourceStore.cs b/src/Sdk/DTPipelines/Pipelines/ResourceStore.cs deleted file mode 100644 index c5ce4ba7c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ResourceStore.cs +++ /dev/null @@ -1,666 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Orchestration.Server.Artifacts; -using GitHub.DistributedTask.Pipelines.Artifacts; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a default implementation of a resource store. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ResourceStore : IResourceStore - { - /// - /// Initializes a new ResourceStore instance with no resources. - /// - public ResourceStore() - : this(endpoints: null) - { - } - - /// - /// Initializes a new ResourceStore instance with the specified resources. If aliases are provided, - /// an alias overrides lookup by name for the specified resource. - /// - /// The collection of endpoints available in the store - /// The collection of secure files available in the store - /// The collection of agent queues available in the store - /// The collection of variable groups available in the store - public ResourceStore( - IList endpoints = null, - IList files = null, - IList queues = null, - IList variableGroups = null, - IList builds = null, - IList containers = null, - IList repositories = null, - IList pipelines = null, - IList pools = null) - : this(new ServiceEndpointStore(endpoints), new SecureFileStore(files), new AgentQueueStore(queues), new VariableGroupStore(variableGroups), new BuildResourceStore(builds), new ContainerResourceStore(containers), new RepositoryResourceStore(repositories), new PipelineResourceStore(pipelines), new AgentPoolStore(pools), new EnvironmentStore(null)) - { - } - - /// - /// Initializes a new ResourceStore instance with the specified resources and endpoint store. If - /// aliases are provided, an alias overrides lookup by name for the specified resource. - /// - /// The store for retrieving referenced service endpoints - /// The store for retrieving referenced secure files - /// The store for retrieving referenced agent queues - /// The store for retrieving reference variable groups - public ResourceStore( - IServiceEndpointStore endpointStore = null, - ISecureFileStore fileStore = null, - IAgentQueueStore queueStore = null, - IVariableGroupStore variableGroupStore = null, - IBuildStore buildStore = null, - IContainerStore containerStore = null, - IRepositoryStore repositoryStore = null, - IPipelineStore pipelineStore = null, - IAgentPoolStore poolStore = null, - IEnvironmentStore environmentStore = null) - { - this.Builds = buildStore ?? new BuildResourceStore(null); - this.Containers = containerStore ?? new ContainerResourceStore(null); - this.Endpoints = endpointStore ?? new ServiceEndpointStore(null); - this.Files = fileStore ?? new SecureFileStore(null); - this.Pipelines = pipelineStore ?? new PipelineResourceStore(null); - this.Queues = queueStore ?? new AgentQueueStore(null); - this.Pools = poolStore ?? new AgentPoolStore(null); - this.Repositories = repositoryStore ?? new RepositoryResourceStore(null); - this.VariableGroups = variableGroupStore ?? new VariableGroupStore(null); - this.Environments = environmentStore ?? new EnvironmentStore(null); - } - - /// - /// Gets the store used for retrieving build resources. - /// - public IBuildStore Builds - { - get; - } - - /// - /// Gets the store used for retrieving container resources. - /// - public IContainerStore Containers - { - get; - } - - /// - /// Gets the store used for retrieving service endpoints. - /// - public IServiceEndpointStore Endpoints - { - get; - } - - /// - /// Gets the store used for retrieving environment. - /// - public IEnvironmentStore Environments - { - get; - } - - /// - /// Gets the store used for retrieving secure files. - /// - public ISecureFileStore Files - { - get; - } - - /// - /// Get the store used for retrieving pipelines. - /// - public IPipelineStore Pipelines - { - get; - } - - /// - /// Gets the store used for retrieving agent queues. - /// - public IAgentQueueStore Queues - { - get; - } - - /// - /// Gets the store used for retrieving agent pools. - /// - public IAgentPoolStore Pools - { - get; - } - - /// - /// Gets the store used for retrieving repository resources. - /// - public IRepositoryStore Repositories - { - get; - } - - /// - /// Gets the store used for retrieving variable groups. - /// - public IVariableGroupStore VariableGroups - { - get; - } - - /// - /// Gets all resources currently in the resource store. - /// - /// - public PipelineResources GetAuthorizedResources() - { - var resources = new PipelineResources(); - resources.Builds.AddRange(this.Builds.GetAll()); - resources.Containers.AddRange(this.Containers.GetAll()); - resources.Endpoints.AddRange(this.Endpoints.GetAuthorizedReferences()); - resources.Files.AddRange(this.Files.GetAuthorizedReferences()); - resources.Pipelines.AddRange(this.Pipelines.GetAll()); - resources.Queues.AddRange(this.Queues.GetAuthorizedReferences()); - resources.Pools.AddRange(this.Pools.GetAuthorizedReferences()); - resources.Repositories.AddRange(this.Repositories.GetAll()); - resources.VariableGroups.AddRange(this.VariableGroups.GetAuthorizedReferences()); - resources.Environments.AddRange(this.Environments.GetReferences()); - return resources; - } - - /// - /// Gets the steps, if any, which should be inserted into the job based on the resources configured. - /// - /// The execution context - /// The current set of steps for the job - /// A list of steps which should be prepended to the job - public IList GetPreSteps( - IPipelineContext context, - IReadOnlyList steps) - { - var allSteps = new List(); - if (context.EnvironmentVersion > 1 && context is PipelineExecutionContext) - { - // Variable group steps are always set first in case the other steps depend on the values - allSteps.AddRangeIfRangeNotNull(this.VariableGroups.GetPreSteps(context, steps)); - - // Now just do the remaining resources in alphabetical order - allSteps.AddRangeIfRangeNotNull(this.Builds.GetPreSteps(context, steps)); - allSteps.AddRangeIfRangeNotNull(this.Repositories.GetPreSteps(context, steps)); - allSteps.AddRangeIfRangeNotNull(this.Pipelines.GetPreSteps(context, steps)); - } - - return allSteps; - } - - /// - /// Get steps that run after the checkout task. - /// - /// The execution context - /// - /// - public Dictionary> GetPostTaskSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new Dictionary>(); - } - - /// - /// Get steps that are run after all other steps. - /// - /// The execution context - /// - public IList GetPostSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - public ServiceEndpoint GetEndpoint(Guid endpointId) - { - return this.Endpoints.Get(new ServiceEndpointReference { Id = endpointId }); - } - - public ServiceEndpoint GetEndpoint(String endpointId) - { - ServiceEndpoint endpoint = null; - if (Guid.TryParse(endpointId, out Guid endpointIdValue)) - { - endpoint = GetEndpoint(endpointIdValue); - } - - if (endpoint == null) - { - endpoint = this.Endpoints.Get(new ServiceEndpointReference { Name = endpointId }); - } - - return endpoint; - } - - public SecureFile GetFile(Guid fileId) - { - return this.Files.Get(new SecureFileReference { Id = fileId }); - } - - public SecureFile GetFile(String fileId) - { - SecureFile file = null; - if (Guid.TryParse(fileId, out Guid fileIdValue)) - { - file = GetFile(fileIdValue); - } - - if (file == null) - { - file = this.Files.Get(new SecureFileReference { Name = fileId }); - } - - return file; - } - - public TaskAgentQueue GetQueue(Int32 queueId) - { - return this.Queues.Get(new AgentQueueReference { Id = queueId }); - } - - public TaskAgentQueue GetQueue(String queueId) - { - TaskAgentQueue queue = null; - if (Int32.TryParse(queueId, out Int32 queueIdValue)) - { - queue = GetQueue(queueIdValue); - } - - if (queue == null) - { - queue = this.Queues.Get(new AgentQueueReference { Name = queueId }); - } - - return queue; - } - - public TaskAgentPool GetPool(Int32 poolId) - { - return this.Pools.Get(new AgentPoolReference { Id = poolId }); - } - - public TaskAgentPool GetPool(String poolName) - { - return this.Pools.Get(new AgentPoolReference { Name = poolName }); - } - - public VariableGroup GetVariableGroup(Int32 groupId) - { - return this.VariableGroups.Get(new VariableGroupReference { Id = groupId }); - } - - public VariableGroup GetVariableGroup(String groupId) - { - VariableGroup variableGroup = null; - if (Int32.TryParse(groupId, out Int32 groupIdValue)) - { - variableGroup = GetVariableGroup(groupIdValue); - } - - if (variableGroup == null) - { - variableGroup = this.VariableGroups.Get(new VariableGroupReference { Name = groupId }); - } - - return variableGroup; - } - - public Boolean ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - if (context.EnvironmentVersion > 1 && context is PipelineExecutionContext) - { - return this.Pipelines.ResolveStep(context, step, out resolvedSteps); - } - - return false; - } - } - - public abstract class InMemoryResourceStore where T : Resource - { - protected InMemoryResourceStore(IEnumerable resources) - { - m_resources = resources?.ToDictionary(x => x.Alias, x => x, StringComparer.OrdinalIgnoreCase) ?? new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - public Int32 Count => m_resources.Count; - - public void Add(T resource) - { - m_resources.Add(resource.Alias, resource); - } - - public void Add(IEnumerable resources) - { - foreach (var resource in resources) - { - m_resources.Add(resource.Alias, resource); - } - } - - public T Get(String alias) - { - if (m_resources.TryGetValue(alias, out T resource)) - { - return resource; - } - - return null; - } - - public IEnumerable GetAll() - { - return m_resources.Values.ToList(); - } - - private Dictionary m_resources; - } - - public class BuildResourceStore : InMemoryResourceStore, IBuildStore - { - public BuildResourceStore( - IEnumerable builds, - IArtifactResolver resolver = null) - : base(builds) - { - this.Resolver = resolver; - } - - public BuildResourceStore(params BuildResource[] builds) - : base(builds) - { - } - - public IArtifactResolver Resolver { get; } - - public IList GetPreSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return null; - } - - public Dictionary> GetPostTaskSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new Dictionary>(); - } - - public IList GetPostSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - public Boolean ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - return false; - } - } - - public class ContainerResourceStore : InMemoryResourceStore, IContainerStore - { - public ContainerResourceStore(IEnumerable containers) - : base(containers) - { - } - - public ContainerResourceStore(params ContainerResource[] containers) - : base(containers) - { - } - - public bool ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - return false; - } - } - - public class PipelineResourceStore : InMemoryResourceStore, IPipelineStore - { - public PipelineResourceStore( - IEnumerable pipelines, - IArtifactResolver artifactResolver = null, - Boolean isEnabled = false, - Boolean useSystemStepsDecorator = false) - : base(pipelines) - { - this.m_artifactResolver = artifactResolver; - this.m_isEnabled = isEnabled; - this.m_useSystemStepsDecorator = useSystemStepsDecorator; - } - - public IList GetPreSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - public Dictionary> GetPostTaskSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new Dictionary>(); - } - - public IList GetPostSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - public Boolean ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - - if (step.IsDownloadTask()) - { - if (!m_isEnabled) - { - // The pre step decorator can't check the FF state. It always adds a download step for a current pipeline. - // To make sure we aren't failing all the existing pipelines, if the DownloadStep FF is not enabled we will return as resolved with empty resolved steps. - return true; - } - - return m_artifactResolver?.ResolveStep(context, step, out resolvedSteps) ?? false; - } - - return false; - } - - private IArtifactResolver m_artifactResolver; - private Boolean m_isEnabled; - private Boolean m_useSystemStepsDecorator; - } - - public class RepositoryResourceStore : InMemoryResourceStore, IRepositoryStore - { - public RepositoryResourceStore(IEnumerable repositories) - : this(repositories, false, false) - { - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public RepositoryResourceStore( - IEnumerable repositories, - Boolean useSystemStepsDecorator, - Boolean includeCheckoutOptions) - : base(repositories) - { - m_useSystemStepsDecorator = useSystemStepsDecorator; - m_includeCheckoutOptions = includeCheckoutOptions; - } - - public IList GetPreSteps( - IPipelineContext context, - IReadOnlyList steps) - { - // If the environment version is 1 we should not inject - if (context.EnvironmentVersion < 2) - { - return null; - } - - var executionContext = context as JobExecutionContext; - if (context is JobExecutionContext jobContext && (jobContext.Phase.Definition as Phase)?.Target.Type != PhaseTargetType.Queue) - { - // only inject checkout step for agent phase - return null; - } - - // Check feature flag DistributedTask.IncludeCheckoutOptions. - // Controls whether the checkout options are merged into the task inputs, - // or whether the checkout task does. - if (!m_includeCheckoutOptions) - { - // Populate default checkout option from repository into task's inputs - foreach (var checkoutTask in steps.Where(x => x.IsCheckoutTask()).OfType()) - { - var repository = Get(checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Repository]); - if (repository != null && repository.Properties.TryGetValue(RepositoryPropertyNames.CheckoutOptions, out CheckoutOptions checkoutOptions)) - { - MergeCheckoutOptions(checkoutOptions, checkoutTask); - } - } - } - - // Check feature flag DistributedTask.YamlSystemStepsDecorator. - // Controls whether to load the checkout step from a YAML template. - if (m_useSystemStepsDecorator) - { - return null; - } - - var selfRepo = Get(PipelineConstants.SelfAlias); - if (selfRepo == null) - { - // self repository doesn't existing, no needs to inject checkout task. - // self repo is for yaml only, designer build should always provide checkout task - return null; - } - else - { - // If any steps contains checkout task, we will not inject checkout task - if (steps.Any(x => x.IsCheckoutTask())) - { - return null; - } - else - { - //Inject checkout:self task - var checkoutTask = new TaskStep() - { - Enabled = true, - DisplayName = PipelineConstants.CheckoutTask.FriendlyName, - Reference = new TaskStepDefinitionReference() - { - Id = PipelineConstants.CheckoutTask.Id, - Version = PipelineConstants.CheckoutTask.Version, - Name = PipelineConstants.CheckoutTask.Name - } - }; - - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Repository] = selfRepo.Alias; - if (selfRepo.Properties.TryGetValue(RepositoryPropertyNames.CheckoutOptions, out CheckoutOptions checkoutOptions)) - { - MergeCheckoutOptions(checkoutOptions, checkoutTask); - } - - return new[] { checkoutTask }; - } - } - } - - public Dictionary> GetPostTaskSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new Dictionary>(); - } - - public IList GetPostSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - private void MergeCheckoutOptions( - CheckoutOptions checkoutOptions, - TaskStep checkoutTask) - { - if (!checkoutTask.Inputs.ContainsKey(PipelineConstants.CheckoutTaskInputs.Clean) && !String.IsNullOrEmpty(checkoutOptions.Clean)) - { - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Clean] = checkoutOptions.Clean; - } - - if (!checkoutTask.Inputs.ContainsKey(PipelineConstants.CheckoutTaskInputs.FetchDepth) && !String.IsNullOrEmpty(checkoutOptions.FetchDepth)) - { - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.FetchDepth] = checkoutOptions.FetchDepth; - } - - if (!checkoutTask.Inputs.ContainsKey(PipelineConstants.CheckoutTaskInputs.Lfs) && !String.IsNullOrEmpty(checkoutOptions.Lfs)) - { - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Lfs] = checkoutOptions.Lfs; - } - - if (!checkoutTask.Inputs.ContainsKey(PipelineConstants.CheckoutTaskInputs.PersistCredentials) && !String.IsNullOrEmpty(checkoutOptions.PersistCredentials)) - { - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.PersistCredentials] = checkoutOptions.PersistCredentials; - } - - if (!checkoutTask.Inputs.ContainsKey(PipelineConstants.CheckoutTaskInputs.Submodules) && !String.IsNullOrEmpty(checkoutOptions.Submodules)) - { - checkoutTask.Inputs[PipelineConstants.CheckoutTaskInputs.Submodules] = checkoutOptions.Submodules; - } - } - - public Boolean ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - return false; - } - - private Boolean m_useSystemStepsDecorator; - private Boolean m_includeCheckoutOptions; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/AgentJobStartedData.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/AgentJobStartedData.cs deleted file mode 100644 index a8a68681d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/AgentJobStartedData.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [DataContract] - public sealed class AgentJobStartedData - { - [DataMember(EmitDefaultValue = false)] - public TaskAgentReference ReservedAgent - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/GraphExecutionContext.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/GraphExecutionContext.cs deleted file mode 100644 index 31c9b4a2f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/GraphExecutionContext.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class GraphExecutionContext : PipelineExecutionContext where TInstance : IGraphNodeInstance - { - private protected GraphExecutionContext(GraphExecutionContext context) - : base(context) - { - this.Node = context.Node; - } - - private protected GraphExecutionContext( - TInstance node, - PipelineState state, - DictionaryContextData data, - ICounterStore counterStore, - IPackageStore packageStore, - IResourceStore resourceStore, - ITaskStore taskStore, - IList stepProviders, - IPipelineIdGenerator idGenerator = null, - IPipelineTraceWriter trace = null, - EvaluationOptions expressionOptions = null, - ExecutionOptions executionOptions = null) - : base(data, counterStore, packageStore, resourceStore, taskStore, stepProviders, state, idGenerator, trace, expressionOptions, executionOptions) - { - ArgumentUtility.CheckForNull(node, nameof(node)); - - this.Node = node; - } - - /// - /// Gets the target node for this execution context. - /// - protected TInstance Node - { - get; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/GraphNodeInstance.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/GraphNodeInstance.cs deleted file mode 100644 index c2e65be20..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/GraphNodeInstance.cs +++ /dev/null @@ -1,144 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [DataContract] - public abstract class GraphNodeInstance : IGraphNodeInstance where TNode : IGraphNode - { - private protected GraphNodeInstance() - { - this.Attempt = 1; - } - - private protected GraphNodeInstance( - String name, - Int32 attempt, - TNode definition, - TaskResult result) - { - this.Name = name; - this.Attempt = attempt; - this.Definition = definition; - this.State = PipelineState.NotStarted; - this.Result = result; - } - - /// - /// Gets or sets the identifier of the node. - /// - [DataMember(EmitDefaultValue = false)] - public String Identifier - { - get; - set; - } - - /// - /// Gets or sets the name of the node. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32 Attempt - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime? StartTime - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime? FinishTime - { - get; - set; - } - - /// - /// Gets the collection of output variables emitted by the instance. - /// - public IDictionary Outputs - { - get - { - if (m_outputs == null) - { - m_outputs = new VariablesDictionary(); - } - return m_outputs; - } - } - - [DataMember(EmitDefaultValue = false)] - public PipelineState State - { - get; - set; - } - - /// - /// Gets or sets the result of the instance. - /// - [DataMember(EmitDefaultValue = false)] - public TaskResult? Result - { - get; - set; - } - - /// - /// Gets the structure defined in the pipeline definition. - /// - public TNode Definition - { - get; - internal set; - } - - /// - /// Gets the timeline record for this instance. - /// - internal TimelineRecord Record - { - get; - } - - public Boolean SecretsAccessed - { - get - { - return m_outputs?.SecretsAccessed.Count > 0; - } - } - - public void ResetSecretsAccessed() - { - m_outputs?.SecretsAccessed.Clear(); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_outputs?.Count == 0) - { - m_outputs = null; - } - } - - [DataMember(Name = "Outputs", EmitDefaultValue = false)] - private VariablesDictionary m_outputs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/JobAttempt.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/JobAttempt.cs deleted file mode 100644 index bda09e88a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/JobAttempt.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class JobAttempt - { - public JobInstance Job - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/JobExecutionContext.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/JobExecutionContext.cs deleted file mode 100644 index d29c3cb51..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/JobExecutionContext.cs +++ /dev/null @@ -1,113 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Pipelines.ContextData; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class JobExecutionContext : PipelineExecutionContext - { - public JobExecutionContext( - PipelineState state, - IPipelineIdGenerator idGenerator = null) - : base(null, null, null, null, null, null, state, idGenerator) - { - } - - public JobExecutionContext( - PhaseExecutionContext context, - JobInstance job, - IDictionary variables, - Int32 positionInPhase = default, - Int32 totalJobsInPhase = default, - IDictionary data = default) - : base(context) - { - this.Stage = context.Stage; - this.Phase = context.Phase; - this.Job = job; - - // Make sure the identifier is properly set - this.Job.Identifier = this.IdGenerator.GetJobIdentifier(this.Stage?.Name, this.Phase.Name, this.Job.Name); - - if (job.Definition?.Variables?.Count > 0) - { - SetUserVariables(job.Definition.Variables.OfType()); - } - - SetSystemVariables(variables); - - // Add the attempt information into the context - var systemVariables = new List - { - new Variable - { - Name = WellKnownDistributedTaskVariables.JobIdentifier, - Value = job.Identifier - }, - new Variable - { - Name = WellKnownDistributedTaskVariables.JobAttempt, - Value = job.Attempt.ToString() - }, - }; - - if (positionInPhase != default) - { - systemVariables.Add(new Variable - { - Name = WellKnownDistributedTaskVariables.JobPositionInPhase, - Value = positionInPhase.ToString() - }); - } - - if (totalJobsInPhase != default) - { - systemVariables.Add(new Variable - { - Name = WellKnownDistributedTaskVariables.TotalJobsInPhase, - Value = totalJobsInPhase.ToString() - }); - } - - SetSystemVariables(systemVariables); - - if (String.IsNullOrEmpty(this.ExecutionOptions.SystemTokenScope) && - this.Variables.TryGetValue(WellKnownDistributedTaskVariables.AccessTokenScope, out VariableValue tokenScope)) - { - this.ExecutionOptions.SystemTokenScope = tokenScope?.Value; - } - - if (data?.Count > 0) - { - foreach (var pair in data) - { - Data[pair.Key] = pair.Value; - } - } - } - - public StageInstance Stage - { - get; - } - - public PhaseInstance Phase - { - get; - } - - public JobInstance Job - { - get; - } - - internal override String GetInstanceName() - { - return this.IdGenerator.GetJobInstanceName(this.Stage?.Name, this.Phase.Name, this.Job.Name, this.Job.Attempt); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/JobInstance.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/JobInstance.cs deleted file mode 100644 index 45d12e8fa..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/JobInstance.cs +++ /dev/null @@ -1,124 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public sealed class JobInstance - { - public JobInstance() - : this(String.Empty) - { - } - - public JobInstance(String name) - : this(name, 1) - { - } - - public JobInstance( - String name, - Int32 attempt) - { - this.Name = name; - this.Attempt = attempt; - } - - public JobInstance( - String name, - TaskResult result) - : this(name) - { - this.Result = result; - } - - public JobInstance(Job job) - : this(job, 1) - { - } - - public JobInstance( - Job job, - Int32 attempt) - : this(job.Name, attempt) - { - this.Definition = job; - this.State = PipelineState.NotStarted; - } - - [DataMember] - public String Identifier - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public Int32 Attempt - { - get; - set; - } - - [DataMember] - public DateTime? StartTime - { - get; - set; - } - - [DataMember] - public DateTime? FinishTime - { - get; - set; - } - - [DataMember] - public PipelineState State - { - get; - set; - } - - [DataMember] - public TaskResult? Result - { - get; - set; - } - - [DataMember] - public Job Definition - { - get; - set; - } - - public IDictionary Outputs - { - get - { - if (m_outputs == null) - { - m_outputs = new VariablesDictionary(); - } - return m_outputs; - } - } - - [DataMember(Name = "Outputs")] - private VariablesDictionary m_outputs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/JobStartedEventData.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/JobStartedEventData.cs deleted file mode 100644 index 84491294e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/JobStartedEventData.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [DataContract] - public sealed class JobStartedEventData - { - [DataMember(EmitDefaultValue = false)] - public PhaseTargetType JobType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Guid JobId - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Object Data - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseAttempt.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseAttempt.cs deleted file mode 100644 index 6995b84ab..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseAttempt.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PhaseAttempt - { - public PhaseInstance Phase - { - get; - set; - } - - public IList Jobs - { - get - { - if (m_jobs == null) - { - m_jobs = new List(); - } - return m_jobs; - } - } - - private List m_jobs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseExecutionContext.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseExecutionContext.cs deleted file mode 100644 index 41deffce0..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseExecutionContext.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - /// - /// Provides context necessary for the execution of a pipeline. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class PhaseExecutionContext : GraphExecutionContext - { - public PhaseExecutionContext( - StageInstance stage = null, - PhaseInstance phase = null, - DictionaryContextData data = null, - EvaluationOptions expressionOptions = null, - ExecutionOptions executionOptions = null) - : this(stage, phase, PipelineState.InProgress, data, - new CounterStore(), new PackageStore(), new ResourceStore(), new TaskStore(), - null, null, null, expressionOptions, executionOptions) - { - } - - /// - /// Initializes a new PipelineExecutionContext instance using the specified task store. - /// - /// The store which should be utilized for task reference resolution - /// The additional pre-defined resources which should be utilized for resource resolution, like: Container - public PhaseExecutionContext( - StageInstance stage, - PhaseInstance phase, - PipelineState state, - DictionaryContextData data, - ICounterStore counterStore, - IPackageStore packageStore, - IResourceStore resourceStore, - ITaskStore taskStore, - IList stepProviders, - IPipelineIdGenerator idGenerator, - IPipelineTraceWriter trace, - EvaluationOptions expressionOptions, - ExecutionOptions executionOptions) - : base(phase, state, data, counterStore, packageStore, resourceStore, taskStore, stepProviders, idGenerator, trace, expressionOptions, executionOptions) - { - this.Stage = stage; - if (this.Stage != null) - { - this.Stage.Identifier = this.IdGenerator.GetStageIdentifier(this.Stage.Name); - } - - // Set the full identifier according to the current context - this.Phase.Identifier = this.IdGenerator.GetPhaseIdentifier(this.Stage?.Name, this.Phase.Name); - } - - /// - /// The current stage which is being executed. - /// - public StageInstance Stage - { - get; - } - - /// - /// The current phase which is being executed. - /// - public PhaseInstance Phase - { - get - { - return base.Node; - } - } - - /// - /// Gets the previous attempt of the phase if this is a retry of a job which has already executed. - /// - public PhaseAttempt PreviousAttempt - { - get; - set; - } - - public JobExecutionContext CreateJobContext( - String name, - Int32 attempt, - Int32 positionInPhase = default, - Int32 totalJobsInPhase = default) - { - return CreateJobContext( - new JobInstance(name, attempt), - positionInPhase, - totalJobsInPhase); - } - - public JobExecutionContext CreateJobContext( - JobInstance jobInstance, - Int32 positionInPhase = default, - Int32 totalJobsInPhase = default) - { - return new JobExecutionContext( - context: this, - job: jobInstance, - variables: null, - positionInPhase: positionInPhase, - totalJobsInPhase: totalJobsInPhase); - } - - internal override String GetInstanceName() - { - return this.IdGenerator.GetPhaseInstanceName(this.Stage?.Name, this.Phase.Name, this.Phase.Attempt); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseInstance.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseInstance.cs deleted file mode 100644 index 7e13aaea3..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/PhaseInstance.cs +++ /dev/null @@ -1,61 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class PhaseInstance : GraphNodeInstance - { - public PhaseInstance() - { - } - - public PhaseInstance(String name) - : this(name, TaskResult.Succeeded) - { - } - - public PhaseInstance( - String name, - Int32 attempt) - : this(name, attempt, null, TaskResult.Succeeded) - { - } - - public PhaseInstance(PhaseNode phase) - : this(phase, 1) - { - } - - public PhaseInstance( - PhaseNode phase, - Int32 attempt) - : this(phase.Name, attempt, phase, TaskResult.Succeeded) - { - } - - public PhaseInstance( - String name, - TaskResult result) - : this(name, 1, null, result) - { - } - - public PhaseInstance( - String name, - Int32 attempt, - PhaseNode definition, - TaskResult result) - : base(name, attempt, definition, result) - { - } - - public static implicit operator PhaseInstance(String name) - { - return new PhaseInstance(name); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineAttemptBuilder.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineAttemptBuilder.cs deleted file mode 100644 index 7cf66fa93..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineAttemptBuilder.cs +++ /dev/null @@ -1,632 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Pipelines.Validation; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - /// - /// Provides functionality to build structured data from the timeline store. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class PipelineAttemptBuilder - { - public PipelineAttemptBuilder( - IPipelineIdGenerator idGenerator, - PipelineProcess pipeline, - params Timeline[] timelines) - { - ArgumentUtility.CheckForNull(idGenerator, nameof(idGenerator)); - ArgumentUtility.CheckForNull(pipeline, nameof(pipeline)); - - this.Pipeline = pipeline; - this.IdGenerator = idGenerator; - m_recordsById = new Dictionary(); - m_recordsByParent = new Dictionary>(); - m_stages = new Dictionary>(StringComparer.OrdinalIgnoreCase); - - if (timelines?.Length > 0) - { - foreach (var timeline in timelines) - { - AddStageAttempts(timeline, m_stages); - } - } - } - - /// - /// Gets the ID generator for this pipeline. - /// - public IPipelineIdGenerator IdGenerator - { - get; - } - - /// - /// Gets the pipeline document. - /// - public PipelineProcess Pipeline - { - get; - } - - /// - /// Creates the initial stage attempts for a brand new pipeline. - /// - /// A list of initial attempts which should be run - public IList Initialize() - { - var initialAttempts = new List(); - foreach (var stage in this.Pipeline.Stages) - { - initialAttempts.Add(CreateAttempt(stage)); - } - return initialAttempts; - } - - /// - /// Produce list of stage attempts needed to retry a pipeline. - /// By default, we will reuse previously successful stage attempts, and produce new attempts for - /// failed stages, and any stages downstream from a failed stage. - /// If specific stage names are provided, only these stages and their descendents will be retried, - /// and will be retried irrespective of previous state. - /// - /// tuple of all attempts (the full list of attempts to be added to the plan) and "new attempts" (the retries) - public Tuple, IList> Retry(IList stageNames = null) - { - var allAttempts = new List(); - var newAttempts = new List(); - var stagesToRetry = new HashSet(StringComparer.OrdinalIgnoreCase); - - GraphValidator.Traverse(this.Pipeline.Stages, (stage, dependencies) => - { - var previousAttempt = GetStageAttempt(stage.Name); - if (previousAttempt == null) - { - // nothing to retry - return; - } - - // collect some data - var directlyTargeted = stageNames?.Contains(stage.Name, StringComparer.OrdinalIgnoreCase) is true; - var needsRetry = NeedsRetry(previousAttempt.Stage.Result); - var dependencyNeedsRetry = dependencies.Any(x => stagesToRetry.Contains(x)); - - // create new attempt - var newAttempt = default(StageAttempt); - if (dependencyNeedsRetry - || (stageNames == default && needsRetry) - || (stageNames != default && directlyTargeted)) - { - // try to create new attempt, if it comes back null, no work needs to be done - // force a retry if the stage is directly targeted but the previous attempt was successful. - newAttempt = CreateAttempt( - stage, - previousAttempt, - forceRetry: (directlyTargeted && !needsRetry) || dependencyNeedsRetry); - } - - // update return lists - if (newAttempt == default) - { - // use previous attempt - allAttempts.Add(previousAttempt); - } - else - { - stagesToRetry.Add(previousAttempt.Stage.Name); - allAttempts.Add(newAttempt); - newAttempts.Add(newAttempt); - } - }); - - return Tuple.Create( - allAttempts as IList, - newAttempts as IList); - } - - /// - /// Create a new stage attempt and a new timeline. - /// The new timeline should contain the Pending entries for any stages, phases and jobs that need to be retried. - /// It should contain a full, re-parented, copy of the timeline subgraphs for stages, phases, and jobs that do not need to be retried. - /// - private StageAttempt CreateAttempt( - Stage stage, - StageAttempt previousStageAttempt = null, - Boolean forceRetry = false) - { - // new instance will have attempt number previous + 1 - var newStageAttempt = new StageAttempt - { - Stage = new StageInstance(stage, previousStageAttempt?.Stage.Attempt + 1 ?? 1), - Timeline = new Timeline(), - }; - - // Compute the stage ID for this attempt - var stageIdentifier = this.IdGenerator.GetStageIdentifier(newStageAttempt.Stage.Name); - var stageId = this.IdGenerator.GetStageInstanceId(newStageAttempt.Stage.Name, newStageAttempt.Stage.Attempt); - newStageAttempt.Timeline.Id = stageId; - newStageAttempt.Stage.Identifier = stageIdentifier; - - if (previousStageAttempt != null) - { - // copy the previous timeline record, reset to "Pending" state - var previousRecord = m_recordsById[this.IdGenerator.GetStageInstanceId(previousStageAttempt.Stage.Name, previousStageAttempt.Stage.Attempt)]; - newStageAttempt.Timeline.Records.Add(ResetRecord(previousRecord, null, stageId, newStageAttempt.Stage.Attempt)); - } - else - { - // create a new stage record - newStageAttempt.Timeline.Records.Add(CreateRecord(newStageAttempt.Stage, null, stageId, stage.DisplayName ?? stage.Name, nameof(Stage), m_stageOrder++, stageIdentifier)); - } - - // walk the phases. - // if a phase does not need to be retried, copy its entire timeline subgraph to the new timeline. - var phaseOrder = 1; - var phasesRetried = false; - var phasesToRetry = new HashSet(StringComparer.OrdinalIgnoreCase); - GraphValidator.Traverse(stage.Phases, (phase, dependencies) => - { - var shouldRetry = false; - var previousPhaseAttempt = previousStageAttempt?.Phases.FirstOrDefault(x => String.Equals(x.Phase.Name, phase.Name, StringComparison.OrdinalIgnoreCase)); - var upstreamDependencyNeedsRetry = dependencies.Any(x => phasesToRetry.Contains(x)); - var previousAttemptNeedsRetry = NeedsRetry(previousPhaseAttempt?.Phase.Result); - if (forceRetry || upstreamDependencyNeedsRetry || previousAttemptNeedsRetry) - { - // If the previous attempt a specific phase failed then we should retry it and everything - // downstream regardless of first attempt status. The failed phases are appended as we walk - // the graph and the set is inspected - shouldRetry = true; - phasesToRetry.Add(phase.Name); - } - - if (!shouldRetry && previousPhaseAttempt != null) - { - // This phase does not need to be retried. - // Copy timeline records from previous timeline to new timeline. - // The new timeline should report that this phase has already been run, and the parent should be the new stage. - previousPhaseAttempt.Phase.Definition = phase; - newStageAttempt.Phases.Add(previousPhaseAttempt); - - // clone so as not to mess up our lookup table. - var previousPhaseId = this.IdGenerator.GetPhaseInstanceId(newStageAttempt.Stage.Name, previousPhaseAttempt.Phase.Name, previousPhaseAttempt.Phase.Attempt); - var newPhaseRecord = m_recordsById[previousPhaseId].Clone(); - newPhaseRecord.ParentId = stageId; // this phase is already completed for the new stage. - - phaseOrder = (newPhaseRecord.Order ?? phaseOrder) + 1; // TODO: what does this do? - newStageAttempt.Timeline.Records.Add(newPhaseRecord); - - // if there are any child records of the phase, copy them too. - // they should exist exactly as they are on the new timeline. - // Only the phase needs to reparent. - newStageAttempt.Timeline.Records.AddRange(CollectAllChildren(newPhaseRecord)); - } - else - { - // This phase needs to be retried. - // Track that we are scheduling a phase for retry in this attempt - phasesRetried = true; - - // Create a new attempt record in the pending state. At runtime the job expansion logic, based on the target - // strategy, will determine what needs to be re-run and what doesn't based on the previous attempt. We don't - // make assumptions about the internals of jobs here as that is the piece the orchestrator doesn't deal with - // directly. - var newPhaseAttempt = new PhaseAttempt - { - Phase = new PhaseInstance(phase, previousPhaseAttempt?.Phase.Attempt + 1 ?? 1), - }; - - var phaseId = this.IdGenerator.GetPhaseInstanceId( - newStageAttempt.Stage.Name, - newPhaseAttempt.Phase.Name, - newPhaseAttempt.Phase.Attempt); - - newPhaseAttempt.Phase.Identifier = this.IdGenerator.GetPhaseIdentifier(newStageAttempt.Stage.Name, newPhaseAttempt.Phase.Name); - newStageAttempt.Timeline.Records.Add(CreateRecord( - newPhaseAttempt.Phase, - stageId, - phaseId, - phase.DisplayName ?? phase.Name, - nameof(Phase), - phaseOrder++, - newPhaseAttempt.Phase.Identifier)); - - // The previous attempt failed but we had no upstream failures means that this specific phase - // needs have the failed jobs re-run. - // For this case we just locate the failed jobs and create new - // attempt records to ensure they are re-run. - if (previousAttemptNeedsRetry && !upstreamDependencyNeedsRetry) - { - foreach (var previousJobAttempt in previousPhaseAttempt.Jobs) - { - var previousJobId = this.IdGenerator.GetJobInstanceId( - newStageAttempt.Stage.Name, - newPhaseAttempt.Phase.Name, - previousJobAttempt.Job.Name, - previousJobAttempt.Job.Attempt); - - if (NeedsRetry(previousJobAttempt.Job.Result)) - { - // this job needs to be retried. - // - // NOTE: - // Phases (JobFactories) normally are expanded dynamically to produce jobs. - // The phase expansion routines allow a list of configurations to be supplied. If non-empty, the JobFactories will only - // produce Jobs with the names provided. - // - // In retry attempts, we already know the Job names that will be produced, and we only want to run a subset of them. - // We can define the subset of jobs to be "expanded" by initializing the PhaseAttempt with named JobAttempts. - // See RunPhase for more details. - var newJobAttempt = new JobAttempt - { - Job = new JobInstance(previousJobAttempt.Job.Name, previousJobAttempt.Job.Attempt + 1), - }; - newJobAttempt.Job.Identifier = this.IdGenerator.GetJobIdentifier( - newStageAttempt.Stage.Name, - newPhaseAttempt.Phase.Name, - newJobAttempt.Job.Name); - newPhaseAttempt.Jobs.Add(newJobAttempt); - - // create a new record in "Pending" state based on the previous record. - var newJobId = this.IdGenerator.GetJobInstanceId( - newStageAttempt.Stage.Name, - newPhaseAttempt.Phase.Name, - newJobAttempt.Job.Name, - newJobAttempt.Job.Attempt); - newStageAttempt.Timeline.Records.Add(ResetRecord(m_recordsById[previousJobId], phaseId, newJobId, newJobAttempt.Job.Attempt)); - } - else - { - // this job does not need to be retried. - // deep copy the timeline subgraph to the new timeline. - // reparent the job record to the new phase id so the job looks completed on the new timeline. - var newJobRecord = m_recordsById[previousJobId].Clone(); - newJobRecord.ParentId = phaseId; - newPhaseAttempt.Jobs.Add(previousJobAttempt); - newStageAttempt.Timeline.Records.Add(newJobRecord); - newStageAttempt.Timeline.Records.AddRange(CollectAllChildren(newJobRecord)); - } - } - } - - newStageAttempt.Phases.Add(newPhaseAttempt); - } - }); - - if (!phasesRetried) - { - // The stage will remain complete so there is no reason to register a new attempt - return null; - } - - // If this is a new pipeline store that is empty we need to initialize the attempts for this stage. - if (!m_stages.TryGetValue(stage.Name, out IList attempts)) - { - attempts = new List(); - m_stages[stage.Name] = attempts; - } - - attempts.Add(newStageAttempt); - return newStageAttempt; - } - - public StageAttempt GetStageAttempt( - String name, - Int32 attempt = -1) - { - if (!m_stages.TryGetValue(name, out var attempts)) - { - return null; - } - - if (attempt <= 0) - { - return attempts.OrderByDescending(x => x.Stage.Attempt).FirstOrDefault(); - } - else - { - return attempts.FirstOrDefault(x => x.Stage.Attempt == attempt); - } - } - - /// - /// returns true if result should be retried. - /// - internal static Boolean NeedsRetry(TaskResult? result) - { - return result == TaskResult.Abandoned - || result == TaskResult.Canceled - || result == TaskResult.Failed; - } - - private TimelineRecord CreateRecord( - IGraphNodeInstance node, - Guid? parentId, - Guid recordId, - String name, - String type, - Int32 order, - String identifier) - { - return new TimelineRecord - { - Attempt = node.Attempt, - Id = recordId, - Identifier = identifier, - Name = name, - Order = order, - ParentId = parentId, - RecordType = type, - RefName = node.Name, - State = TimelineRecordState.Pending, - }; - } - - /// - /// creates a new timeline record with Pending state based on the input. - /// - private TimelineRecord ResetRecord( - TimelineRecord record, - Guid? parentId, - Guid newId, - Int32 attempt) - { - return new TimelineRecord - { - // new stuff - Attempt = attempt, - Id = newId, - ParentId = parentId, - State = TimelineRecordState.Pending, - - // old stuff - Identifier = record.Identifier, - Name = record.Name, - Order = record.Order, - RecordType = record.RecordType, - RefName = record.RefName, - }; - } - - /// - /// Returns tuple of recordsById, recordsByParentId - /// - internal static Tuple, IDictionary>> ParseTimeline(Timeline timeline) - { - var recordsById = new Dictionary(); - var recordsByParentId = new Dictionary>(); - - foreach (var record in timeline?.Records) - { - recordsById[record.Id] = record; - - if (record.ParentId != null) - { - if (!recordsByParentId.TryGetValue(record.ParentId.Value, out var childRecords)) - { - childRecords = new List(); - recordsByParentId.Add(record.ParentId.Value, childRecords); - } - - childRecords.Add(record); - } - else if (record.RecordType == nameof(Stage)) - { - FixRecord(record); - } - } - - return Tuple.Create( - recordsById as IDictionary, - recordsByParentId as IDictionary>); - } - - private void AddStageAttempts( - Timeline timeline, - IDictionary> attempts) - { - if (timeline == default) - { - return; // nothing to do - } - - // parse timeline - var tuple = ParseTimeline(timeline); - m_recordsById = tuple.Item1; - m_recordsByParent = tuple.Item2; - - foreach (var stageRecord in m_recordsById.Values.Where(x => x.RecordType == "Stage")) - { - var attempt = new StageAttempt - { - Stage = new StageInstance - { - Attempt = stageRecord.Attempt, - FinishTime = stageRecord.FinishTime, - Identifier = stageRecord.Identifier, - Name = stageRecord.RefName, - Result = stageRecord.Result, - StartTime = stageRecord.StartTime, - State = Convert(stageRecord.State.Value), - }, - Timeline = new Timeline - { - Id = timeline.Id, - }, - }; - - attempt.Timeline.Records.Add(stageRecord); - - if (m_recordsByParent.TryGetValue(stageRecord.Id, out var phaseRecords)) - { - AddPhaseAttempts( - attempt, - phaseRecords.Where(x => x.RecordType == nameof(Phase)), - m_recordsByParent); - } - - if (!attempts.TryGetValue(attempt.Stage.Identifier, out var stageAttempts)) - { - stageAttempts = new List(); - attempts.Add(attempt.Stage.Identifier, stageAttempts); - } - - stageAttempts.Add(attempt); - } - } - - private void AddPhaseAttempts( - StageAttempt stageAttempt, - IEnumerable phaseRecords, - IDictionary> recordsByParent) - { - foreach (var phaseRecord in phaseRecords) - { - FixRecord(phaseRecord); - - var phaseAttempt = new PhaseAttempt - { - Phase = new PhaseInstance - { - Attempt = phaseRecord.Attempt, - FinishTime = phaseRecord.FinishTime, - Identifier = phaseRecord.Identifier, - Name = phaseRecord.RefName, - Result = phaseRecord.Result, - StartTime = phaseRecord.StartTime, - State = Convert(phaseRecord.State.Value), - }, - }; - - stageAttempt.Phases.Add(phaseAttempt); - stageAttempt.Timeline.Records.Add(phaseRecord); - - // Drive down into the individual jobs if they exist - if (recordsByParent.TryGetValue(phaseRecord.Id, out var jobRecords)) - { - AddJobAttempts( - stageAttempt, - phaseAttempt, - jobRecords.Where(x => x.RecordType == nameof(Job)), - recordsByParent); - } - } - } - - private void AddJobAttempts( - StageAttempt stageAttempt, - PhaseAttempt phaseAttempt, - IEnumerable jobRecords, - IDictionary> recordsByParent) - { - foreach (var jobRecord in jobRecords) - { - FixRecord(jobRecord); - - var jobAttempt = new JobAttempt - { - Job = new JobInstance - { - Attempt = jobRecord.Attempt, - FinishTime = jobRecord.FinishTime, - Identifier = jobRecord.Identifier, - Name = jobRecord.RefName, - Result = jobRecord.Result, - StartTime = jobRecord.StartTime, - State = Convert(jobRecord.State.Value), - }, - }; - - phaseAttempt.Jobs.Add(jobAttempt); - stageAttempt.Timeline.Records.Add(jobRecord); - - // Just blindly copy the child records - stageAttempt.Timeline.Records.AddRange(CollectAllChildren(jobRecord)); - } - } - - internal IList CollectAllChildren( - TimelineRecord root, - Int32 maxDepth = int.MaxValue) - { - return CollectAllChildren(root, m_recordsByParent, maxDepth); - } - - internal static IList CollectAllChildren( - TimelineRecord root, - IDictionary> recordsByParent, - Int32 maxDepth = int.MaxValue) - { - var result = new List(); - if (!recordsByParent.TryGetValue(root.Id, out var childRecords)) - { - return result; - } - - // instead of actually recursing, create a queue of record, depth pairs. - var recordQueue = new Queue>(childRecords.Select(x => Tuple.Create(x, 1))); - while (recordQueue.Count > 0) - { - var t = recordQueue.Dequeue(); - var currentRecord = t.Item1; - var currentDepth = t.Item2; - - // collect record - result.Add(currentRecord); - - // check depth - if (currentDepth >= maxDepth) - { - continue; - } - - // enqueue children - var childDepth = currentDepth + 1; - if (recordsByParent.TryGetValue(currentRecord.Id, out var newChildren)) - { - foreach (var newChild in newChildren) - { - recordQueue.Enqueue(Tuple.Create(newChild, childDepth)); - } - } - } - - return result; - } - - private static PipelineState Convert(TimelineRecordState state) - { - switch (state) - { - case TimelineRecordState.Completed: - return PipelineState.Completed; - case TimelineRecordState.InProgress: - return PipelineState.InProgress; - } - - return PipelineState.NotStarted; - } - - /// - /// The timeline records get normalized into strings which are not case-sensitive, meaning the input - /// casing may not match what is output.In order to compensate for this we update the ref name from - /// the identifier, as the identifier reflects the actual value. - /// - private static void FixRecord(TimelineRecord record) - { - if (!String.IsNullOrEmpty(record.Identifier)) - { - record.RefName = PipelineUtilities.GetName(record.Identifier); - } - } - - // Includes all attempts of all stages - private Int32 m_stageOrder = 1; - private IDictionary m_recordsById; - private IDictionary> m_recordsByParent; - private IDictionary> m_stages; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineExecutionContext.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineExecutionContext.cs deleted file mode 100644 index f8133bc78..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/PipelineExecutionContext.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PipelineExecutionContext : PipelineContextBase - { - private protected PipelineExecutionContext(PipelineExecutionContext context) - : base(context) - { - this.State = context.State; - this.ExecutionOptions = context.ExecutionOptions; - } - - private protected PipelineExecutionContext( - DictionaryContextData data, - ICounterStore counterStore, - IPackageStore packageStore, - IResourceStore resourceStore, - ITaskStore taskStore, - IList stepProviders, - PipelineState state, - IPipelineIdGenerator idGenerator = null, - IPipelineTraceWriter trace = null, - EvaluationOptions expressionOptions = null, - ExecutionOptions executionOptions = null) - : base(data, counterStore, packageStore, resourceStore, taskStore, stepProviders, idGenerator, trace, expressionOptions) - { - this.State = state; - this.ExecutionOptions = executionOptions ?? new ExecutionOptions(); - } - - /// - /// Gets the current state of the pipeline. - /// - public PipelineState State - { - get; - } - - /// - /// Gets the execution options used for the pipeline. - /// - public ExecutionOptions ExecutionOptions - { - get; - } - - /// - /// Gets the instance ID for the current context. - /// - /// - internal Guid GetInstanceId() - { - return this.IdGenerator.GetInstanceId(this.GetInstanceName()); - } - - /// - /// When overridden in a derived class, gets the instance name using . - /// - /// The instance name according to the associated generator - internal abstract String GetInstanceName(); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/StageAttempt.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/StageAttempt.cs deleted file mode 100644 index cbffa1ee7..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/StageAttempt.cs +++ /dev/null @@ -1,40 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class StageAttempt - { - internal StageAttempt() - { - } - - public StageInstance Stage - { - get; - set; - } - - public IList Phases - { - get - { - if (m_phases == null) - { - m_phases = new List(); - } - return m_phases; - } - } - - public Timeline Timeline - { - get; - internal set; - } - - private List m_phases; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/StageExecutionContext.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/StageExecutionContext.cs deleted file mode 100644 index 34a7f00fb..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/StageExecutionContext.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Pipelines.ContextData; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - /// - /// Provides context necessary for the execution of a pipeline. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class StageExecutionContext : GraphExecutionContext - { - public StageExecutionContext( - StageInstance stage = default, - DictionaryContextData data = null) - : this(stage, PipelineState.InProgress, data, new CounterStore(), new PackageStore(), new ResourceStore(), new TaskStore(), null, null, null, null, null) - { - } - - /// - /// Initializes a new StageExecutionContext instance using the specified stage and services. - /// - /// The store which should be utilized for task reference resolution - /// The additional pre-defined resources which should be utilized for resource resolution, like: Container - public StageExecutionContext( - StageInstance stage, - PipelineState state, - DictionaryContextData data, - ICounterStore counterStore, - IPackageStore packageStore, - IResourceStore resourceStore, - ITaskStore taskStore, - IList stepProviders, - IPipelineIdGenerator idGenerator, - IPipelineTraceWriter trace, - EvaluationOptions expressionOptions, - ExecutionOptions executionOptions) - : base(stage, state, data, counterStore, packageStore, resourceStore, taskStore, stepProviders, idGenerator, trace, expressionOptions, executionOptions) - { - this.Stage.Identifier = this.IdGenerator.GetStageIdentifier(stage.Name); - } - - /// - /// The current stage which is being executed. - /// - public StageInstance Stage => this.Node; - - /// - /// Gets the previous attempt of the stage if this is a retry of a job which has already executed. - /// - public StageAttempt PreviousAttempt - { - get; - } - - internal override String GetInstanceName() - { - return this.IdGenerator.GetStageInstanceName(this.Stage.Name, this.Stage.Attempt); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Runtime/StageInstance.cs b/src/Sdk/DTPipelines/Pipelines/Runtime/StageInstance.cs deleted file mode 100644 index 93ef248c5..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Runtime/StageInstance.cs +++ /dev/null @@ -1,61 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Runtime -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class StageInstance : GraphNodeInstance - { - public StageInstance() - { - } - - public StageInstance(String name) - : this(name, TaskResult.Succeeded) - { - } - - public StageInstance( - String name, - Int32 attempt) - : this(name, attempt, null, TaskResult.Succeeded) - { - } - - public StageInstance(Stage stage) - : this(stage, 1) - { - } - - public StageInstance( - Stage stage, - Int32 attempt) - : this(stage.Name, attempt, stage, TaskResult.Succeeded) - { - } - - public StageInstance( - String name, - TaskResult result) - : this(name, 1, null, result) - { - } - - public StageInstance( - String name, - Int32 attempt, - Stage definition, - TaskResult result) - : base(name, attempt, definition, result) - { - } - - public static implicit operator StageInstance(String name) - { - return new StageInstance(name); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/SecretStoreConfiguration.cs b/src/Sdk/DTPipelines/Pipelines/SecretStoreConfiguration.cs deleted file mode 100644 index 544b062a9..000000000 --- a/src/Sdk/DTPipelines/Pipelines/SecretStoreConfiguration.cs +++ /dev/null @@ -1,91 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class SecretStoreConfiguration - { - public SecretStoreConfiguration() - { - } - - private SecretStoreConfiguration(SecretStoreConfiguration configurationToCopy) - { - this.Endpoint = configurationToCopy.Endpoint?.Clone(); - this.StoreName = configurationToCopy.StoreName; - - m_endpointId = configurationToCopy.m_endpointId; - if (configurationToCopy.m_keys?.Count > 0) - { - m_keys = new List(configurationToCopy.m_keys); - } - } - - [DataMember(EmitDefaultValue = false)] - public ServiceEndpointReference Endpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String StoreName - { - get; - set; - } - - public IList Keys - { - get - { - if (m_keys == null) - { - m_keys = new List(); - } - return m_keys; - } - } - - public SecretStoreConfiguration Clone() - { - return new SecretStoreConfiguration(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (this.Endpoint == null && m_endpointId != Guid.Empty) - { - this.Endpoint = new ServiceEndpointReference - { - Id = m_endpointId, - }; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_keys?.Count == 0) - { - m_keys = null; - } - - if (this.Endpoint != null && this.Endpoint.Id != Guid.Empty) - { - m_endpointId = this.Endpoint.Id; - } - } - - [DataMember(Name = "EndpointId", EmitDefaultValue = false)] - private Guid m_endpointId; - - [DataMember(Name = "Keys", EmitDefaultValue = false)] - private List m_keys; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/SecureFileReference.cs b/src/Sdk/DTPipelines/Pipelines/SecureFileReference.cs deleted file mode 100644 index 4226c9d18..000000000 --- a/src/Sdk/DTPipelines/Pipelines/SecureFileReference.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class SecureFileReference : ResourceReference - { - public SecureFileReference() - { - } - - private SecureFileReference(SecureFileReference referenceToCopy) - : base(referenceToCopy) - { - this.Id = referenceToCopy.Id; - } - - [DataMember(EmitDefaultValue = false)] - public Guid Id - { - get; - set; - } - - public SecureFileReference Clone() - { - return new SecureFileReference(this); - } - - public override String ToString() - { - return base.ToString() ?? this.Id.ToString("D"); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/SecureFileStore.cs b/src/Sdk/DTPipelines/Pipelines/SecureFileStore.cs deleted file mode 100644 index f2448ec0c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/SecureFileStore.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class SecureFileStore : ISecureFileStore - { - public SecureFileStore( - IList files, - ISecureFileResolver resolver = null) - { - this.Resolver = resolver; - Add(files?.ToArray()); - } - - /// - /// Get the endpoint resolver configured for this store. - /// - public ISecureFileResolver Resolver - { - get; - } - - public IList GetAuthorizedReferences() - { - return m_resourcesById.Values.Select(x => new SecureFileReference { Id = x.Id }).ToList(); - } - - public SecureFile Get(SecureFileReference reference) - { - if (reference == null) - { - return null; - } - - var referenceId = reference.Id; - var referenceName = reference.Name?.Literal; - if (referenceId == Guid.Empty && String.IsNullOrEmpty(referenceName)) - { - return null; - } - - SecureFile authorizedResource = null; - if (referenceId != Guid.Empty) - { - if (m_resourcesById.TryGetValue(referenceId, out authorizedResource)) - { - return authorizedResource; - } - } - else if (!String.IsNullOrEmpty(referenceName)) - { - if (m_resourcesByName.TryGetValue(referenceName, out List matchingResources)) - { - if (matchingResources.Count > 1) - { - throw new AmbiguousResourceSpecificationException(PipelineStrings.AmbiguousServiceEndpointSpecification(referenceId)); - } - - return matchingResources[0]; - } - } - - // If we have an authorizer then attempt to authorize the reference for use - authorizedResource = this.Resolver?.Resolve(reference); - if (authorizedResource != null) - { - Add(authorizedResource); - } - - return authorizedResource; - } - - private void Add(params SecureFile[] resources) - { - if (resources?.Length > 0) - { - foreach (var resource in resources) - { - if (m_resourcesById.TryGetValue(resource.Id, out _)) - { - continue; - } - - m_resourcesById.Add(resource.Id, resource); - - if (!m_resourcesByName.TryGetValue(resource.Name, out List resourcesByName)) - { - resourcesByName = new List(); - m_resourcesByName.Add(resource.Name, resourcesByName); - } - - resourcesByName.Add(resource); - } - } - } - - private readonly Dictionary m_resourcesById = new Dictionary(); - private readonly Dictionary> m_resourcesByName = new Dictionary>(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ServerTarget.cs b/src/Sdk/DTPipelines/Pipelines/ServerTarget.cs deleted file mode 100644 index f8008352f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ServerTarget.cs +++ /dev/null @@ -1,92 +0,0 @@ -using System; -using System.ComponentModel; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class ServerTarget : PhaseTarget - { - public ServerTarget() - : base(PhaseTargetType.Server) - { - } - - private ServerTarget(ServerTarget targetToClone) - : base(targetToClone) - { - this.Execution = targetToClone.Execution?.Clone(); - } - - [DataMember(EmitDefaultValue = false)] - public ParallelExecutionOptions Execution - { - get; - set; - } - - public override PhaseTarget Clone() - { - return new ServerTarget(this); - } - - public override Boolean IsValid(TaskDefinition task) - { - return task.RunsOn.Contains(TaskRunsOnConstants.RunsOnServer, StringComparer.OrdinalIgnoreCase); - } - - internal override JobExecutionContext CreateJobContext( - PhaseExecutionContext context, - String jobName, - Int32 attempt, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory) - { - context.Trace?.EnterProperty("CreateJobContext"); - var e = this.Execution ?? new ParallelExecutionOptions(); - var jobContext = e.CreateJobContext( - context, - jobName, - attempt, - null, - null, - continueOnError, - timeoutInMinutes, - cancelTimeoutInMinutes, - jobFactory); - context.Trace?.LeaveProperty("CreateJobContext"); - - jobContext.Variables[WellKnownDistributedTaskVariables.EnableAccessToken] = Boolean.TrueString; - return jobContext; - } - - internal override ExpandPhaseResult Expand( - PhaseExecutionContext context, - Boolean continueOnError, - Int32 timeoutInMinutes, - Int32 cancelTimeoutInMinutes, - IJobFactory jobFactory, - JobExpansionOptions options) - { - context.Trace?.EnterProperty("Expand"); - var execution = this.Execution ?? new ParallelExecutionOptions(); - var result = execution.Expand( - context: context, - container: null, - sidecarContainers: null, - continueOnError: continueOnError, - timeoutInMinutes: timeoutInMinutes, - cancelTimeoutInMinutes: cancelTimeoutInMinutes, - jobFactory: jobFactory, - options: options); - context.Trace?.LeaveProperty("Expand"); - return result; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/ServiceEndpointStore.cs b/src/Sdk/DTPipelines/Pipelines/ServiceEndpointStore.cs deleted file mode 100644 index 80cf530fd..000000000 --- a/src/Sdk/DTPipelines/Pipelines/ServiceEndpointStore.cs +++ /dev/null @@ -1,118 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class ServiceEndpointStore : IServiceEndpointStore - { - public ServiceEndpointStore( - IList endpoints, - IServiceEndpointResolver resolver = null, - Boolean lazyLoadEndpoints = false) - { - this.Resolver = resolver; - this.LazyLoadEndpoints = lazyLoadEndpoints; - Add(endpoints?.ToArray()); - } - - /// - /// Get the endpoint resolver configured for this store. - /// - public IServiceEndpointResolver Resolver - { - get; - } - - public IList GetAuthorizedReferences() - { - if (LazyLoadEndpoints) - { - return this.Resolver != null ? this.Resolver.GetAuthorizedReferences() - : new List(); - } - - return m_endpointsById.Values.Select(x => new ServiceEndpointReference { Id = x.Id, Name = x.Name }).ToList(); - } - - public void Authorize(ServiceEndpointReference reference) - { - this.Resolver?.Authorize(reference); - } - - public ServiceEndpoint Get(ServiceEndpointReference reference) - { - if (reference == null) - { - return null; - } - - var referenceId = reference.Id; - var referenceName = reference.Name?.Literal; - if (referenceId == Guid.Empty && String.IsNullOrEmpty(referenceName)) - { - return null; - } - - ServiceEndpoint authorizedEndpoint = null; - if (referenceId != Guid.Empty) - { - if (m_endpointsById.TryGetValue(referenceId, out authorizedEndpoint)) - { - return authorizedEndpoint; - } - } - else if (!String.IsNullOrEmpty(referenceName)) - { - if (m_endpointsByName.TryGetValue(referenceName, out List matchingEndpoints)) - { - if (matchingEndpoints.Count > 1) - { - throw new AmbiguousResourceSpecificationException(PipelineStrings.AmbiguousServiceEndpointSpecification(referenceId)); - } - - return matchingEndpoints[0]; - } - } - - authorizedEndpoint = this.Resolver?.Resolve(reference); - if (authorizedEndpoint != null) - { - Add(authorizedEndpoint); - } - - return authorizedEndpoint; - } - - private void Add(params ServiceEndpoint[] endpoints) - { - if (endpoints?.Length > 0) - { - foreach (var endpoint in endpoints) - { - if (m_endpointsById.TryGetValue(endpoint.Id, out _)) - { - continue; - } - - m_endpointsById.Add(endpoint.Id, endpoint); - - if (!m_endpointsByName.TryGetValue(endpoint.Name, out List endpointsByName)) - { - endpointsByName = new List(); - m_endpointsByName.Add(endpoint.Name, endpointsByName); - } - - endpointsByName.Add(endpoint); - } - } - } - - private readonly Dictionary m_endpointsById = new Dictionary(); - private readonly Dictionary> m_endpointsByName = new Dictionary>(StringComparer.OrdinalIgnoreCase); - private readonly Boolean LazyLoadEndpoints; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Stage.cs b/src/Sdk/DTPipelines/Pipelines/Stage.cs deleted file mode 100644 index c94aab45c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Stage.cs +++ /dev/null @@ -1,208 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines.Validation; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class Stage : IGraphNode - { - public Stage() - { - } - - public Stage( - String name, - IList phases) - { - this.Name = name; - - if (phases?.Count > 0) - { - m_phases = new List(phases); - } - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String DisplayName - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Condition - { - get; - set; - } - - public IList Variables - { - get - { - if (m_variables == null) - { - m_variables = new List(); - } - return m_variables; - } - } - - public IList Phases - { - get - { - if (m_phases == null) - { - m_phases = new List(); - } - return m_phases; - } - } - - public ISet DependsOn - { - get - { - if (m_dependsOn == null) - { - m_dependsOn = new HashSet(StringComparer.OrdinalIgnoreCase); - } - return m_dependsOn; - } - } - - void IGraphNode.Validate( - PipelineBuildContext context, - ValidationResult result) - { - // Default the condition to something reasonable if none is specified - if (String.IsNullOrEmpty(this.Condition)) - { - this.Condition = StageCondition.Default; - } - else - { - // Simply construct the condition and make sure the syntax and functions used are valid - var parsedCondition = new StageCondition(this.Condition); - } - - if (m_variables?.Count > 0) - { - var variablesCopy = new List(); - foreach (var variable in this.Variables) - { - if (variable is Variable simpleVariable) - { - // Do not allow phase overrides for certain variables. - if (Phase.s_nonOverridableVariables.Contains(simpleVariable.Name)) - { - continue; - } - } - else if (variable is VariableGroupReference groupVariable) - { - if (context.EnvironmentVersion < 2) - { - result.Errors.Add(new PipelineValidationError(PipelineStrings.StageVariableGroupNotSupported(this.Name, groupVariable))); - continue; - } - - result.ReferencedResources.VariableGroups.Add(groupVariable); - - if (context.BuildOptions.ValidateResources) - { - var variableGroup = context.ResourceStore.VariableGroups.Get(groupVariable); - if (variableGroup == null) - { - result.UnauthorizedResources.VariableGroups.Add(groupVariable); - result.Errors.Add(new PipelineValidationError(PipelineStrings.VariableGroupNotFoundForStage(this.Name, groupVariable))); - } - } - } - - variablesCopy.Add(variable); - } - - m_variables.Clear(); - m_variables.AddRange(variablesCopy); - } - - GraphValidator.Validate(context, result, PipelineStrings.JobNameWhenNoNameIsProvided, this.Name, this.Phases, Phase.GetErrorMessage); - } - - internal static String GetErrorMessage( - String code, - params Object[] values) - { - switch (code) - { - case PipelineConstants.NameInvalid: - // values[0] is the graph name which is null during stage graph validation - // values[1] is the stage name - return PipelineStrings.StageNameInvalid(values[1]); - - case PipelineConstants.NameNotUnique: - // values[0] is the graph name which is null during stage graph validation - // values[1] is the stage name - return PipelineStrings.StageNamesMustBeUnique(values[1]); - - case PipelineConstants.StartingPointNotFound: - return PipelineStrings.PipelineNotValidNoStartingStage(); - - case PipelineConstants.DependencyNotFound: - // values[0] is the graph name which is null during stage graph validation - // values[1] is the node name - // values[2] is the dependency node name - return PipelineStrings.StageDependencyNotFound(values[1], values[2]); - - case PipelineConstants.GraphContainsCycle: - // values[0] is the graph name which is null during stage graph validation - // values[1] is the node name - // values[2] is the dependency node name - return PipelineStrings.StageGraphCycleDetected(values[1], values[2]); - } - - throw new NotSupportedException(); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_dependsOn?.Count == 0) - { - m_dependsOn = null; - } - - if (m_phases?.Count == 0) - { - m_phases = null; - } - - if (m_variables?.Count == 0) - { - m_variables = null; - } - } - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private List m_variables; - - [DataMember(Name = "Phases", EmitDefaultValue = false)] - private List m_phases; - - [DataMember(Name = "DependsOn", EmitDefaultValue = false)] - private HashSet m_dependsOn; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/StageCondition.cs b/src/Sdk/DTPipelines/Pipelines/StageCondition.cs deleted file mode 100644 index 874fd9862..000000000 --- a/src/Sdk/DTPipelines/Pipelines/StageCondition.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Pipelines.Runtime; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class StageCondition : GraphCondition - { - public StageCondition(String condition) - : base(condition) - { - } - - public ConditionResult Evaluate(StageExecutionContext context) - { - var traceWriter = new ConditionTraceWriter(); - var evaluationResult = m_parsedCondition.Evaluate(traceWriter, context.SecretMasker, context, context.ExpressionOptions); - return new ConditionResult() { Value = evaluationResult.IsTruthy, Trace = traceWriter.Trace }; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Step.cs b/src/Sdk/DTPipelines/Pipelines/Step.cs index 7fe27dca3..8c2492eaa 100644 --- a/src/Sdk/DTPipelines/Pipelines/Step.cs +++ b/src/Sdk/DTPipelines/Pipelines/Step.cs @@ -7,9 +7,6 @@ namespace GitHub.DistributedTask.Pipelines { [DataContract] [KnownType(typeof(ActionStep))] - [KnownType(typeof(TaskStep))] - [KnownType(typeof(TaskTemplateStep))] - [KnownType(typeof(GroupStep))] [JsonConverter(typeof(StepConverter))] [EditorBrowsable(EditorBrowsableState.Never)] public abstract class Step @@ -69,20 +66,7 @@ namespace GitHub.DistributedTask.Pipelines [EditorBrowsable(EditorBrowsableState.Never)] public enum StepType { - [DataMember] - Task = 1, - - [DataMember] - TaskTemplate = 2, - - [DataMember] - Group = 3, - [DataMember] Action = 4, - - [DataMember] - [Obsolete("Deprecated", false)] - Script = 5, } } diff --git a/src/Sdk/DTPipelines/Pipelines/StepConverter.cs b/src/Sdk/DTPipelines/Pipelines/StepConverter.cs index d617d50c6..c6b9ad559 100644 --- a/src/Sdk/DTPipelines/Pipelines/StepConverter.cs +++ b/src/Sdk/DTPipelines/Pipelines/StepConverter.cs @@ -22,9 +22,9 @@ namespace GitHub.DistributedTask.Pipelines } public override object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, + JsonReader reader, + Type objectType, + Object existingValue, JsonSerializer serializer) { if (reader.TokenType != JsonToken.StartObject) @@ -33,26 +33,7 @@ namespace GitHub.DistributedTask.Pipelines } JObject value = JObject.Load(reader); - if (!value.TryGetValue("Type", StringComparison.OrdinalIgnoreCase, out JToken stepTypeValue)) - { - Step compatStepObject; - if (value.TryGetValue("Parameters", StringComparison.OrdinalIgnoreCase, out _)) - { - compatStepObject = new TaskTemplateStep(); - } - else - { - compatStepObject = new TaskStep(); - } - - using (var objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, compatStepObject); - } - - return compatStepObject; - } - else + if (value.TryGetValue("Type", StringComparison.OrdinalIgnoreCase, out JToken stepTypeValue)) { StepType stepType; if (stepTypeValue.Type == JTokenType.Integer) @@ -70,18 +51,6 @@ namespace GitHub.DistributedTask.Pipelines case StepType.Action: stepObject = new ActionStep(); break; - - case StepType.Group: - stepObject = new GroupStep(); - break; - - case StepType.Task: - stepObject = new TaskStep(); - break; - - case StepType.TaskTemplate: - stepObject = new TaskTemplateStep(); - break; } using (var objectReader = value.CreateReader()) @@ -91,6 +60,10 @@ namespace GitHub.DistributedTask.Pipelines return stepObject; } + else + { + return null; + } } public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) diff --git a/src/Sdk/DTPipelines/Pipelines/StrategyResult.cs b/src/Sdk/DTPipelines/Pipelines/StrategyResult.cs deleted file mode 100644 index 9d7973e37..000000000 --- a/src/Sdk/DTPipelines/Pipelines/StrategyResult.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.Pipelines.ContextData; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class StrategyResult - { - public StrategyResult() - { - FailFast = true; - } - - public Boolean FailFast { get; set; } - - public int MaxParallel { get; set; } - - public IList Configurations { get; } = new List(); - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class StrategyConfiguration - { - public String DisplayName { get; set; } - - public String Name { get; set; } - - public IDictionary ContextData { get; } = new Dictionary(StringComparer.Ordinal); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskCondition.cs b/src/Sdk/DTPipelines/Pipelines/TaskCondition.cs deleted file mode 100644 index 4be8abd11..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskCondition.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.ComponentModel; -using System.Linq; -using System.Text; -using GitHub.DistributedTask.Expressions2; -using GitHub.DistributedTask.Expressions2.Sdk; -using GitHub.DistributedTask.Pipelines.Expressions; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class TaskCondition - { - public TaskCondition(String condition) - { - m_condition = condition ?? Default; - m_parser = new ExpressionParser(); - m_parsedCondition = m_parser.CreateTree(m_condition, new ConditionTraceWriter(), s_namedValueInfo, s_functionInfo); - m_requiresVariables = new Lazy(HasVariablesReference); - } - - /// - /// Gets the default condition if none is specified - /// - public static String Default - { - get - { - return "success()"; - } - } - - public Boolean RequiresVariables - { - get - { - return m_requiresVariables.Value; - } - } - - public ConditionResult Evaluate(JobExecutionContext context) - { - var traceWriter = new ConditionTraceWriter(); - var evaluationResult = m_parsedCondition.Evaluate(traceWriter, context.SecretMasker, context, context.ExpressionOptions); - return new ConditionResult() { Value = evaluationResult.IsTruthy, Trace = traceWriter.Trace }; - } - - private Boolean HasVariablesReference() - { - return false; - } - - private readonly String m_condition; - private readonly ExpressionParser m_parser; - private readonly IExpressionNode m_parsedCondition; - private readonly Lazy m_requiresVariables; - - private static readonly INamedValueInfo[] s_namedValueInfo = new INamedValueInfo[] - { - }; - - private static readonly IFunctionInfo[] s_functionInfo = new IFunctionInfo[] - { - new FunctionInfo("always", 0, 0), - new FunctionInfo("failure", 0, 0), - new FunctionInfo("cancelled", 0, 0), - new FunctionInfo("success", 0, 0), - }; - - private sealed class ConditionTraceWriter : ITraceWriter - { - public String Trace - { - get - { - return m_info.ToString(); - } - } - - public void Info(String message) - { - m_info.AppendLine(message); - } - - public void Verbose(String message) - { - // Not interested - } - - private StringBuilder m_info = new StringBuilder(); - } - - private sealed class AlwaysNode : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - return true; - } - } - - private sealed class CancelledNode : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var conditionContext = context.State as JobExecutionContext; - return conditionContext.State == PipelineState.Canceling; - } - } - - private sealed class FailureNode : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var executionContext = context.State as JobExecutionContext; - if (executionContext.State != PipelineState.InProgress) - { - return false; - } - - // The variable should always be set into the environment for a job - if (!executionContext.Variables.TryGetValue(WellKnownDistributedTaskVariables.JobStatus, out var value) || - !Enum.TryParse(value.Value, true, out var result)) - { - return false; - } - - return result == TaskResult.Failed; - } - } - - private sealed class SuccessNode : Function - { - protected override Object EvaluateCore( - EvaluationContext context, - out ResultMemory resultMemory) - { - resultMemory = null; - var executionContext = context.State as JobExecutionContext; - if (executionContext.State != PipelineState.InProgress) - { - return false; - } - - // The variable should always be set into the environment for a job - if (!executionContext.Variables.TryGetValue(WellKnownDistributedTaskVariables.JobStatus, out var value) || - !Enum.TryParse(value.Value, true, out var result)) - { - return false; - } - - return result == TaskResult.Succeeded || result == TaskResult.SucceededWithIssues; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskDefinitionExtensions.cs b/src/Sdk/DTPipelines/Pipelines/TaskDefinitionExtensions.cs deleted file mode 100644 index 5c68c5d97..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskDefinitionExtensions.cs +++ /dev/null @@ -1,70 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class TaskDefinitionExtensions - { - public static String ComputeDisplayName( - this TaskDefinition taskDefinition, - IDictionary inputs) - { - if (!String.IsNullOrEmpty(taskDefinition.InstanceNameFormat)) - { - return VariableUtility.ExpandVariables(taskDefinition.InstanceNameFormat, inputs); - } - else if (!String.IsNullOrEmpty(taskDefinition.FriendlyName)) - { - return taskDefinition.FriendlyName; - } - else - { - return taskDefinition.Name; - } - } - - /// - /// Returns the maximum of the two versions: the currentMinimum and the task's MinimumAgentVersion - /// - public static String GetMinimumAgentVersion( - this TaskDefinition taskDefinition, - String currentMinimum) - { - String minimumVersion; - - // If task.minAgentVersion > currentMin, this task needs a newer agent. So, return task.minAgentVersion - if (DemandMinimumVersion.CompareVersion(taskDefinition.MinimumAgentVersion, currentMinimum) > 0) - { - minimumVersion = taskDefinition.MinimumAgentVersion; - } - else - { - minimumVersion = currentMinimum; - } - - // If any of the task execution jobs requires Node10, return the minimum agent version that supports it - if (taskDefinition.RequiresNode10() && - DemandMinimumVersion.CompareVersion(s_node10MinAgentVersion, minimumVersion) > 0) - { - minimumVersion = s_node10MinAgentVersion; - } - - return minimumVersion; - } - - private static bool RequiresNode10( - this TaskDefinition taskDefinition) - { - return taskDefinition.PreJobExecution.Keys.Contains(s_node10, StringComparer.OrdinalIgnoreCase) || - taskDefinition.Execution.Keys.Contains(s_node10, StringComparer.OrdinalIgnoreCase) || - taskDefinition.PostJobExecution.Keys.Contains(s_node10, StringComparer.OrdinalIgnoreCase); - } - - private static string s_node10MinAgentVersion = "2.144.0"; - private static string s_node10 = "Node10"; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskStep.cs b/src/Sdk/DTPipelines/Pipelines/TaskStep.cs deleted file mode 100644 index 61be80b0f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskStep.cs +++ /dev/null @@ -1,177 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.ObjectTemplating.Tokens; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class TaskStep : JobStep - { - [JsonConstructor] - public TaskStep() - { - } - - internal TaskStep(TaskInstance legacyTaskInstance) - { - this.ContinueOnError = new BooleanToken(null, null, null, legacyTaskInstance.ContinueOnError); - this.DisplayName = legacyTaskInstance.DisplayName; - this.Enabled = legacyTaskInstance.Enabled; - this.Id = legacyTaskInstance.InstanceId; - this.Name = legacyTaskInstance.RefName; - this.TimeoutInMinutes = new NumberToken(null, null, null, legacyTaskInstance.TimeoutInMinutes); - this.Reference = new TaskStepDefinitionReference() - { - Id = legacyTaskInstance.Id, - Name = legacyTaskInstance.Name, - Version = legacyTaskInstance.Version - }; - - if (!String.IsNullOrEmpty(legacyTaskInstance.Condition)) - { - this.Condition = legacyTaskInstance.Condition; - } - else if (legacyTaskInstance.AlwaysRun) - { - this.Condition = "succeededOrFailed()"; - } - else - { - this.Condition = "succeeded()"; - } - - foreach (var input in legacyTaskInstance.Inputs) - { - this.Inputs[input.Key] = input.Value; - } - - foreach (var env in legacyTaskInstance.Environment) - { - this.Environment[env.Key] = env.Value; - } - } - - private TaskStep(TaskStep taskToClone) - : base(taskToClone) - { - this.Reference = taskToClone.Reference?.Clone(); - - if (taskToClone.m_environment?.Count > 0) - { - m_environment = new Dictionary(taskToClone.m_environment, StringComparer.OrdinalIgnoreCase); - } - - if (taskToClone.m_inputs?.Count > 0) - { - m_inputs = new Dictionary(taskToClone.m_inputs, StringComparer.OrdinalIgnoreCase); - } - } - - public override StepType Type => StepType.Task; - - [DataMember] - public TaskStepDefinitionReference Reference - { - get; - set; - } - - public IDictionary Environment - { - get - { - if (m_environment == null) - { - m_environment = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_environment; - } - } - - public IDictionary Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_inputs; - } - } - - public override Step Clone() - { - return new TaskStep(this); - } - - internal TaskInstance ToLegacyTaskInstance() - { - TaskInstance task = new TaskInstance() - { - AlwaysRun = String.Equals(this.Condition ?? String.Empty, "succeededOrFailed()", StringComparison.Ordinal), - Condition = this.Condition, - ContinueOnError = this.ContinueOnError?.AssertBoolean(null).Value ?? false, - DisplayName = this.DisplayName, - Enabled = this.Enabled, - InstanceId = this.Id, - RefName = this.Name, - TimeoutInMinutes = (Int32)(this.TimeoutInMinutes?.AssertNumber(null).Value ?? 0d), - Id = this.Reference.Id, - Name = this.Reference.Name, - Version = this.Reference.Version, - }; - - foreach (var env in this.Environment) - { - task.Environment[env.Key] = env.Value; - } - - foreach (var input in this.Inputs) - { - task.Inputs[input.Key] = input.Value; - } - - return task; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_environment?.Count == 0) - { - m_environment = null; - } - - if (m_inputs?.Count == 0) - { - m_inputs = null; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (m_environment != null) - { - m_environment = new Dictionary(m_environment, StringComparer.OrdinalIgnoreCase); - } - - if (m_inputs != null) - { - m_inputs = new Dictionary(m_inputs, StringComparer.OrdinalIgnoreCase); - } - } - - [DataMember(Name = "Environment", EmitDefaultValue = false)] - private IDictionary m_environment; - - [DataMember(Name = "Inputs", EmitDefaultValue = false)] - private IDictionary m_inputs; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskStepDefinitionReference.cs b/src/Sdk/DTPipelines/Pipelines/TaskStepDefinitionReference.cs deleted file mode 100644 index b58762acf..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskStepDefinitionReference.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.WebApi; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class TaskStepDefinitionReference : ITaskDefinitionReference - { - [JsonConstructor] - public TaskStepDefinitionReference() - { - } - - private TaskStepDefinitionReference(TaskStepDefinitionReference referenceToClone) - { - this.Id = referenceToClone.Id; - this.Name = referenceToClone.Name; - this.Version = referenceToClone.Version; - } - - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public String Version - { - get; - set; - } - - public TaskStepDefinitionReference Clone() - { - return new TaskStepDefinitionReference(this); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskStore.cs b/src/Sdk/DTPipelines/Pipelines/TaskStore.cs deleted file mode 100644 index ce27813a3..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskStore.cs +++ /dev/null @@ -1,214 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Pipelines.Artifacts; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechanism for efficient resolution of task specifications to specific versions of the tasks. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class TaskStore : ITaskStore - { - public TaskStore(params TaskDefinition[] tasks) - : this((IEnumerable)tasks) - { - } - - /// - /// Constructs a new TaskStore instance with the specified tasks. - /// - /// All tasks which should be made available for task resolution - public TaskStore( - IEnumerable tasks, - ITaskResolver resolver = null) - { - m_nameLookup = new Dictionary>>(StringComparer.OrdinalIgnoreCase); - m_tasks = new Dictionary>(); - Resolver = resolver; - - // Filter out legacy tasks with conflicting names. - // - // The PublishBuildArtifacts V0 task ID is different from PublishBuildArtifacts V1. - // Attempts to resolve the PublishBuildArtifacts task by name will result in name conflict. - // The PublishBuildArtfacts V0 task is not in use anymore. It can simply be removed from - // the list of tasks, and the naming conflict averted. - // - // Additional details: The PublishBuildArtifacts V0 split into two tasks: PublishBuildArtifacts V1 - // and CopyPublishBuildArtifacts V1. The CopyPublishBuildArtifacts V1 task retained the GUID and a - // new GUID was generated for PublishBuildArtifacts V0. The split happened before task-major-version-locking - // was implemented. Therefore, no definitions are using the old version. - tasks = WellKnownTaskDefinitions - .Concat(tasks?.Where(x => !(x.Id == s_publishBuildArtifacts_v0_ID && x.Version?.Major == 0)) ?? Enumerable.Empty()) - .ToList(); - - // Build a lookup of all task versions for a given task identifier - foreach (var task in tasks) - { - AddVersion(task); - } - - // Filter the tasks to the latest within each major version so we can provide a lookup by name - var latestTasksByMajorVersion = tasks.GroupBy(x => new { x.Id, x.Version.Major }).Select(x => x.OrderByDescending(y => y.Version).First()); - foreach (var task in latestTasksByMajorVersion) - { - // The name should never be null in production environments but just in case don't provide by-name lookup - // for tasks which don't provide one. - if (!String.IsNullOrEmpty(task.Name)) - { - // Add the name lookup. - IDictionary> tasksByIdLookup; - if (!m_nameLookup.TryGetValue(task.Name, out tasksByIdLookup)) - { - tasksByIdLookup = new Dictionary>(); - m_nameLookup.Add(task.Name, tasksByIdLookup); - } - - IList tasksById; - if (!tasksByIdLookup.TryGetValue(task.Id, out tasksById)) - { - tasksById = new List(); - tasksByIdLookup.Add(task.Id, tasksById); - } - - tasksById.Add(task); - - if (!String.IsNullOrEmpty(task.ContributionIdentifier)) - { - // Add the contribution-qualified-name lookup. - var qualifiedName = $"{task.ContributionIdentifier}.{task.Name}"; - if (!m_nameLookup.TryGetValue(qualifiedName, out tasksByIdLookup)) - { - tasksByIdLookup = new Dictionary>(); - m_nameLookup.Add(qualifiedName, tasksByIdLookup); - } - - if (!tasksByIdLookup.TryGetValue(task.Id, out tasksById)) - { - tasksById = new List(); - tasksByIdLookup.Add(task.Id, tasksById); - } - - tasksById.Add(task); - } - } - } - } - - public ITaskResolver Resolver - { - get; - } - - /// - /// Resolves a task from the store using the unqiue identifier and version. - /// - /// The unique identifier of the task - /// The version of the task which is desired - /// The closest matching task definition if found; otherwise, null - public TaskDefinition ResolveTask( - Guid taskId, - String versionSpec) - { - TaskDefinition task = null; - - // Treat missing version as "*" - if (String.IsNullOrEmpty(versionSpec)) - { - versionSpec = "*"; - } - - if (m_tasks.TryGetValue(taskId, out IDictionary tasks)) - { - var parsedSpec = TaskVersionSpec.Parse(versionSpec); - task = parsedSpec.Match(tasks.Values); - } - - // Read-thru on miss - if (task == null && Resolver != null) - { - task = Resolver.Resolve(taskId, versionSpec); - if (task != null) - { - AddVersion(task); - } - } - - return task; - } - - /// - /// Resolves a task from the store using the specified name and version. - /// - /// The name of the task - /// The version of the task which is desired - /// The closest matching task definition if found; otherwise, null - public TaskDefinition ResolveTask( - String name, - String versionSpec) - { - Guid taskIdentifier; - if (!Guid.TryParse(name, out taskIdentifier)) - { - IDictionary> nameLookup; - if (!m_nameLookup.TryGetValue(name, out nameLookup)) - { - return null; - } - - if (nameLookup.Count == 1) - { - // Exactly one task ID was resolved. - taskIdentifier = nameLookup.Keys.Single(); - } - else - { - // More than one task ID was resolved. - // Prefer in-the-box tasks over extension tasks. - var inTheBoxTaskIdentifiers = - nameLookup - .Where(pair => pair.Value.All(taskDefinition => String.IsNullOrEmpty(taskDefinition.ContributionIdentifier))) - .Select(pair => pair.Key) - .ToList(); - if (inTheBoxTaskIdentifiers.Count == 1) - { - taskIdentifier = inTheBoxTaskIdentifiers[0]; - } - else - { - // Otherwise, ambiguous. - throw new AmbiguousTaskSpecificationException(PipelineStrings.AmbiguousTaskSpecification(name, String.Join(", ", nameLookup.Keys))); - } - } - } - - return ResolveTask(taskIdentifier, versionSpec); - } - - private void AddVersion(TaskDefinition task) - { - IDictionary tasksByVersion; - if (!m_tasks.TryGetValue(task.Id, out tasksByVersion)) - { - tasksByVersion = new Dictionary(StringComparer.OrdinalIgnoreCase); - m_tasks.Add(task.Id, tasksByVersion); - } - - tasksByVersion[task.Version] = task; - } - - private IDictionary> m_tasks; - private IDictionary>> m_nameLookup; - - private static readonly Guid s_publishBuildArtifacts_v0_ID = new Guid("1d341bb0-2106-458c-8422-d00bcea6512a"); - - private static readonly TaskDefinition[] WellKnownTaskDefinitions = new[] - { - PipelineConstants.CheckoutTask, - PipelineArtifactConstants.DownloadTask, - }; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskTemplateReference.cs b/src/Sdk/DTPipelines/Pipelines/TaskTemplateReference.cs deleted file mode 100644 index 532867d20..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskTemplateReference.cs +++ /dev/null @@ -1,47 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class TaskTemplateReference - { - public TaskTemplateReference() - { - } - - private TaskTemplateReference(TaskTemplateReference referenceToClone) - { - this.Id = referenceToClone.Id; - this.Name = referenceToClone.Name; - this.Version = referenceToClone.Version; - } - - [DataMember(EmitDefaultValue = false)] - public Guid Id - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Version - { - get; - set; - } - - public TaskTemplateReference Clone() - { - return new TaskTemplateReference(this); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskTemplateStep.cs b/src/Sdk/DTPipelines/Pipelines/TaskTemplateStep.cs deleted file mode 100644 index 708d58455..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskTemplateStep.cs +++ /dev/null @@ -1,65 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class TaskTemplateStep : Step - { - public TaskTemplateStep() - { - } - - private TaskTemplateStep(TaskTemplateStep templateToClone) - : base(templateToClone) - { - this.Reference = templateToClone.Reference?.Clone(); - - if (templateToClone.m_parameters?.Count > 0) - { - m_parameters = new Dictionary(templateToClone.m_parameters, StringComparer.OrdinalIgnoreCase); - } - } - - public override StepType Type => StepType.TaskTemplate; - - public IDictionary Parameters - { - get - { - if (m_parameters == null) - { - m_parameters = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_parameters; - } - } - - [DataMember(EmitDefaultValue = false)] - public TaskTemplateReference Reference - { - get; - set; - } - - public override Step Clone() - { - return new TaskTemplateStep(this); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_parameters?.Count == 0) - { - m_parameters = null; - } - } - - [DataMember(Name = "Parameters", EmitDefaultValue = false)] - private IDictionary m_parameters; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TaskTemplateStore.cs b/src/Sdk/DTPipelines/Pipelines/TaskTemplateStore.cs deleted file mode 100644 index a48762ef7..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TaskTemplateStore.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class TaskTemplateStore : ITaskTemplateStore - { - public TaskTemplateStore(IList resolvers) - { - m_resolvers = new List(resolvers ?? Enumerable.Empty()); - } - - public void AddProvider(ITaskTemplateResolver resolver) - { - ArgumentUtility.CheckForNull(resolver, nameof(resolver)); - m_resolvers.Add(resolver); - } - - public IEnumerable ResolveTasks(TaskTemplateStep step) - { - var resolver = m_resolvers.FirstOrDefault(x => x.CanResolve(step.Reference)); - if (resolver == null) - { - throw new NotSupportedException(PipelineStrings.TaskTemplateNotSupported(step.Reference.Name, step.Reference.Version)); - } - - return resolver.ResolveTasks(step); - } - - private readonly IList m_resolvers; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/TimelineRecordIdGenerator.cs b/src/Sdk/DTPipelines/Pipelines/TimelineRecordIdGenerator.cs deleted file mode 100644 index b6a54e863..000000000 --- a/src/Sdk/DTPipelines/Pipelines/TimelineRecordIdGenerator.cs +++ /dev/null @@ -1,189 +0,0 @@ -using System; -using System.ComponentModel; -using System.Text; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public static class TimelineRecordIdGenerator - { - public static Guid GetId(String refName) - { - byte[] bytes = Encoding.BigEndianUnicode.GetBytes(refName); - var sha1ForNonSecretPurposes = new Sha1ForNonSecretPurposes(); - sha1ForNonSecretPurposes.Start(); - sha1ForNonSecretPurposes.Append(namespaceBytes); - sha1ForNonSecretPurposes.Append(bytes); - Array.Resize(ref bytes, 16); - sha1ForNonSecretPurposes.Finish(bytes); - bytes[7] = (byte)((bytes[7] & 15) | 80); - return new Guid(bytes); - } - - // Value of 'DistributedTask.Pipelines' encoded without the namespace bytes on the front - private static readonly byte[] namespaceBytes = new byte[] - { - 83, - 55, - 27, - 127, - 212, - 97, - 75, - 93, - 197, - 226, - 39, - 51, - 83, - 35, - 223, - 36 - }; - - private struct Sha1ForNonSecretPurposes - { - private long length; - - private uint[] w; - - private int pos; - - public void Start() - { - if (this.w == null) - { - this.w = new uint[85]; - } - this.length = 0L; - this.pos = 0; - this.w[80] = 1732584193u; - this.w[81] = 4023233417u; - this.w[82] = 2562383102u; - this.w[83] = 271733878u; - this.w[84] = 3285377520u; - } - - public void Append(byte input) - { - this.w[this.pos / 4] = (this.w[this.pos / 4] << 8 | (uint)input); - int arg_35_0 = 64; - int num = this.pos + 1; - this.pos = num; - if (arg_35_0 == num) - { - this.Drain(); - } - } - - public void Append(byte[] input) - { - for (int i = 0; i < input.Length; i++) - { - byte input2 = input[i]; - this.Append(input2); - } - } - - public void Finish(byte[] output) - { - long num = this.length + (long)(8 * this.pos); - this.Append(128); - while (this.pos != 56) - { - this.Append(0); - } - this.Append((byte)(num >> 56)); - this.Append((byte)(num >> 48)); - this.Append((byte)(num >> 40)); - this.Append((byte)(num >> 32)); - this.Append((byte)(num >> 24)); - this.Append((byte)(num >> 16)); - this.Append((byte)(num >> 8)); - this.Append((byte)num); - int num2 = (output.Length < 20) ? output.Length : 20; - for (int num3 = 0; num3 != num2; num3++) - { - uint num4 = this.w[80 + num3 / 4]; - output[num3] = (byte)(num4 >> 24); - this.w[80 + num3 / 4] = num4 << 8; - } - } - - private void Drain() - { - for (int num = 16; num != 80; num++) - { - this.w[num] = Rol1(this.w[num - 3] ^ this.w[num - 8] ^ this.w[num - 14] ^ this.w[num - 16]); - } - uint num2 = this.w[80]; - uint num3 = this.w[81]; - uint num4 = this.w[82]; - uint num5 = this.w[83]; - uint num6 = this.w[84]; - for (int num7 = 0; num7 != 20; num7++) - { - uint num8 = (num3 & num4) | (~num3 & num5); - uint num9 = Rol5(num2) + num8 + num6 + 1518500249u + this.w[num7]; - num6 = num5; - num5 = num4; - num4 = Rol30(num3); - num3 = num2; - num2 = num9; - } - for (int num10 = 20; num10 != 40; num10++) - { - uint num11 = num3 ^ num4 ^ num5; - uint num12 = Rol5(num2) + num11 + num6 + 1859775393u + this.w[num10]; - num6 = num5; - num5 = num4; - num4 = Rol30(num3); - num3 = num2; - num2 = num12; - } - for (int num13 = 40; num13 != 60; num13++) - { - uint num14 = (num3 & num4) | (num3 & num5) | (num4 & num5); - uint num15 = Rol5(num2) + num14 + num6 + 2400959708u + this.w[num13]; - num6 = num5; - num5 = num4; - num4 = Rol30(num3); - num3 = num2; - num2 = num15; - } - for (int num16 = 60; num16 != 80; num16++) - { - uint num17 = num3 ^ num4 ^ num5; - uint num18 = Rol5(num2) + num17 + num6 + 3395469782u + this.w[num16]; - num6 = num5; - num5 = num4; - num4 = Rol30(num3); - num3 = num2; - num2 = num18; - } - this.w[80] += num2; - this.w[81] += num3; - this.w[82] += num4; - this.w[83] += num5; - this.w[84] += num6; - this.length += 512L; - this.pos = 0; - } - - private static uint Rol1(uint input) - { - return input << 1 | input >> 31; - } - - private static uint Rol5(uint input) - { - return input << 5 | input >> 27; - } - - private static uint Rol30(uint input) - { - return input << 30 | input >> 2; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/GraphValidator.cs b/src/Sdk/DTPipelines/Pipelines/Validation/GraphValidator.cs deleted file mode 100644 index 8a1d7535f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/GraphValidator.cs +++ /dev/null @@ -1,186 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - internal static class GraphValidator - { - internal delegate String ErrorFormatter(String code, params Object[] values); - - internal static void Validate( - PipelineBuildContext context, - ValidationResult result, - Func getBaseRefName, - String graphName, - IList nodes, - ErrorFormatter formatError) where T : class, IGraphNode - { - var unnamedNodes = new List(); - var startingNodes = new List(); - var knownNames = new HashSet(StringComparer.OrdinalIgnoreCase); - Boolean hasDuplicateName = false; - foreach (var node in nodes) - { - if (!String.IsNullOrEmpty(node.Name)) - { - if (!NameValidation.IsValid(node.Name, context.BuildOptions.AllowHyphenNames)) - { - result.Errors.Add(new PipelineValidationError(PipelineConstants.NameInvalid, formatError(PipelineConstants.NameInvalid, graphName, node.Name))); - } - else if (!knownNames.Add(node.Name)) - { - hasDuplicateName = true; - result.Errors.Add(new PipelineValidationError(PipelineConstants.NameNotUnique, formatError(PipelineConstants.NameNotUnique, graphName, node.Name))); - } - } - else - { - unnamedNodes.Add(node); - } - - if (node.DependsOn.Count == 0) - { - startingNodes.Add(node); - } - } - - Int32 nodeCounter = 1; - foreach (var unnamedNode in unnamedNodes) - { - var candidateName = getBaseRefName(nodeCounter); - while (!knownNames.Add(candidateName)) - { - nodeCounter++; - candidateName = getBaseRefName(nodeCounter); - } - - nodeCounter++; - unnamedNode.Name = candidateName; - } - - // Now that we have generated default names we can validate and provide error messages - foreach (var node in nodes) - { - node.Validate(context, result); - } - - if (startingNodes.Count == 0) - { - result.Errors.Add(new PipelineValidationError(PipelineConstants.StartingPointNotFound, formatError(PipelineConstants.StartingPointNotFound, graphName))); - return; - } - - // Skip validating the graph if duplicate phase names - if (hasDuplicateName) - { - return; - } - - var nodesToVisit = new Queue(startingNodes); - var nodeLookup = nodes.ToDictionary(x => x.Name, StringComparer.OrdinalIgnoreCase); - var unsatisfiedDependencies = nodes.ToDictionary(x => x.Name, x => new List(x.DependsOn), StringComparer.OrdinalIgnoreCase); - var visitedNames = new HashSet(StringComparer.OrdinalIgnoreCase); - while (nodesToVisit.Count > 0) - { - var currentPhase = nodesToVisit.Dequeue(); - - visitedNames.Add(currentPhase.Name); - - // Now figure out which nodes would start as a result of this - foreach (var nodeState in unsatisfiedDependencies) - { - for (Int32 i = nodeState.Value.Count - 1; i >= 0; i--) - { - if (nodeState.Value[i].Equals(currentPhase.Name, StringComparison.OrdinalIgnoreCase)) - { - nodeState.Value.RemoveAt(i); - if (nodeState.Value.Count == 0) - { - nodesToVisit.Enqueue(nodeLookup[nodeState.Key]); - } - } - } - } - } - - // There are nodes which are never going to execute, which is generally caused by a cycle in the graph. - var unreachableNodeCount = nodes.Count - visitedNames.Count; - if (unreachableNodeCount > 0) - { - foreach (var unreachableNode in unsatisfiedDependencies.Where(x => x.Value.Count > 0)) - { - foreach (var unsatisifedDependency in unreachableNode.Value) - { - if (!nodeLookup.ContainsKey(unsatisifedDependency)) - { - result.Errors.Add(new PipelineValidationError(PipelineConstants.DependencyNotFound, formatError(PipelineConstants.DependencyNotFound, graphName, unreachableNode.Key, unsatisifedDependency))); - } - else - { - result.Errors.Add(new PipelineValidationError(PipelineConstants.GraphContainsCycle, formatError(PipelineConstants.GraphContainsCycle, graphName, unreachableNode.Key, unsatisifedDependency))); - } - } - } - } - } - - /// - /// Traverses a validated graph running a callback on each node in the order it would execute at runtime. - /// - /// The type of graph node - /// The full set of nodes in the graph - /// A callback which is invoked for each node as execution would begin - internal static void Traverse( - IList nodes, - Action> handleNode) where T : class, IGraphNode - { - var nodeLookup = nodes.ToDictionary(x => x.Name, x => new GraphTraversalState(x), StringComparer.OrdinalIgnoreCase); - var pendingNodes = nodes.ToDictionary(x => x.Name, x => new List(x.DependsOn), StringComparer.OrdinalIgnoreCase); - var nodesToVisit = new Queue>(nodes.Where(x => x.DependsOn.Count == 0).Select(x => new GraphTraversalState(x))); - while (nodesToVisit.Count > 0) - { - var currentNode = nodesToVisit.Dequeue(); - - // Invoke the callback on this node since it would execute next. The dependencies provided to the - // callback is a fully recursive set of all dependencies for context on how a node would execute - // at runtime. - handleNode(currentNode.Node, currentNode.Dependencies); - - // Now figure out which nodes would start as a result of this - foreach (var nodeState in pendingNodes) - { - for (Int32 i = nodeState.Value.Count - 1; i >= 0; i--) - { - if (nodeState.Value[i].Equals(currentNode.Node.Name, StringComparison.OrdinalIgnoreCase)) - { - nodeState.Value.RemoveAt(i); - - // Make sure we include the completed nodes recursive dependency set into the dependent - // node recursive dependency set for accurate hit detection. - var traversalState = nodeLookup[nodeState.Key]; - traversalState.Dependencies.Add(currentNode.Node.Name); - traversalState.Dependencies.UnionWith(currentNode.Dependencies); - - if (nodeState.Value.Count == 0) - { - nodesToVisit.Enqueue(traversalState); - } - } - } - } - } - } - - private class GraphTraversalState where T : class, IGraphNode - { - public GraphTraversalState(T node) - { - this.Node = node; - } - - public T Node { get; } - public ISet Dependencies { get; } = new HashSet(StringComparer.OrdinalIgnoreCase); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/IInputValidator.cs b/src/Sdk/DTPipelines/Pipelines/Validation/IInputValidator.cs deleted file mode 100644 index c517c740e..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/IInputValidator.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System.ComponentModel; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - /// - /// Provides a contract validators must implement to participate in input validation. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public interface IInputValidator - { - /// - /// Validates the input value using the provided context. - /// - /// The current input validation context - /// A result which indicates success or failure of the validation in addition to detailed reason on failure - InputValidationResult Validate(InputValidationContext context); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationContext.cs b/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationContext.cs deleted file mode 100644 index 61ce8c88a..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationContext.cs +++ /dev/null @@ -1,73 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Expressions; -using GitHub.DistributedTask.Logging; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - /// - /// Provides the necessary context for performing input value validation. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class InputValidationContext - { - /// - /// Gets or sets an expression which should be used to validate . - /// - [DataMember(EmitDefaultValue = false)] - public String Expression - { - get; - set; - } - - /// - /// Gets or sets a value indicating whether or not to evaluate the expression using . - /// - [DataMember(EmitDefaultValue = false)] - public Boolean Evaluate - { - get; - set; - } - - /// - /// Gets or sets the options used during expression evalation. - /// - public EvaluationOptions EvaluationOptions - { - get; - set; - } - - /// - /// Gets or sets the secret masker implementation. - /// - public ISecretMasker SecretMasker - { - get; - set; - } - - /// - /// Gets or sets the trace writer implementation. - /// - public ITraceWriter TraceWriter - { - get; - set; - } - - /// - /// Gets or sets the value which should be validated. - /// - [DataMember(EmitDefaultValue = false)] - public String Value - { - get; - set; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationResult.cs b/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationResult.cs deleted file mode 100644 index f7ce3ad0c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidationResult.cs +++ /dev/null @@ -1,43 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - /// - /// Provides information about the result of input validation. - /// - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class InputValidationResult - { - public InputValidationResult() - { - } - - /// - /// Gets or sets a value indicating whether or not the input value is valid. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IsValid - { - get; - set; - } - - /// - /// Gets or sets a value indicating a detailed reason the input value is not valid. - /// - [DataMember(EmitDefaultValue = false)] - public String Reason - { - get; - set; - } - - /// - /// Provides a convenience property to return successful validation results. - /// - public static readonly InputValidationResult Succeeded = new InputValidationResult { IsValid = true }; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidator.cs b/src/Sdk/DTPipelines/Pipelines/Validation/InputValidator.cs deleted file mode 100644 index 9cfe8ce73..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/InputValidator.cs +++ /dev/null @@ -1,44 +0,0 @@ -using System; -using System.ComponentModel; -using GitHub.DistributedTask.Expressions; -using GitHub.DistributedTask.Pipelines.Expressions; -using GitHub.DistributedTask.WebApi; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - /// - /// Provides n validator implementation for task inputs. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public class InputValidator : IInputValidator - { - public InputValidationResult Validate(InputValidationContext context) - { - if (String.IsNullOrEmpty(context.Expression)) - { - return InputValidationResult.Succeeded; - } - - var result = new InputValidationResult(); - try - { - var parser = new ExpressionParser(); - var tree = parser.CreateTree(context.Expression, context.TraceWriter, namedValues: InputValidationConstants.NamedValues, functions: InputValidationConstants.Functions); - if (context.Evaluate) - { - result.IsValid = tree.Evaluate(context.TraceWriter, context.SecretMasker, context, context.EvaluationOptions); - } - else - { - result.IsValid = true; - } - } - catch (Exception ex) when (ex is ParseException || ex is RegularExpressionInvalidOptionsException || ex is NotSupportedException) - { - result.Reason = ex.Message; - } - - return result; - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/ScriptTaskValidator.cs b/src/Sdk/DTPipelines/Pipelines/Validation/ScriptTaskValidator.cs deleted file mode 100644 index 52452096d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/ScriptTaskValidator.cs +++ /dev/null @@ -1,198 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Text.RegularExpressions; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - /// - /// Validates script tasks for bad tokens. For best performance, create one instance and reuse - this is - /// thread safe. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ScriptTaskValidator - { - /// - /// If supplied, combined with to form a single set of bad tokens. - /// - public ScriptTaskValidator(IBadTokenProvider clientTokenPrv = null) - { - var regexToMatch = new HashSet(RegexPatternComparer.Instance); - var tokenToMatch = new HashSet(StringComparer.OrdinalIgnoreCase); - - var tokenPrvs = new List(2) { BaseBadTokenProvider.Instance }; - if (clientTokenPrv != null) - { - tokenPrvs.Add(clientTokenPrv); - } - - foreach (IBadTokenProvider tokenPrv in tokenPrvs) - { - foreach (string pattern in tokenPrv.GetRegexPatternsToMatch()) - { - regexToMatch.Add( - new Regex(pattern, RegexOptions.Compiled, matchTimeout: TimeSpan.FromMilliseconds(100))); - } - - foreach (string staticToken in tokenPrv.GetStaticTokensToMatch()) - { - tokenToMatch.Add(staticToken); - } - } - - m_regexesToMatch = regexToMatch.ToArray(); - m_stringsToMatch = tokenToMatch.ToArray(); - } - - /// - /// Check a string for tokens containing "banned" patterns. This method is thread safe. - /// - public bool HasBadParamOrArgument( - string exeAndArgs, - out string matchedPattern, - out string matchedToken) - { - ArgumentUtility.CheckForNull(exeAndArgs, nameof(exeAndArgs)); - - string[] args = exeAndArgs.Split(); - - // Using for loops b/c they are measurably faster than foreach and this is n^2 - for (int i = 0; i < args.Length; i++) - { - string arg = args[i]; - - // Check static matches - for (int j = 0; j < m_stringsToMatch.Length; j++) - { - string toTest = m_stringsToMatch[j]; - if (arg.IndexOf(toTest, StringComparison.OrdinalIgnoreCase) >= 0) - { - matchedPattern = toTest; - matchedToken = arg; - - return true; - } - } - - // Check regexes - for (int j = 0; j < m_regexesToMatch.Length; j++) - { - Regex toTest = m_regexesToMatch[j]; - if (toTest.IsMatch(arg)) - { - matchedPattern = toTest.ToString(); - matchedToken = arg; - - return true; - } - } - } - - matchedPattern = null; - matchedToken = null; - return false; - } - - // These are arrays for max perf when enumerating/indexing - private readonly Regex[] m_regexesToMatch; - private readonly string[] m_stringsToMatch; - - public interface IBadTokenProvider - { - IEnumerable GetRegexPatternsToMatch(); - - IEnumerable GetStaticTokensToMatch(); - } - - /// - /// Static set of bad tokens we know about. - /// - private sealed class BaseBadTokenProvider : IBadTokenProvider - { - private BaseBadTokenProvider() - { - } - - public IEnumerable GetRegexPatternsToMatch() - { - // https://en.wikipedia.org/wiki/Base58 - const string base58charPattern = "[1-9a-km-zA-HJ-NP-Z]"; - - // We expect arguments to begin with whitespace (i.e. --config-option bla) or an = (i.e. - // --config-option=bla). If whitespace, we'll split the string so there is none to start. - const string beginTokenDelimiter = "(^|=)"; - - // We always expect arguments to end with whitespace, so any match will be the end of the string - const string endTokenDelimiter = "$"; - - string wrapInDelimeters(string argument) - { - return beginTokenDelimiter + argument + endTokenDelimiter; - } - - // Avoid patterns than can cause catastrophic backtracking for perf reasons - // https://www.regular-expressions.info/catastrophic.html - return new[] - { - // Monero wallets. See https://moneroaddress.org/ - // http://monero.wikia.com/wiki/Address_validation - wrapInDelimeters("4" + base58charPattern + "{94}"), - wrapInDelimeters("4" + base58charPattern + "{105}"), - - // Bitcoin wallets. See https://en.bitcoin.it/wiki/Address - // Starts with 1 or 3, total 33-35 base58 chars - wrapInDelimeters("[1-3]" + base58charPattern + "{32,34}"), - // Starts with bc[1-16], then 39(?) to 87 (90-3) base32 chars - // See: https://en.bitcoin.it/wiki/Bech32 - wrapInDelimeters("bc[0-9]{1,2}([0-9a-zA-Z]){39}"), - wrapInDelimeters("bc[0-9]{1,2}([0-9a-zA-Z]){59}"), - }; - } - - public IEnumerable GetStaticTokensToMatch() - { - return new[] - { - // Begin known mining pools - "xmr.suprnova.cc", - "MoneroOcean.stream", - "supportXMR.com", - "xmr.nanopool.org", - "monero.hashvault.pro", - "MoriaXMR.com", - "xmrpool.", - "minergate.com", - "viaxmr.com", - "xmr.suprnova.cc", - // End known mining pools - - // Probable mining argument - "--donate-level", - - // Other probable mining processes - "cpuminer", - "cryptonight", - "sgminer", - "xmrig", - "nheqminer" - }; - } - - public static readonly IBadTokenProvider Instance = new BaseBadTokenProvider(); - } - - private sealed class RegexPatternComparer : IEqualityComparer - { - private RegexPatternComparer() - { - } - - public bool Equals(Regex x, Regex y) => x.ToString() == y.ToString(); - public int GetHashCode(Regex obj) => obj.GetHashCode(); - - public static readonly IEqualityComparer Instance = new RegexPatternComparer(); - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Validation/ValidationResult.cs b/src/Sdk/DTPipelines/Pipelines/Validation/ValidationResult.cs deleted file mode 100644 index 00ed51cd9..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Validation/ValidationResult.cs +++ /dev/null @@ -1,110 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines.Validation -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class ValidationResult - { - public PipelineEnvironment Environment - { - get; - internal set; - } - - public IList Errors - { - get - { - if (m_errors == null) - { - m_errors = new List(); - } - return m_errors; - } - } - - public PipelineResources ReferencedResources - { - get - { - if (m_referencedResources == null) - { - m_referencedResources = new PipelineResources(); - } - return m_referencedResources; - } - } - - public PipelineResources UnauthorizedResources - { - get - { - if (m_unauthorizedResources == null) - { - m_unauthorizedResources = new PipelineResources(); - } - return m_unauthorizedResources; - } - } - - internal void AddQueueReference( - Int32 id, - String name) - { - if (id != 0) - { - this.ReferencedResources.Queues.Add(new AgentQueueReference { Id = id }); - } - else if (!String.IsNullOrEmpty(name)) - { - this.ReferencedResources.Queues.Add(new AgentQueueReference { Name = name }); - } - } - - internal void AddPoolReference( - Int32 id, - String name) - { - if (id != 0) - { - this.ReferencedResources.Pools.Add(new AgentPoolReference { Id = id }); - } - else if (!String.IsNullOrEmpty(name)) - { - this.ReferencedResources.Pools.Add(new AgentPoolReference { Name = name }); - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_errors?.Count == 0) - { - m_errors = null; - } - - if (m_referencedResources?.Count == 0) - { - m_referencedResources = null; - } - - if (m_unauthorizedResources?.Count == 0) - { - m_unauthorizedResources = null; - } - } - - [DataMember(Name = "Errors", EmitDefaultValue = false)] - private List m_errors; - - [DataMember(Name = "ReferencedResources", EmitDefaultValue = false)] - private PipelineResources m_referencedResources; - - [DataMember(Name = "UnauthorizedResources", EmitDefaultValue = false)] - private PipelineResources m_unauthorizedResources; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/Variable.cs b/src/Sdk/DTPipelines/Pipelines/Variable.cs deleted file mode 100644 index 6b99a0321..000000000 --- a/src/Sdk/DTPipelines/Pipelines/Variable.cs +++ /dev/null @@ -1,50 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class Variable : IVariable - { - public Variable() - { - } - - private Variable(Variable variableToClone) - { - this.Name = variableToClone.Name; - this.Secret = variableToClone.Secret; - this.Value = variableToClone.Value; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Secret - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Value - { - get; - set; - } - - public Variable Clone() - { - return new Variable(this); - } - - VariableType IVariable.Type => VariableType.Inline; - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/VariableGroupReference.cs b/src/Sdk/DTPipelines/Pipelines/VariableGroupReference.cs deleted file mode 100644 index 46e98b82f..000000000 --- a/src/Sdk/DTPipelines/Pipelines/VariableGroupReference.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class VariableGroupReference : ResourceReference, IVariable - { - public VariableGroupReference() - { - } - - private VariableGroupReference(VariableGroupReference referenceToCopy) - : base(referenceToCopy) - { - this.Id = referenceToCopy.Id; - this.GroupType = referenceToCopy.GroupType; - this.SecretStore = referenceToCopy.SecretStore?.Clone(); - } - - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String GroupType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public SecretStoreConfiguration SecretStore - { - get; - set; - } - - public VariableGroupReference Clone() - { - return new VariableGroupReference(this); - } - - public override String ToString() - { - return base.ToString() ?? this.Id.ToString(); - } - - [DataMember(Name = nameof(Type))] - VariableType IVariable.Type - { - get - { - return VariableType.Group; - } - } - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/VariableGroupStore.cs b/src/Sdk/DTPipelines/Pipelines/VariableGroupStore.cs deleted file mode 100644 index 3ea48d876..000000000 --- a/src/Sdk/DTPipelines/Pipelines/VariableGroupStore.cs +++ /dev/null @@ -1,187 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public class VariableGroupStore : IVariableGroupStore - { - public VariableGroupStore( - IList resources, - IVariableGroupResolver resolver = null, - params IVariableValueProvider[] valueProviders) - { - this.Resolver = resolver; - Add(resources?.ToArray()); - - if (valueProviders?.Length > 0) - { - m_valueProviders = new Dictionary(StringComparer.OrdinalIgnoreCase); - foreach (var valueProvider in valueProviders) - { - if (!m_valueProviders.TryAdd(valueProvider.GroupType, valueProvider)) - { - throw new ArgumentException($"Group type {valueProvider.GroupType} cannot have more than one provider", nameof(valueProviders)); - } - } - } - } - - /// - /// Get the variable group resolver configured for this store. - /// - public IVariableGroupResolver Resolver - { - get; - } - - public IList GetAuthorizedReferences() - { - return m_resourcesById.Values.Select(x => new VariableGroupReference { Id = x.Id }).ToList(); - } - - public VariableGroup Get(VariableGroupReference reference) - { - if (reference == null) - { - return null; - } - - var referenceId = reference.Id; - var referenceName = reference.Name?.Literal; - if (referenceId == 0 && String.IsNullOrEmpty(referenceName)) - { - return null; - } - - VariableGroup authorizedResource = null; - if (referenceId != 0) - { - if (m_resourcesById.TryGetValue(referenceId, out authorizedResource)) - { - return authorizedResource; - } - } - else if (!String.IsNullOrEmpty(referenceName)) - { - if (m_resourcesByName.TryGetValue(referenceName, out List matchingResources)) - { - if (matchingResources.Count > 1) - { - throw new AmbiguousResourceSpecificationException(PipelineStrings.AmbiguousVariableGroupSpecification(referenceName)); - } - - return matchingResources[0]; - } - } - - // If we have an authorizer then attempt to authorize the reference for use - authorizedResource = this.Resolver?.Resolve(reference); - if (authorizedResource != null) - { - Add(authorizedResource); - } - - return authorizedResource; - } - - public IList GetPreSteps( - IPipelineContext context, - IReadOnlyList steps) - { - if (context.ReferencedResources.VariableGroups.Count == 0) - { - return null; - } - - // If the environment version is 1 and it's a build context we should inject - if (context.EnvironmentVersion < 2 && context is PipelineExecutionContext) - { - return null; - } - - var newSteps = new List(); - foreach (var group in context.ReferencedResources.VariableGroups.Where(x => x.SecretStore != null && x.SecretStore.Keys.Count > 0)) - { - // Only inject a task if the provider supports task injection for the current context - var valueProvider = GetValueProvider(group); - if (valueProvider != null && !valueProvider.ShouldGetValues(context)) - { - newSteps.AddRangeIfRangeNotNull(valueProvider.GetSteps(context, group, group.SecretStore.Keys)); - } - } - - return newSteps; - } - - public Dictionary> GetPostTaskSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new Dictionary>(); - } - - public IList GetPostSteps( - IPipelineContext context, - IReadOnlyList steps) - { - return new List(); - } - - public Boolean ResolveStep( - IPipelineContext context, - JobStep step, - out IList resolvedSteps) - { - resolvedSteps = new List(); - return false; - } - - /// - /// Gets the value provider which may be used to retrieve values for the variable group from the data store. - /// - /// The target variable group - /// A provider suitable for retrieving values from the variable group - public IVariableValueProvider GetValueProvider(VariableGroupReference group) - { - if (m_valueProviders != null && m_valueProviders.TryGetValue(group.GroupType, out var valueProvider)) - { - return valueProvider; - } - return null; - } - - private void Add(params VariableGroup[] resources) - { - if (resources?.Length > 0) - { - foreach (var resource in resources) - { - if (m_resourcesById.TryGetValue(resource.Id, out _)) - { - continue; - } - - m_resourcesById.Add(resource.Id, resource); - - if (!m_resourcesByName.TryGetValue(resource.Name, out List resourcesByName)) - { - resourcesByName = new List(); - m_resourcesByName.Add(resource.Name, resourcesByName); - } - - resourcesByName.Add(resource); - } - } - } - - private readonly Dictionary m_valueProviders; - private readonly Dictionary m_resourcesById = new Dictionary(); - private readonly Dictionary> m_resourcesByName = new Dictionary>(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/VariablesDictionary.cs b/src/Sdk/DTPipelines/Pipelines/VariablesDictionary.cs deleted file mode 100644 index 71b6d170c..000000000 --- a/src/Sdk/DTPipelines/Pipelines/VariablesDictionary.cs +++ /dev/null @@ -1,355 +0,0 @@ -using System; -using System.Collections; -using System.Collections.Generic; -using System.Collections.ObjectModel; -using System.ComponentModel; -using System.Linq; -using GitHub.DistributedTask.WebApi; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.Pipelines -{ - /// - /// Provides a mechansim for modeling a variable dictionary as a simple string dictionary for expression - /// evaluation. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public sealed class VariablesDictionary : IDictionary, IDictionary - { - /// - /// Initializes a new VariablesDictionary instance with an empty variable set. - /// - public VariablesDictionary() - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - /// - /// Initializes a new VariablesDictionary instance using the specified dictionary for initialization. - /// - /// The source from which to copy - public VariablesDictionary(VariablesDictionary copyFrom) - : this(copyFrom, false) - { - } - - /// - /// Initializes a new VariablesDictionary instance using the specified dictionary for initialization. - /// - /// The source from which to copy - public VariablesDictionary(IDictionary copyFrom) - : this(copyFrom?.ToDictionary(x => x.Key, x => new VariableValue { Value = x.Value }, StringComparer.OrdinalIgnoreCase), false) - { - } - - /// - /// Initializes a new VariablesDictionary instance using the specified dictionary for initialization. - /// - /// The source from which to copy - public VariablesDictionary(IDictionary copyFrom) - : this(copyFrom, false) - { - } - - private VariablesDictionary( - IDictionary copyFrom, - Boolean readOnly) - { - ArgumentUtility.CheckForNull(copyFrom, nameof(copyFrom)); - - if (readOnly) - { - m_variables = new ReadOnlyDictionary(copyFrom); - } - else - { - m_variables = new Dictionary(copyFrom, StringComparer.OrdinalIgnoreCase); - } - } - - /// - /// Gets the set of secrets which were accessed. - /// - public HashSet SecretsAccessed - { - get - { - return m_secretsAccessed; - } - } - - public VariableValue this[String key] - { - get - { - if (!m_variables.TryGetValue(key, out VariableValue variableValue)) - { - throw new KeyNotFoundException(key); - } - - if (variableValue.IsSecret) - { - m_secretsAccessed.Add(key); - } - - return variableValue; - } - set - { - m_variables[key] = value; - } - } - - public ICollection Keys - { - get - { - return m_variables.Keys; - } - } - - public ICollection Values - { - get - { - return m_variables.Values; - } - } - - public Int32 Count - { - get - { - return m_variables.Count; - } - } - - public Boolean IsReadOnly - { - get - { - return m_variables.IsReadOnly; - } - } - - public void Add( - String key, - VariableValue value) - { - m_variables.Add(key, value); - } - - public void Add(KeyValuePair item) - { - m_variables.Add(item); - } - - public VariablesDictionary AsReadOnly() - { - if (m_variables.IsReadOnly) - { - return this; - } - - return new VariablesDictionary(m_variables, true); - } - - public void Clear() - { - m_variables.Clear(); - } - - public Boolean Contains(KeyValuePair item) - { - return m_variables.Contains(item); - } - - public Boolean ContainsKey(String key) - { - return m_variables.ContainsKey(key); - } - - public void CopyTo( - KeyValuePair[] array, - Int32 arrayIndex) - { - m_variables.CopyTo(array, arrayIndex); - } - - public IEnumerator> GetEnumerator() - { - return m_variables.GetEnumerator(); - } - - public Boolean Remove(String key) - { - return m_variables.Remove(key); - } - - public Boolean Remove(KeyValuePair item) - { - return m_variables.Remove(item); - } - - public Boolean TryGetValue( - String key, - out VariableValue value) - { - if (m_variables.TryGetValue(key, out value)) - { - if (value.IsSecret) - { - m_secretsAccessed.Add(key); - } - - return true; - } - - return false; - } - - ICollection IDictionary.Keys - { - get - { - return m_variables.Keys; - } - } - - ICollection IDictionary.Values - { - get - { - return m_variables.Select(x => x.Value?.Value).ToArray(); - } - } - - Int32 ICollection>.Count - { - get - { - return m_variables.Count; - } - } - - Boolean ICollection>.IsReadOnly - { - get - { - return m_variables.IsReadOnly; - } - } - - String IDictionary.this[String key] - { - get - { - if (!m_variables.TryGetValue(key, out VariableValue variableValue)) - { - throw new KeyNotFoundException(key); - } - - if (variableValue.IsSecret) - { - m_secretsAccessed.Add(key); - } - - return variableValue.Value; - } - set - { - if (!m_variables.TryGetValue(key, out VariableValue existingValue)) - { - m_variables.Add(key, value); - } - else - { - // Preserve whether or not this variable value is a secret - existingValue.Value = value; - } - } - } - - IEnumerator IEnumerable.GetEnumerator() - { - return m_variables.GetEnumerator(); - } - - IEnumerator> IEnumerable>.GetEnumerator() - { - foreach (var variable in m_variables) - { - yield return new KeyValuePair(variable.Key, variable.Value?.Value); - } - } - - Boolean IDictionary.TryGetValue( - String key, - out String value) - { - if (m_variables.TryGetValue(key, out VariableValue variableValue)) - { - if (variableValue.IsSecret) - { - m_secretsAccessed.Add(key); - } - - value = variableValue.Value; - return true; - } - - value = null; - return false; - } - - Boolean IDictionary.ContainsKey(String key) - { - return m_variables.ContainsKey(key); - } - - void IDictionary.Add( - String key, - String value) - { - m_variables.Add(key, value); - } - - Boolean IDictionary.Remove(String key) - { - return m_variables.Remove(key); - } - - void ICollection>.Add(KeyValuePair item) - { - m_variables.Add(new KeyValuePair(item.Key, item.Value)); - } - - void ICollection>.Clear() - { - m_variables.Clear(); - } - - Boolean ICollection>.Contains(KeyValuePair item) - { - return m_variables.Contains(new KeyValuePair(item.Key, item.Value)); - } - - void ICollection>.CopyTo( - KeyValuePair[] array, - Int32 arrayIndex) - { - foreach (var variable in m_variables) - { - array[arrayIndex++] = new KeyValuePair(variable.Key, variable.Value?.Value); - } - } - - Boolean ICollection>.Remove(KeyValuePair item) - { - return m_variables.Remove(new KeyValuePair(item.Key, item.Value)); - } - - private readonly HashSet m_secretsAccessed = new HashSet(StringComparer.OrdinalIgnoreCase); - private IDictionary m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } -} diff --git a/src/Sdk/DTPipelines/Pipelines/WorkspaceMapping.cs b/src/Sdk/DTPipelines/Pipelines/WorkspaceMapping.cs deleted file mode 100644 index fb193dd5d..000000000 --- a/src/Sdk/DTPipelines/Pipelines/WorkspaceMapping.cs +++ /dev/null @@ -1,71 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.Pipelines -{ - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public class WorkspaceMapping - { - /// - /// The map/cloak in tfvc. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean Exclude - { - get; - set; - } - - /// - /// The server path. - /// - [DataMember(EmitDefaultValue = false)] - public String ServerPath - { - get; - set; - } - - /// - /// The local path. - /// - [DataMember(EmitDefaultValue = false)] - public String LocalPath - { - get; - set; - } - - /// - /// The revision in svn. - /// - [DataMember(EmitDefaultValue = false)] - public String Revision - { - get; - set; - } - - /// - /// The depth in svn. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 Depth - { - get; - set; - } - - /// - /// Indicates whether to ignore externals in svn. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IgnoreExternals - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/AgentJobRequestMessage.cs b/src/Sdk/DTWebApi/WebApi/AgentJobRequestMessage.cs deleted file mode 100644 index 292e4077d..000000000 --- a/src/Sdk/DTWebApi/WebApi/AgentJobRequestMessage.cs +++ /dev/null @@ -1,79 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.ObjectModel; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - - public sealed class AgentJobRequestMessage : JobRequestMessage - { - [JsonConstructor] - internal AgentJobRequestMessage() : base(JobRequestMessageTypes.AgentJobRequest) - { - } - - public AgentJobRequestMessage( - TaskOrchestrationPlanReference plan, - TimelineReference timeline, - Guid jobId, - String jobName, - String jobRefName, - JobEnvironment environment, - IEnumerable tasks) - : base(JobRequestMessageTypes.AgentJobRequest, plan, timeline, jobId, jobName, jobRefName, environment) - { - m_tasks = new List(tasks); - } - - [DataMember] - public Int64 RequestId - { - get; - internal set; - } - - [DataMember] - public Guid LockToken - { - get; - internal set; - } - - [DataMember] - public DateTime LockedUntil - { - get; - internal set; - } - - public ReadOnlyCollection Tasks - { - get - { - if (m_tasks == null) - { - m_tasks = new List(); - } - return m_tasks.AsReadOnly(); - } - } - - public TaskAgentMessage GetAgentMessage() - { - var body = JsonUtility.ToString(this); - - return new TaskAgentMessage - { - Body = body, - MessageType = JobRequestMessageTypes.AgentJobRequest - }; - } - - [DataMember(Name = "Tasks", EmitDefaultValue = false)] - private List m_tasks; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/AuditAction.cs b/src/Sdk/DTWebApi/WebApi/AuditAction.cs deleted file mode 100644 index e133be9d2..000000000 --- a/src/Sdk/DTWebApi/WebApi/AuditAction.cs +++ /dev/null @@ -1,19 +0,0 @@ -namespace GitHub.DistributedTask.WebApi -{ - using System.Runtime.Serialization; - - public enum AuditAction - { - [EnumMember] - Add = 1, - - [EnumMember] - Update = 2, - - [EnumMember] - Delete = 3, - - [EnumMember] - Undelete = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableGroupProviderData.cs b/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableGroupProviderData.cs deleted file mode 100644 index 756d02326..000000000 --- a/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableGroupProviderData.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureKeyVaultVariableGroupProviderData : VariableGroupProviderData - { - [DataMember(EmitDefaultValue = true)] - public Guid ServiceEndpointId - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Vault - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime LastRefreshedOn - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableValue.cs b/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableValue.cs deleted file mode 100644 index 4bae3ac45..000000000 --- a/src/Sdk/DTWebApi/WebApi/AzureKeyVaultVariableValue.cs +++ /dev/null @@ -1,47 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureKeyVaultVariableValue: VariableValue - { - public AzureKeyVaultVariableValue() - { - } - - public AzureKeyVaultVariableValue(AzureKeyVaultVariableValue value) - : this(value.Value, value.IsSecret, value.Enabled, value.ContentType, value.Expires) - { - } - - public AzureKeyVaultVariableValue(String value, Boolean isSecret, Boolean enabled, String contentType, DateTime? expires) - :base(value, isSecret) - { - Enabled = enabled; - ContentType = contentType; - Expires = expires; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean Enabled - { - get; - set; - } - - [DataMember(EmitDefaultValue = true)] - public String ContentType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime? Expires - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Demand.cs b/src/Sdk/DTWebApi/WebApi/Demand.cs deleted file mode 100644 index 669fbff45..000000000 --- a/src/Sdk/DTWebApi/WebApi/Demand.cs +++ /dev/null @@ -1,103 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using System.Text.RegularExpressions; -using GitHub.Services.Common; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [JsonConverter(typeof(DemandJsonConverter))] - public abstract class Demand - { - protected Demand( - String name, - String value) - { - ArgumentUtility.CheckStringForNullOrEmpty(name, "name"); - this.Name = name; - this.Value = value; - } - - [DataMember] - public String Name - { - get; - private set; - } - - [DataMember(EmitDefaultValue = false)] - public String Value - { - get; - private set; - } - - public override sealed Boolean Equals(Object obj) - { - Demand demand = obj as Demand; - return demand != null && demand.ToString().Equals(this.ToString(), StringComparison.OrdinalIgnoreCase); - } - - public override sealed Int32 GetHashCode() - { - return this.ToString().ToUpperInvariant().GetHashCode(); - } - - public override sealed String ToString() - { - return GetExpression(); - } - - public abstract Demand Clone(); - - protected abstract String GetExpression(); - - public abstract Boolean IsSatisfied(IDictionary capabilities); - - public static Boolean TryParse( - String input, - out Demand demand) - { - demand = null; - - Match match = s_demandRegex.Match(input); - if (!match.Success) - { - return false; - } - - String name = match.Groups["name"].Value; - String opcode = match.Groups["opcode"].Value; - String value = match.Groups["value"].Value; - - if (String.IsNullOrEmpty(opcode)) - { - demand = new DemandExists(name); - } - else - { - switch (opcode) - { - case "equals": - demand = new DemandEquals(name, value); - break; - case "gtVersion": - demand = new DemandMinimumVersion(name, value); - break; - } - } - - return demand != null; - } - - public void Update(String value) - { - ArgumentUtility.CheckStringForNullOrEmpty(value, "value"); - this.Value = value; - } - - private static readonly Regex s_demandRegex = new Regex(@"^(?\S+)(\s+\-(?\S+)\s+(?.*))?$", RegexOptions.Compiled); - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DemandEquals.cs b/src/Sdk/DTWebApi/WebApi/DemandEquals.cs deleted file mode 100644 index a8da39e34..000000000 --- a/src/Sdk/DTWebApi/WebApi/DemandEquals.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Runtime.Serialization; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class DemandEquals : Demand - { - public DemandEquals( - String name, - String value) - : base(name, value) - { - ArgumentUtility.CheckStringForNullOrEmpty(value, "value"); - } - - public override Demand Clone() - { - return new DemandEquals(this.Name, this.Value); - } - - protected override String GetExpression() - { - return String.Format(CultureInfo.InvariantCulture, "{0} -equals {1}", this.Name, this.Value); - } - - public override Boolean IsSatisfied(IDictionary capabilities) - { - String value; - return capabilities.TryGetValue(this.Name, out value) && this.Value.Equals(value, StringComparison.OrdinalIgnoreCase); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DemandExists.cs b/src/Sdk/DTWebApi/WebApi/DemandExists.cs deleted file mode 100644 index 84a950c0f..000000000 --- a/src/Sdk/DTWebApi/WebApi/DemandExists.cs +++ /dev/null @@ -1,36 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class DemandExists : Demand - { - public DemandExists(String name) - : base(name, null) - { - } - - public override Demand Clone() - { - return new DemandExists(this.Name); - } - - protected override String GetExpression() - { - return this.Name; - } - - public override Boolean IsSatisfied(IDictionary capabilities) - { - return capabilities.ContainsKey(this.Name); - } - - public new void Update(String value) - { - // Exists can not override value - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DemandJsonConverter.cs b/src/Sdk/DTWebApi/WebApi/DemandJsonConverter.cs deleted file mode 100644 index 37c1e0211..000000000 --- a/src/Sdk/DTWebApi/WebApi/DemandJsonConverter.cs +++ /dev/null @@ -1,45 +0,0 @@ -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using System; -using System.Reflection; - -namespace GitHub.DistributedTask.WebApi -{ - internal sealed class DemandJsonConverter : VssSecureJsonConverter - { - public override Boolean CanConvert(Type objectType) - { - return typeof(Demand).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (existingValue == null && reader.TokenType == JsonToken.String) - { - Demand demand; - if (Demand.TryParse((String)reader.Value, out demand)) - { - existingValue = demand; - } - } - - return existingValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - base.WriteJson(writer, value, serializer); - if (value != null) - { - writer.WriteValue(value.ToString()); - } - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DemandMinimumVersion.cs b/src/Sdk/DTWebApi/WebApi/DemandMinimumVersion.cs deleted file mode 100644 index 4cac2b22f..000000000 --- a/src/Sdk/DTWebApi/WebApi/DemandMinimumVersion.cs +++ /dev/null @@ -1,127 +0,0 @@ -using GitHub.DistributedTask.Pipelines; -using GitHub.Services.Common; -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Linq; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class DemandMinimumVersion : Demand - { - public DemandMinimumVersion( - String name, - String value) - : base(name, value) - { - ArgumentUtility.CheckStringForNullOrEmpty(value, "value"); - } - - public override Demand Clone() - { - return new DemandMinimumVersion(this.Name, this.Value); - } - - protected override String GetExpression() - { - return String.Format(CultureInfo.InvariantCulture, "{0} -gtVersion {1}", this.Name, this.Value); - } - - public override Boolean IsSatisfied(IDictionary capabilities) - { - String value; - if (capabilities.TryGetValue(this.Name, out value)) - { - // return true if our version is less than or equal to the capability version from the agent - return CompareVersion(this.Value, value) <= 0; - } - - // same as capabilityVersion == null - return false; - } - - public static Int32 CompareVersion(String semanticVersion1, String semanticVersion2) - { - // compare == first - second (-1 means second is greater, 1 means first is greater, 0 means they are equal) - Version version1 = ParseVersion(semanticVersion1); - Version version2 = ParseVersion(semanticVersion2); - if (version1 == null && version2 == null) - { - // they are both null, so they are equal - return 0; - } - else if (version1 == null) - { - // version2 is greater - return -1; - } - else if (version2 == null) - { - // version1 is greater - return 1; - } - - return version1.CompareTo(version2); - } - - /// - /// Gets the minimum agent version demand from the specified set of demands. Agent version demands are removed - /// from the input set. - /// - /// The demands - /// The highest minimum version required based in the input set - public static DemandMinimumVersion MaxAndRemove(ISet demands) - { - DemandMinimumVersion minAgentVersion = null; - var demandsCopy = demands.Where(x => x.Name.Equals(PipelineConstants.AgentVersionDemandName, StringComparison.OrdinalIgnoreCase)).OfType().ToList(); - foreach (var demand in demandsCopy) - { - if (minAgentVersion == null || CompareVersion(demand.Value, minAgentVersion.Value) > 0) - { - minAgentVersion = demand; - } - - demands.Remove(demand); - } - - return minAgentVersion; - } - - public static DemandMinimumVersion Max(IEnumerable demands) - { - DemandMinimumVersion minAgentVersion = null; - foreach (var demand in demands.Where(x => x.Name.Equals(PipelineConstants.AgentVersionDemandName, StringComparison.OrdinalIgnoreCase)).OfType()) - { - if (minAgentVersion == null || CompareVersion(demand.Value, minAgentVersion.Value) > 0) - { - minAgentVersion = demand; - } - } - - return minAgentVersion; - } - - public static Version ParseVersion(String versionString) - { - Version version = null; - if (!String.IsNullOrEmpty(versionString)) - { - int index = versionString.IndexOf('-'); - if (index > 0) - { - versionString = versionString.Substring(0, index); - } - - if (!Version.TryParse(versionString, out version)) - { - // If we couldn't parse it, set it back to null - version = null; - } - } - - return version; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroup.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroup.cs deleted file mode 100644 index 29dc10085..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroup.cs +++ /dev/null @@ -1,83 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment group. - /// - [DataContract] - public class DeploymentGroup : DeploymentGroupReference - { - /// - /// Number of deployment targets in the deployment group. - /// - [DataMember] - public Int32 MachineCount - { - get; - internal set; - } - - /// - /// List of deployment targets in the deployment group. - /// - public IList Machines - { - get - { - if (m_machines == null) - { - m_machines = new List(); - } - return m_machines; - } - internal set - { - m_machines = value; - } - } - - /// - /// Description of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - /// - /// List of unique tags across all deployment targets in the deployment group. - /// - public IList MachineTags - { - get - { - if (m_tags == null) - { - m_tags = new List(); - } - return m_tags; - } - internal set - { - m_tags = value; - } - } - - /// - /// List of deployment targets in the deployment group. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Machines")] - private IList m_machines; - - /// - /// List of unique tags across all deployment targets in the deployment group. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "MachineTags")] - private IList m_tags; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupActionFilter.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupActionFilter.cs deleted file mode 100644 index dbd9d8bc6..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupActionFilter.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// This is useful in getting a list of deployment groups, filtered for which caller has permissions to take a particular action. - /// - [Flags] - [DataContract] - public enum DeploymentGroupActionFilter - { - /// - /// All deployment groups. - /// - [EnumMember] - None = 0, - - /// - /// Only deployment groups for which caller has **manage** permission. - /// - [EnumMember] - Manage = 2, - - /// - /// Only deployment groups for which caller has **use** permission. - /// - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupCreateParameter.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupCreateParameter.cs deleted file mode 100644 index 61ecb420c..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupCreateParameter.cs +++ /dev/null @@ -1,72 +0,0 @@ -using GitHub.Services.WebApi; -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to create Deployment group. - /// - [DataContract] - public class DeploymentGroupCreateParameter - { - /// - /// Name of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Description of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - /// - /// Identifier of the deployment pool in which deployment agents are registered. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 PoolId - { - get; - set; - } - - /// - /// Deployment pool in which deployment agents are registered. - /// This is obsolete. Kept for compatibility. Will be marked obsolete explicitly by M132. - /// - [DataMember(EmitDefaultValue = false)] - [ClientInternalUseOnly(OmitFromTypeScriptDeclareFile = false)] - public DeploymentGroupCreateParameterPoolProperty Pool - { - get; - set; - } - } - - /// - /// Properties of Deployment pool to create Deployment group. - /// - [DataContract] - public class DeploymentGroupCreateParameterPoolProperty - { - /// - /// Deployment pool identifier. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupExpands.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupExpands.cs deleted file mode 100644 index 37ca5c1fe..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupExpands.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to be included or expanded in deployment group objects. This is useful when getting a single or list of deployment grouops. - /// - [Flags] - [DataContract] - public enum DeploymentGroupExpands - { - /// - /// No additional properties. - /// - [EnumMember] - None = 0, - - /// - /// Deprecated: Include all the deployment targets. - /// - [EnumMember] - Machines = 2, - - /// - /// Include unique list of tags across all deployment targets. - /// - [EnumMember] - Tags = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupMetrics.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupMetrics.cs deleted file mode 100644 index 0efd3438e..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupMetrics.cs +++ /dev/null @@ -1,62 +0,0 @@ -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment group metrics. - /// - [DataContract] - public sealed class DeploymentGroupMetrics - { - /// - /// Deployment group. - /// - [DataMember] - public DeploymentGroupReference DeploymentGroup - { - get; - internal set; - } - - /// - /// List of deployment group properties. And types of metrics provided for those properties. - /// - [DataMember] - public MetricsColumnsHeader ColumnsHeader - { - get; - internal set; - } - - /// - /// Values of properties and the metrics. - /// E.g. 1: total count of deployment targets for which 'TargetState' is 'offline'. - /// E.g. 2: Average time of deployment to the deployment targets for which 'LastJobStatus' is 'passed' and 'TargetState' is 'online'. - /// - public IList Rows - { - get - { - if (m_rows == null) - { - m_rows = new List(); - } - - return m_rows; - } - internal set - { - m_rows = value; - } - } - - /// - /// Values of properties and the metrics. - /// E.g. 1: total count of deployment targets for which 'TargetState' is 'offline'. - /// E.g. 2: Average time of deployment to the deployment targets for which 'LastJobStatus' is 'passed' and 'TargetState' is 'online'. - /// - [DataMember(Name = "Rows")] - private IList m_rows; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupReference.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupReference.cs deleted file mode 100644 index bdd34601f..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupReference.cs +++ /dev/null @@ -1,90 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment group reference. This is useful for referring a deployment group in another object. - /// - [DataContract] - public class DeploymentGroupReference - { - [JsonConstructor] - public DeploymentGroupReference() - { - } - - private DeploymentGroupReference(DeploymentGroupReference referenceToClone) - { - this.Id = referenceToClone.Id; - this.Name = referenceToClone.Name; - - if (referenceToClone.Project != null) - { - this.Project = new ProjectReference - { - Id = referenceToClone.Project.Id, - Name = referenceToClone.Project.Name, - }; - } - - if (referenceToClone.Pool != null) - { - this.Pool = new TaskAgentPoolReference - { - Id = referenceToClone.Pool.Id, - IsHosted = referenceToClone.Pool.IsHosted, - Name = referenceToClone.Pool.Name, - PoolType = referenceToClone.Pool.PoolType, - Scope = referenceToClone.Pool.Scope, - }; - } - } - - /// - /// Deployment group identifier. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - internal set; - } - - /// - /// Project to which the deployment group belongs. - /// - [DataMember(EmitDefaultValue = false)] - public ProjectReference Project - { - get; - internal set; - } - - /// - /// Name of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Deployment pool in which deployment agents are registered. - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - - public virtual DeploymentGroupReference Clone() - { - return new DeploymentGroupReference(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentGroupUpdateParameter.cs b/src/Sdk/DTWebApi/WebApi/DeploymentGroupUpdateParameter.cs deleted file mode 100644 index be382a967..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentGroupUpdateParameter.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment group update parameter. - /// - [DataContract] - public class DeploymentGroupUpdateParameter - { - /// - /// Name of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Description of the deployment group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentMachine.cs b/src/Sdk/DTWebApi/WebApi/DeploymentMachine.cs deleted file mode 100644 index 786e2394a..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentMachine.cs +++ /dev/null @@ -1,99 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment target. - /// - [DataContract] - public class DeploymentMachine : ICloneable - { - public DeploymentMachine() - { - } - - private DeploymentMachine(DeploymentMachine machineToBeCloned) - { - this.Id = machineToBeCloned.Id; - this.Tags = (Tags == null) ? null : new List(machineToBeCloned.Tags); - this.Agent = machineToBeCloned.Agent?.Clone(); - } - - /// - /// Deployment target Identifier. - /// - [DataMember] - public Int32 Id - { - get; - set; - } - - /// - /// Tags of the deployment target. - /// - public IList Tags - { - get - { - return m_tags; - } - set - { - m_tags = value; - } - } - - /// - /// Deployment agent. - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgent Agent - { - get; - set; - } - - public PropertiesCollection Properties - { - get - { - if (m_properties == null) - { - m_properties = new PropertiesCollection(); - } - - return m_properties; - } - internal set - { - m_properties = value; - } - } - - object ICloneable.Clone() - { - return this.Clone(); - } - - public DeploymentMachine Clone() - { - return new DeploymentMachine(this); - } - - /// - /// Tags of the deployment target. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Tags")] - private IList m_tags; - - /// - /// Properties of the deployment target. - /// - [DataMember(EmitDefaultValue = false, Name = "Properties")] - private PropertiesCollection m_properties; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentMachineExpands.cs b/src/Sdk/DTWebApi/WebApi/DeploymentMachineExpands.cs deleted file mode 100644 index 732fac64a..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentMachineExpands.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [Flags] - [DataContract] - public enum DeploymentMachineExpands - { - [EnumMember] - None = 0, - - [EnumMember] - Capabilities = 2, - - [EnumMember] - AssignedRequest = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroup.cs b/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroup.cs deleted file mode 100644 index 5db57253b..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroup.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class DeploymentMachineGroup : DeploymentMachineGroupReference - { - [DataMember] - public Int32 Size - { - get; - internal set; - } - - public IList Machines - { - get - { - if (m_machines == null) - { - m_machines = new List(); - } - - return m_machines; - } - - internal set - { - m_machines = value; - } - } - - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Machines")] - private IList m_machines; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroupReference.cs b/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroupReference.cs deleted file mode 100644 index 8b1b05673..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentMachineGroupReference.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class DeploymentMachineGroupReference - { - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - internal set; - } - - [DataMember(EmitDefaultValue = false)] - public ProjectReference Project - { - get; - internal set; - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummary.cs b/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummary.cs deleted file mode 100644 index 4b2cdaab7..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummary.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment pool summary. - /// - [DataContract] - public sealed class DeploymentPoolSummary - { - /// - /// Deployment pool. - /// - [DataMember] - public TaskAgentPoolReference Pool - { - get; - internal set; - } - - /// - /// Number of deployment agents that are online. - /// - [DataMember] - public Int32 OnlineAgentsCount - { - get; - internal set; - } - - /// - /// Number of deployment agents that are offline. - /// - [DataMember] - public Int32 OfflineAgentsCount - { - get; - internal set; - } - - /// - /// Virtual machine Resource referring in pool. - /// - [DataMember] - public EnvironmentResourceReference Resource - { - get; - internal set; - } - - /// - /// List of deployment groups referring to the deployment pool. - /// - public IList DeploymentGroups - { - get - { - if (m_deploymentGroups == null) - { - m_deploymentGroups = new List(); - } - return m_deploymentGroups; - } - internal set - { - m_deploymentGroups = value; - } - } - - /// - /// List of deployment groups referring to the deployment pool. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "DeploymentGroups")] - private IList m_deploymentGroups; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummaryExpands.cs b/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummaryExpands.cs deleted file mode 100644 index 63586be3c..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentPoolSummaryExpands.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to be included or expanded in deployment pool summary objects. This is useful when getting a single or list of deployment pool summaries. - /// - [Flags] - [DataContract] - public enum DeploymentPoolSummaryExpands - { - /// - /// No additional properties - /// - [EnumMember] - None = 0, - - /// - /// Include deployment groups referring to the deployment pool. - /// - [EnumMember] - DeploymentGroups = 2, - - /// - /// Include Resource referring to the deployment pool. - /// - [EnumMember] - Resource = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentTargetExpands.cs b/src/Sdk/DTWebApi/WebApi/DeploymentTargetExpands.cs deleted file mode 100644 index a1b3e371e..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentTargetExpands.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to be included or expanded in deployment target objects. This is useful when getting a single or list of deployment targets. - /// - [Flags] - [DataContract] - public enum DeploymentTargetExpands - { - /// - /// No additional properties. - /// - [EnumMember] - None = 0, - - /// - /// Include capabilities of the deployment agent. - /// - [EnumMember] - Capabilities = 2, - - /// - /// Include the job request assigned to the deployment agent. - /// - [EnumMember] - AssignedRequest = 4, - - /// - /// Include the last completed job request of the deployment agent. - /// - [EnumMember] - LastCompletedRequest = 8 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/DeploymentTargetUpdateParameter.cs b/src/Sdk/DTWebApi/WebApi/DeploymentTargetUpdateParameter.cs deleted file mode 100644 index 8f2a4835f..000000000 --- a/src/Sdk/DTWebApi/WebApi/DeploymentTargetUpdateParameter.cs +++ /dev/null @@ -1,41 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Deployment target update parameter. - /// - [DataContract] - public class DeploymentTargetUpdateParameter - { - /// - /// Identifier of the deployment target. - /// - [DataMember] - public Int32 Id - { - get; - set; - } - - /// - /// Tags of the deployment target.. - /// - public IList Tags - { - get - { - return m_tags; - } - set - { - m_tags = value; - } - } - - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Tags")] - private IList m_tags; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/EnableAccessTokenType.cs b/src/Sdk/DTWebApi/WebApi/EnableAccessTokenType.cs deleted file mode 100644 index e1a8f6913..000000000 --- a/src/Sdk/DTWebApi/WebApi/EnableAccessTokenType.cs +++ /dev/null @@ -1,10 +0,0 @@ -namespace GitHub.DistributedTask.WebApi -{ - public enum EnableAccessTokenType - { - None, - Variable, - True = Variable, - SecretVariable, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentCreateParameter.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentCreateParameter.cs deleted file mode 100644 index 35085a396..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentCreateParameter.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to create Environment. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentCreateParameter - { - /// - /// Name of the environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Description of the environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentDeploymentExecutionRecord.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentDeploymentExecutionRecord.cs deleted file mode 100644 index b37da3949..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentDeploymentExecutionRecord.cs +++ /dev/null @@ -1,192 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// EnvironmentDeploymentExecutionRecord. - /// - [DataContract] - public class EnvironmentDeploymentExecutionRecord - { - /// - /// Id of the Environment deployment execution history record - /// - [DataMember] - public Int64 Id - { - get; - set; - } - - /// - /// Request identifier of the Environment deployment execution history record - /// - [DataMember] - public String RequestIdentifier - { - get; - set; - } - - /// - /// Id of the Environment - /// - [DataMember] - public Int32 EnvironmentId - { - get; - set; - } - - /// - /// Service owner Id - /// - [DataMember(EmitDefaultValue = false)] - public Guid ServiceOwner - { - get; - set; - } - - /// - /// Project Id - /// - [DataMember(EmitDefaultValue = false)] - public Guid ScopeId - { - get; - set; - } - - /// - /// Resource Id - /// - [DataMember(EmitDefaultValue = false)] - public Int32? ResourceId - { - get; - set; - } - - /// - /// Plan type of the environment deployment execution record - /// - [DataMember(EmitDefaultValue = false)] - public String PlanType - { - get; - set; - } - - /// - /// Plan Id - /// - [DataMember(EmitDefaultValue = false)] - public Guid PlanId - { - get; - set; - } - - /// - /// Stage name - /// - [DataMember(EmitDefaultValue = false)] - public String StageName - { - get; - set; - } - - /// - /// Job name - /// - [DataMember(EmitDefaultValue = false)] - public String JobName - { - get; - set; - } - - /// - /// Stage Attempt - /// - [DataMember(EmitDefaultValue = false)] - public Int32 StageAttempt - { - get; - set; - } - - /// - /// Job Attempt - /// - [DataMember(EmitDefaultValue = false)] - public Int32 JobAttempt - { - get; - set; - } - - /// - /// Definition of the environment deployment execution owner - /// - [DataMember(EmitDefaultValue = false)] - public TaskOrchestrationOwner Definition - { - get; - set; - } - - /// - /// Owner of the environment deployment execution record - /// - [DataMember(EmitDefaultValue = false)] - public TaskOrchestrationOwner Owner - { - get; - set; - } - - /// - /// Result of the environment deployment execution - /// - [DataMember(EmitDefaultValue = false)] - public TaskResult? Result - { - get; - set; - } - - /// - /// Queue time of the environment deployment execution - /// - [DataMember(EmitDefaultValue = false)] - public DateTime QueueTime - { - get; - set; - } - - /// - /// Start time of the environment deployment execution - /// - [DataMember(EmitDefaultValue = false)] - public DateTime? StartTime - { - get; - set; - } - - /// - /// Finish time of the environment deployment execution - /// - [DataMember(EmitDefaultValue = false)] - public DateTime? FinishTime - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentExpands.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentExpands.cs deleted file mode 100644 index e7bf1e795..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentExpands.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to be included or expanded in environment objects. This is useful when getting a single environment. - /// - [Flags] - [DataContract] - public enum EnvironmentExpands - { - /// - /// No additional properties - /// - [EnumMember] - None = 0, - - /// - /// Include resource references referring to the environment. - /// - [EnumMember] - ResourceReferences = 1 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentInstance.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentInstance.cs deleted file mode 100644 index 6fb071004..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentInstance.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Environment. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentInstance - { - /// - /// Id of the Environment - /// - [DataMember] - public Int32 Id - { - get; - set; - } - - /// - /// Name of the Environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Description of the Environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - /// - /// Identity reference of the user who created the Environment. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef CreatedBy - { - get; - set; - } - - /// - /// Creation time of the Environment - /// - [DataMember] - public DateTime CreatedOn - { - get; - set; - } - - /// - /// Identity reference of the user who last modified the Environment. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef LastModifiedBy - { - get; - set; - } - - /// - /// Last modified time of the Environment - /// - [DataMember] - public DateTime LastModifiedOn - { - get; - set; - } - - /// - /// List of resources - /// - public IList Resources - { - get - { - if (this.resources == null) - { - this.resources = new List(); - } - - return this.resources; - } - } - - /// - /// Resources that defined or used for this environment. - /// We use this for deployment job's resource authorization. - /// - public Pipelines.PipelineResources ReferencedResources - { - get; - set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Resources")] - private IList resources; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentLinkedResourceReference.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentLinkedResourceReference.cs deleted file mode 100644 index ddc8ffedb..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentLinkedResourceReference.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// EnvironmentLinkedResourceReference. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentLinkedResourceReference - { - /// - /// Id of the resource. - /// - [DataMember] - public String Id - { - get; - set; - } - - /// - /// Type of resource. - /// - [DataMember(EmitDefaultValue = false)] - public String TypeName - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentReference.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentReference.cs deleted file mode 100644 index 75b2012c4..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentReference.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentReference - { - [DataMember] - public Int32 Id { get; set; } - - [DataMember] - public String Name { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResource.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResource.cs deleted file mode 100644 index 89d9f2c94..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResource.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public abstract class EnvironmentResource - { - [DataMember] - public Int32 Id { get; set; } - - [DataMember] - public String Name { get; set; } - - /// - /// Environment resource type - /// - [DataMember] - public EnvironmentResourceType Type { get; set; } - - [DataMember] - public IdentityRef CreatedBy { get; set; } - - [DataMember] - public DateTime CreatedOn { get; set; } - - [DataMember] - public IdentityRef LastModifiedBy { get; set; } - - [DataMember] - public DateTime LastModifiedOn { get; set; } - - [DataMember] - public EnvironmentReference EnvironmentReference { get; set; } - - protected EnvironmentResource() - { - Name = string.Empty; - - CreatedBy = new IdentityRef(); - - LastModifiedBy = new IdentityRef(); - - this.EnvironmentReference = new EnvironmentReference(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceReference.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceReference.cs deleted file mode 100644 index d80266964..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceReference.cs +++ /dev/null @@ -1,63 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// EnvironmentResourceReference. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentResourceReference - { - /// - /// Id of the resource. - /// - [DataMember] - public Int32 Id - { - get; - set; - } - - /// - /// Name of the resource. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Type of the resource. - /// - [DataMember(EmitDefaultValue = false)] - public EnvironmentResourceType Type - { - get; - set; - } - - /// - /// List of linked resources - /// - public IList LinkedResources - { - get - { - if (m_linkedResources == null) - { - m_linkedResources = new List(); - } - - return m_linkedResources; - } - } - - private IList m_linkedResources; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceType.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceType.cs deleted file mode 100644 index 87d0be73d..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentResourceType.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.ComponentModel; - - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// EnvironmentResourceType. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [Flags] - public enum EnvironmentResourceType - { - Undefined = 0, - - /// - /// Unknown resource type - /// - Generic = 1, - - /// - /// Virtual machine resource type - /// - VirtualMachine = 2, - - /// - /// Kubernetes resource type - /// - Kubernetes = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentUpdateParameter.cs b/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentUpdateParameter.cs deleted file mode 100644 index 6fdf9fab8..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/EnvironmentUpdateParameter.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Properties to update Environment. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class EnvironmentUpdateParameter - { - /// - /// Name of the environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Description of the environment. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResource.cs b/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResource.cs deleted file mode 100644 index fc0cfee9c..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResource.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class KubernetesResource : EnvironmentResource - { - [DataMember] - public String Namespace { get; set; } - - [DataMember] - public String ClusterName { get; set; } - - [DataMember] - public Guid ServiceEndpointId { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResourceCreateParameters.cs b/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResourceCreateParameters.cs deleted file mode 100644 index c400258c7..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/KubernetesResourceCreateParameters.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class KubernetesResourceCreateParameters - { - [DataMember] - public String Name { get; set; } - - [DataMember] - public String Namespace { get; set; } - - [DataMember] - public String ClusterName { get; set; } - - [DataMember] - public Guid ServiceEndpointId { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachine.cs b/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachine.cs deleted file mode 100644 index 242096ece..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachine.cs +++ /dev/null @@ -1,41 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class VirtualMachine - { - [DataMember] - public Int32 Id { get; set; } - - [DataMember] - public TaskAgent Agent { get; set; } - - /// - /// List of tags - /// - public IList Tags - { - get - { - if (this.tags == null) - { - this.tags = new List(); - } - - return this.tags; - } - set - { - this.tags = value; - } - } - - [DataMember(IsRequired = false, EmitDefaultValue = false, Name = "Tags")] - private IList tags; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroup.cs b/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroup.cs deleted file mode 100644 index 040b7a7e0..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroup.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class VirtualMachineGroup : EnvironmentResource - { - [DataMember] - public Int32 PoolId { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroupCreateParameters.cs b/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroupCreateParameters.cs deleted file mode 100644 index 7a3bee5c1..000000000 --- a/src/Sdk/DTWebApi/WebApi/Environment/VirtualMachineGroupCreateParameters.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class VirtualMachineGroupCreateParameters - { - [DataMember] - public String Name { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ExpressionValidationItem.cs b/src/Sdk/DTWebApi/WebApi/ExpressionValidationItem.cs deleted file mode 100644 index 0a294e23b..000000000 --- a/src/Sdk/DTWebApi/WebApi/ExpressionValidationItem.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class ExpressionValidationItem : ValidationItem - { - public ExpressionValidationItem() - : base(InputValidationTypes.Expression) - { - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/IOrchestrationProcess.cs b/src/Sdk/DTWebApi/WebApi/IOrchestrationProcess.cs deleted file mode 100644 index 3fd813dc0..000000000 --- a/src/Sdk/DTWebApi/WebApi/IOrchestrationProcess.cs +++ /dev/null @@ -1,172 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Reflection; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Internal; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - [ClientIgnore] - [DataContract] - [EditorBrowsable(EditorBrowsableState.Never)] - public enum OrchestrationProcessType - { - [DataMember] - Container = 1, - - [DataMember] - Pipeline = 2, - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [JsonConverter(typeof(OrchestrationEnvironmentJsonConverter))] - public interface IOrchestrationEnvironment - { - OrchestrationProcessType ProcessType { get; } - - IDictionary Variables { get; } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [JsonConverter(typeof(OrchestrationProcessJsonConverter))] - public interface IOrchestrationProcess - { - OrchestrationProcessType ProcessType { get; } - } - - internal sealed class OrchestrationProcessJsonConverter : VssSecureJsonConverter - { - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(IOrchestrationProcess).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - JObject value = JObject.Load(reader); - IOrchestrationProcess process = null; - if (value.TryGetValue("stages", StringComparison.OrdinalIgnoreCase, out _) || - value.TryGetValue("phases", StringComparison.OrdinalIgnoreCase, out _)) - { - process = new PipelineProcess(); - } - else if (value.TryGetValue("children", StringComparison.OrdinalIgnoreCase, out _)) - { - process = new TaskOrchestrationContainer(); - } - - if (process != null) - { - using (var objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, process); - } - } - - return process; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } - - internal sealed class OrchestrationEnvironmentJsonConverter : VssSecureJsonConverter - { - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(IOrchestrationEnvironment).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - JToken propertyValue; - JObject value = JObject.Load(reader); - IOrchestrationEnvironment environment = null; - OrchestrationProcessType processType = OrchestrationProcessType.Container; - if (value.TryGetValue("ProcessType", StringComparison.OrdinalIgnoreCase, out propertyValue)) - { - if (propertyValue.Type == JTokenType.Integer) - { - processType = (OrchestrationProcessType)(Int32)propertyValue; - } - else if (propertyValue.Type != JTokenType.String || !Enum.TryParse((String)propertyValue, true, out processType)) - { - return null; - } - } - - switch (processType) - { - case OrchestrationProcessType.Container: - environment = new PlanEnvironment(); - break; - - case OrchestrationProcessType.Pipeline: - environment = new PipelineEnvironment(); - break; - } - - if (environment != null) - { - using (var objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, environment); - } - } - - return environment; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ITaskDefinitionReference.cs b/src/Sdk/DTWebApi/WebApi/ITaskDefinitionReference.cs deleted file mode 100644 index 4a70dffe2..000000000 --- a/src/Sdk/DTWebApi/WebApi/ITaskDefinitionReference.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - public interface ITaskDefinitionReference - { - Guid Id { get; } - - String Name { get; } - - String Version { get; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/IdentityRefExtensions.cs b/src/Sdk/DTWebApi/WebApi/IdentityRefExtensions.cs deleted file mode 100644 index 9813c0905..000000000 --- a/src/Sdk/DTWebApi/WebApi/IdentityRefExtensions.cs +++ /dev/null @@ -1,27 +0,0 @@ -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - internal static class IdentityRefExtensions - { - public static IdentityRef Clone(this IdentityRef source) - { - if (source == null) - { - return null; - } - - return new IdentityRef - { - DisplayName = source.DisplayName, - Id = source.Id, - ImageUrl = source.ImageUrl, - IsAadIdentity = source.IsAadIdentity, - IsContainer = source.IsContainer, - ProfileUrl = source.ProfileUrl, - UniqueName = source.UniqueName, - Url = source.Url, - }; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/InputBindingContext.cs b/src/Sdk/DTWebApi/WebApi/InputBindingContext.cs deleted file mode 100644 index 694b6cdf7..000000000 --- a/src/Sdk/DTWebApi/WebApi/InputBindingContext.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class InputBindingContext - { - /// - /// Value of the input - /// - [DataMember(EmitDefaultValue = false)] - public String Value - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/InputValidationItem.cs b/src/Sdk/DTWebApi/WebApi/InputValidationItem.cs deleted file mode 100644 index acb5a72bf..000000000 --- a/src/Sdk/DTWebApi/WebApi/InputValidationItem.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class InputValidationItem : ValidationItem - { - public InputValidationItem() - : base(InputValidationTypes.Input) - { - } - - /// - /// Provides binding context for the expression to evaluate - /// - [DataMember(EmitDefaultValue = false)] - public InputBindingContext Context - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobEnvironment.cs b/src/Sdk/DTWebApi/WebApi/JobEnvironment.cs deleted file mode 100644 index a0ba24ffb..000000000 --- a/src/Sdk/DTWebApi/WebApi/JobEnvironment.cs +++ /dev/null @@ -1,294 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Represents the context of variables and vectors for a job request. - /// - [DataContract] - public sealed class JobEnvironment : ICloneable - { - /// - /// Initializes a new JobEnvironment with empty collections of repositories, vectors, - /// and variables. - /// - public JobEnvironment() - { - } - - public JobEnvironment( - IDictionary variables, - List maskhints, - JobResources resources) - { - if (resources!= null) - { - this.Endpoints.AddRange(resources.Endpoints.Where(x => !String.Equals(x.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase))); - this.SystemConnection = resources.Endpoints.FirstOrDefault(x => String.Equals(x.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase)); - this.SecureFiles.AddRange(resources.SecureFiles); - } - - if (maskhints != null) - { - this.MaskHints.AddRange(maskhints); - } - - if (variables != null) - { - foreach (var variable in variables) - { - this.Variables[variable.Key] = variable.Value?.Value; - - if (variable.Value?.IsSecret == true) - { - // Make sure we propagate secret variables into the mask hints - this.MaskHints.Add(new MaskHint { Type = MaskType.Variable, Value = variable.Key }); - } - } - } - } - - public void Extract( - Dictionary variables, - HashSet maskhints, - JobResources jobResources) - { - // construct variables - HashSet secretVariables = new HashSet(this.MaskHints.Where(t => t.Type == MaskType.Variable).Select(v => v.Value), StringComparer.OrdinalIgnoreCase); - foreach (var variable in this.Variables) - { - variables[variable.Key] = new VariableValue(variable.Value, secretVariables.Contains(variable.Key)); - } - - // construct maskhints - maskhints.AddRange(this.MaskHints.Where(x => !(x.Type == MaskType.Variable && secretVariables.Contains(x.Value))).Select(x => x.Clone())); - - // constuct job resources (endpoints, securefiles and systemconnection) - jobResources.SecureFiles.AddRange(this.SecureFiles.Select(x => x.Clone())); - jobResources.Endpoints.AddRange(this.Endpoints.Select(x => x.Clone())); - - if (this.SystemConnection != null) - { - jobResources.Endpoints.Add(this.SystemConnection.Clone()); - } - } - - public JobEnvironment(PlanEnvironment environment) - { - ArgumentUtility.CheckForNull(environment, nameof(environment)); - - if (environment.MaskHints.Count > 0) - { - m_maskHints = new List(environment.MaskHints.Select(x => x.Clone())); - } - - if (environment.Options.Count > 0) - { - m_options = environment.Options.ToDictionary(x => x.Key, x => x.Value.Clone()); - } - - if (environment.Variables.Count > 0) - { - m_variables = new Dictionary(environment.Variables, StringComparer.OrdinalIgnoreCase); - } - } - - private JobEnvironment(JobEnvironment environmentToClone) - { - if (environmentToClone.SystemConnection != null) - { - this.SystemConnection = environmentToClone.SystemConnection.Clone(); - } - - if (environmentToClone.m_maskHints != null) - { - m_maskHints = environmentToClone.m_maskHints.Select(x => x.Clone()).ToList(); - } - - if (environmentToClone.m_endpoints != null) - { - m_endpoints = environmentToClone.m_endpoints.Select(x => x.Clone()).ToList(); - } - - if (environmentToClone.m_secureFiles != null) - { - m_secureFiles = environmentToClone.m_secureFiles.Select(x => x.Clone()).ToList(); - } - - if (environmentToClone.m_options != null) - { - m_options = environmentToClone.m_options.ToDictionary(x => x.Key, x => x.Value.Clone()); - } - - if (environmentToClone.m_variables != null) - { - m_variables = new Dictionary(environmentToClone.m_variables, StringComparer.OrdinalIgnoreCase); - } - } - - /// - /// Gets or sets the endpoint used for communicating back to the calling service. - /// - [DataMember(EmitDefaultValue = false)] - public ServiceEndpoint SystemConnection - { - get; - set; - } - - /// - /// Gets the collection of mask hints - /// - public List MaskHints - { - get - { - if (m_maskHints == null) - { - m_maskHints = new List(); - } - return m_maskHints; - } - } - - /// - /// Gets the collection of endpoints associated with the current context. - /// - public List Endpoints - { - get - { - if (m_endpoints == null) - { - m_endpoints = new List(); - } - return m_endpoints; - } - } - - /// - /// Gets the collection of secure files associated with the current context - /// - public List SecureFiles - { - get - { - if (m_secureFiles == null) - { - m_secureFiles = new List(); - } - return m_secureFiles; - } - } - - /// - /// Gets the collection of options associated with the current context. (Deprecated, use by 1.x agent) - /// - public IDictionary Options - { - get - { - if (m_options == null) - { - m_options = new Dictionary(); - } - return m_options; - } - } - - /// - /// Gets the collection of variables associated with the current context. - /// - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_variables; - } - } - - Object ICloneable.Clone() - { - return this.Clone(); - } - - /// - /// Creates a deep copy of the job environment. - /// - /// A deep copy of the job environment - public JobEnvironment Clone() - { - return new JobEnvironment(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (m_serializedMaskHints != null && m_serializedMaskHints.Count > 0) - { - m_maskHints = new List(m_serializedMaskHints.Distinct()); - } - - m_serializedMaskHints = null; - - SerializationHelper.Copy(ref m_serializedVariables, ref m_variables, true); - SerializationHelper.Copy(ref m_serializedEndpoints, ref m_endpoints, true); - SerializationHelper.Copy(ref m_serializedSecureFiles, ref m_secureFiles, true); - SerializationHelper.Copy(ref m_serializedOptions, ref m_options, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (this.m_maskHints != null && this.m_maskHints.Count > 0) - { - m_serializedMaskHints = new List(this.m_maskHints.Distinct()); - } - - SerializationHelper.Copy(ref m_variables, ref m_serializedVariables); - SerializationHelper.Copy(ref m_endpoints, ref m_serializedEndpoints); - SerializationHelper.Copy(ref m_secureFiles, ref m_serializedSecureFiles); - SerializationHelper.Copy(ref m_options, ref m_serializedOptions); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedMaskHints = null; - m_serializedVariables = null; - m_serializedEndpoints = null; - m_serializedSecureFiles = null; - m_serializedOptions = null; - } - - private List m_maskHints; - private List m_endpoints; - private List m_secureFiles; - private IDictionary m_options; - private IDictionary m_variables; - - [DataMember(Name = "Endpoints", EmitDefaultValue = false)] - private List m_serializedEndpoints; - - [DataMember(Name = "SecureFiles", EmitDefaultValue = false)] - private List m_serializedSecureFiles; - - [DataMember(Name = "Options", EmitDefaultValue = false)] - private IDictionary m_serializedOptions; - - [DataMember(Name = "Mask", EmitDefaultValue = false)] - private List m_serializedMaskHints; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private IDictionary m_serializedVariables; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobEvent.cs b/src/Sdk/DTWebApi/WebApi/JobEvent.cs index b17e44493..3bfbdd53b 100644 --- a/src/Sdk/DTWebApi/WebApi/JobEvent.cs +++ b/src/Sdk/DTWebApi/WebApi/JobEvent.cs @@ -16,22 +16,12 @@ namespace GitHub.DistributedTask.WebApi public const String JobCompleted = "JobCompleted"; public const String JobStarted = "JobStarted"; - - public const String TaskAssigned = "TaskAssigned"; - - public const String TaskStarted = "TaskStarted"; - - public const String TaskCompleted = "TaskCompleted"; } [DataContract] [KnownType(typeof(JobAssignedEvent))] [KnownType(typeof(JobCompletedEvent))] [KnownType(typeof(JobStartedEvent))] - [KnownType(typeof(TaskAssignedEvent))] - [KnownType(typeof(TaskStartedEvent))] - [KnownType(typeof(TaskCompletedEvent))] - [KnownType(typeof(TaskLocalExecutionCompletedEvent))] [JsonConverter(typeof(JobEventJsonConverter))] public abstract class JobEvent { @@ -179,89 +169,6 @@ namespace GitHub.DistributedTask.WebApi } } - [DataContract] - public sealed class TaskAssignedEvent : TaskEvent - { - public TaskAssignedEvent() - : base(JobEventTypes.TaskAssigned) - { - } - - public TaskAssignedEvent( - Guid jobId, - Guid taskId) - : base(JobEventTypes.TaskAssigned, jobId, taskId) - { - } - } - - [DataContract] - public sealed class TaskStartedEvent : TaskEvent - { - public TaskStartedEvent() - : base(JobEventTypes.TaskStarted) - { - } - - public TaskStartedEvent( - Guid jobId, - Guid taskId) - : base(JobEventTypes.TaskStarted, jobId, taskId) - { - } - } - - [DataContract] - public sealed class TaskCompletedEvent : TaskEvent - { - public TaskCompletedEvent() - : base(JobEventTypes.TaskCompleted) - { - } - - public TaskCompletedEvent( - Guid jobId, - Guid taskId, - TaskResult taskResult) - : base(JobEventTypes.TaskCompleted, jobId, taskId) - { - Result = taskResult; - } - - [DataMember] - public TaskResult Result - { - get; - set; - } - } - - [DataContract] - [ClientIgnore] - internal sealed class TaskLocalExecutionCompletedEvent : TaskEvent - { - public TaskLocalExecutionCompletedEvent() - : base(JobEventTypes.TaskCompleted) - { - } - - public TaskLocalExecutionCompletedEvent( - Guid jobId, - Guid taskId, - ServerTaskSectionExecutionOutput data) - : base(JobEventTypes.TaskCompleted, jobId, taskId) - { - EventData = data; - } - - [DataMember] - public ServerTaskSectionExecutionOutput EventData - { - get; - set; - } - } - internal sealed class JobEventJsonConverter : VssSecureJsonConverter { public override Boolean CanWrite @@ -304,18 +211,6 @@ namespace GitHub.DistributedTask.WebApi { jobEvent = new JobStartedEvent(); } - else if (String.Equals(nameValue, JobEventTypes.TaskAssigned, StringComparison.Ordinal)) - { - jobEvent = new TaskAssignedEvent(); - } - else if (String.Equals(nameValue, JobEventTypes.TaskStarted, StringComparison.Ordinal)) - { - jobEvent = new TaskStartedEvent(); - } - else if (String.Equals(nameValue, JobEventTypes.TaskCompleted, StringComparison.Ordinal)) - { - jobEvent = new TaskCompletedEvent(); - } } } diff --git a/src/Sdk/DTWebApi/WebApi/JobExecutionModeTypes.cs b/src/Sdk/DTWebApi/WebApi/JobExecutionModeTypes.cs deleted file mode 100644 index 911da471a..000000000 --- a/src/Sdk/DTWebApi/WebApi/JobExecutionModeTypes.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.WebApi -{ - public class JobExecutionModeTypes - { - public const string Server = "Server"; - - public const string Agent = "Agent"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobOption.cs b/src/Sdk/DTWebApi/WebApi/JobOption.cs deleted file mode 100644 index 36c7b4276..000000000 --- a/src/Sdk/DTWebApi/WebApi/JobOption.cs +++ /dev/null @@ -1,87 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Represents an option that may affect the way an agent runs the job. - /// - [DataContract] - public class JobOption : ICloneable - { - /// - /// Initializes a new JobOption with an empty collection of data. - /// - public JobOption() - { - } - - private JobOption(JobOption optionToClone) - { - this.Id = optionToClone.Id; - - if (optionToClone.m_data != null) - { - m_data = new Dictionary(optionToClone.m_data, StringComparer.OrdinalIgnoreCase); - } - } - - /// - /// Gets the id of the option. - /// - [DataMember] - public Guid Id { get; set; } - - /// - /// Gets the data associated with the option. - /// - public IDictionary Data - { - get - { - if (m_data == null) - { - m_data = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_data; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - if (m_serializedData != null && m_serializedData.Count > 0) - { - m_data = new Dictionary(m_serializedData, StringComparer.OrdinalIgnoreCase); - } - - m_serializedData = null; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - m_serializedData = this.Data.Count > 0 ? this.Data : null; - } - - Object ICloneable.Clone() - { - return this.Clone(); - } - - /// - /// Creates a deep copy of the job option. - /// - /// A deep copy of the job option - public JobOption Clone() - { - return new JobOption(this); - } - - private Dictionary m_data; - - [DataMember(Name = "Data", EmitDefaultValue = false)] - private IDictionary m_serializedData; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobRequestMessage.cs b/src/Sdk/DTWebApi/WebApi/JobRequestMessage.cs deleted file mode 100644 index 4f0098178..000000000 --- a/src/Sdk/DTWebApi/WebApi/JobRequestMessage.cs +++ /dev/null @@ -1,86 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Collections.ObjectModel; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [JsonConverter(typeof(JobRequestMessageJsonConverter))] - - public abstract class JobRequestMessage - { - protected JobRequestMessage(string messageType) - { - this.MessageType = messageType; - } - - protected JobRequestMessage( - string messageType, - TaskOrchestrationPlanReference plan, - TimelineReference timeline, - Guid jobId, - String jobName, - String jobRefName, - JobEnvironment environment) - { - this.MessageType = messageType; - this.Plan = plan; - this.JobId = jobId; - this.JobName = jobName; - this.JobRefName = jobRefName; - this.Timeline = timeline; - this.Environment = environment; - } - - [DataMember] - public String MessageType - { - get; - private set; - } - - [DataMember] - public TaskOrchestrationPlanReference Plan - { - get; - private set; - } - - [DataMember] - public TimelineReference Timeline - { - get; - private set; - } - - [DataMember] - public Guid JobId - { - get; - private set; - } - - [DataMember] - public String JobName - { - get; - private set; - } - - [DataMember] - public String JobRefName - { - get; - private set; - } - - [DataMember] - public JobEnvironment Environment - { - get; - private set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobRequestMessageJsonConverter.cs b/src/Sdk/DTWebApi/WebApi/JobRequestMessageJsonConverter.cs deleted file mode 100644 index d1810d7b5..000000000 --- a/src/Sdk/DTWebApi/WebApi/JobRequestMessageJsonConverter.cs +++ /dev/null @@ -1,89 +0,0 @@ -using System; -using System.Reflection; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - internal sealed class JobRequestMessageJsonConverter : VssSecureJsonConverter - { - public override Boolean CanConvert(Type objectType) - { - return typeof(JobRequestMessage).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - Object newValue = null; - JToken propertyValue; - JObject value = JObject.Load(reader); - - if (value.TryGetValue("MessageType", StringComparison.OrdinalIgnoreCase, out propertyValue)) - { - if (propertyValue.Type == JTokenType.String) - { - var messageType = (String)propertyValue; - - switch (messageType) - { - case JobRequestMessageTypes.AgentJobRequest: - newValue = new AgentJobRequestMessage(); - break; - - case JobRequestMessageTypes.ServerTaskRequest: - case JobRequestMessageTypes.ServerJobRequest: - newValue = new ServerTaskRequestMessage(); - break; - } - } - } - - if (newValue == null) - { - if (value.TryGetValue("RequestId", StringComparison.OrdinalIgnoreCase, out propertyValue)) - { - newValue = new AgentJobRequestMessage(); - } - } - - if (newValue == null) - { - return existingValue; - } - - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - // The virtual method returns false for CanWrite so this should never be invoked - throw new NotSupportedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/JobRequestMessageTypes.cs b/src/Sdk/DTWebApi/WebApi/JobRequestMessageTypes.cs index 2edc57e4c..326473750 100644 --- a/src/Sdk/DTWebApi/WebApi/JobRequestMessageTypes.cs +++ b/src/Sdk/DTWebApi/WebApi/JobRequestMessageTypes.cs @@ -4,12 +4,6 @@ namespace GitHub.DistributedTask.WebApi { public static class JobRequestMessageTypes { - public const String AgentJobRequest = "JobRequest"; - - public const String ServerJobRequest = "ServerJobRequest"; - - public const String ServerTaskRequest = "ServerTaskRequest"; - public const String PipelineAgentJobRequest = "PipelineAgentJobRequest"; } } diff --git a/src/Sdk/DTWebApi/WebApi/MachineGroupActionFilter.cs b/src/Sdk/DTWebApi/WebApi/MachineGroupActionFilter.cs deleted file mode 100644 index 733c02e84..000000000 --- a/src/Sdk/DTWebApi/WebApi/MachineGroupActionFilter.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [Flags] - [DataContract] - public enum MachineGroupActionFilter - { - [EnumMember] - None = 0, - - [EnumMember] - Manage = 2, - - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/MarketplacePurchasedLicense.cs b/src/Sdk/DTWebApi/WebApi/MarketplacePurchasedLicense.cs deleted file mode 100644 index 093ecd718..000000000 --- a/src/Sdk/DTWebApi/WebApi/MarketplacePurchasedLicense.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Represents a purchase of resource units in a secondary marketplace. - /// - /// - /// The type of resource purchased (pipelines, minutes) is not represented here. - /// - [DataContract] - public sealed class MarketplacePurchasedLicense - { - /// - /// The Marketplace display name. - /// - /// "GitHub" - [DataMember(EmitDefaultValue = false)] - public String MarketplaceName { get; set; } - - /// - /// The name of the identity making the purchase as seen by the marketplace - /// - /// "AppPreview, Microsoft, etc." - [DataMember(EmitDefaultValue = false)] - public String PurchaserName { get; set; } - - /// - /// The quantity purchased. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 PurchaseUnitCount { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/MetricsColumn.cs b/src/Sdk/DTWebApi/WebApi/MetricsColumn.cs deleted file mode 100644 index 2ba192d73..000000000 --- a/src/Sdk/DTWebApi/WebApi/MetricsColumn.cs +++ /dev/null @@ -1,100 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Metrics columns header - /// - [DataContract] - public sealed class MetricsColumnsHeader - { - /// - /// Properties of deployment group for which metrics are provided. - /// E.g. 1: LastJobStatus - /// E.g. 2: TargetState - /// - public IList Dimensions - { - get - { - if (m_dimensions == null) - { - m_dimensions = new List(); - } - - return m_dimensions; - } - internal set - { - m_dimensions = value; - } - } - - /// - /// The types of metrics. - /// E.g. 1: total count of deployment targets. - /// E.g. 2: Average time of deployment to the deployment targets. - /// - public IList Metrics - { - get - { - if (m_metrics == null) - { - m_metrics = new List(); - } - - return m_metrics; - } - internal set - { - m_metrics = value; - } - } - - /// - /// Properties of deployment group for which metrics are provided. - /// E.g. 1: LastJobStatus - /// E.g. 2: TargetState - /// - [DataMember(Name = "Dimensions")] - private IList m_dimensions; - - /// - /// The types of metrics. - /// E.g. 1: total count of deployment targets. - /// E.g. 2: Average time of deployment to the deployment targets. - /// - [DataMember(Name = "Metrics")] - private IList m_metrics; - } - - /// - /// Meta data for a metrics column. - /// - [DataContract] - public sealed class MetricsColumnMetaData - { - /// - /// Name. - /// - [DataMember] - public String ColumnName - { - get; - internal set; - } - - /// - /// Data type. - /// - [DataMember] - public String ColumnValueType - { - get; - internal set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/MetricsRow.cs b/src/Sdk/DTWebApi/WebApi/MetricsRow.cs deleted file mode 100644 index 5ae352782..000000000 --- a/src/Sdk/DTWebApi/WebApi/MetricsRow.cs +++ /dev/null @@ -1,71 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Metrics row. - /// - [DataContract] - public sealed class MetricsRow - { - /// - /// The values of the properties mentioned as 'Dimensions' in column header. - /// E.g. 1: For a property 'LastJobStatus' - metrics will be provided for 'passed', 'failed', etc. - /// E.g. 2: For a property 'TargetState' - metrics will be provided for 'online', 'offline' targets. - /// - public IList Dimensions - { - get - { - if (m_dimensions == null) - { - m_dimensions = new List(); - } - - return m_dimensions; - } - internal set - { - m_dimensions = value; - } - } - - /// - /// Metrics in serialized format. - /// Should be deserialized based on the data type provided in header. - /// - public IList Metrics - { - get - { - if (m_metrics == null) - { - m_metrics = new List(); - } - - return m_metrics; - } - internal set - { - m_metrics = value; - } - } - - /// - /// The values of the properties mentioned as 'Dimensions' in column header. - /// E.g. 1: For a property 'LastJobStatus' - metrics will be provided for 'passed', 'failed', etc. - /// E.g. 2: For a property 'TargetState' - metrics will be provided for 'online', 'offline' targets. - /// - [DataMember(Name = "Dimensions")] - private IList m_dimensions; - - /// - /// Metrics in serialized format. - /// Should be deserialized based on the data type provided in header. - /// - [DataMember(Name = "Metrics")] - private IList m_metrics; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/PlanEnvironment.cs b/src/Sdk/DTWebApi/WebApi/PlanEnvironment.cs deleted file mode 100644 index 8de5134d1..000000000 --- a/src/Sdk/DTWebApi/WebApi/PlanEnvironment.cs +++ /dev/null @@ -1,156 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.DistributedTask.Pipelines; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class PlanEnvironment : IOrchestrationEnvironment - { - public PlanEnvironment() - { - } - - private PlanEnvironment(PlanEnvironment environmentToClone) - { - if (environmentToClone.m_options != null) - { - m_options = m_options.ToDictionary(x => x.Key, x => x.Value.Clone()); - } - - if (environmentToClone.m_maskHints != null) - { - m_maskHints = environmentToClone.m_maskHints.Select(x => x.Clone()).ToList(); - } - - if (environmentToClone.m_variables != null) - { - m_variables = new VariablesDictionary(environmentToClone.m_variables); - } - } - - /// - /// Gets the collection of mask hints - /// - public List MaskHints - { - get - { - if (m_maskHints == null) - { - m_maskHints = new List(); - } - return m_maskHints; - } - } - - /// - /// Gets the collection of options associated with the current context. - /// - /// This is being deprecated and should not be used - public IDictionary Options - { - get - { - if (m_options == null) - { - m_options = new Dictionary(); - } - return m_options; - } - } - - /// - /// Gets the collection of variables associated with the current context. - /// - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new VariablesDictionary(); - } - return m_variables; - } - } - - OrchestrationProcessType IOrchestrationEnvironment.ProcessType - { - get - { - return OrchestrationProcessType.Container; - } - } - - IDictionary IOrchestrationEnvironment.Variables - { - get - { - if (m_variables == null) - { - m_variables = new VariablesDictionary(); - } - return m_variables; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedOptions, ref m_options, true); - SerializationHelper.Copy(ref m_serializedMaskHints, ref m_maskHints, true); - - var secretNames = new HashSet(m_maskHints?.Where(x => x.Type == MaskType.Variable).Select(x => x.Value) ?? new String[0], StringComparer.OrdinalIgnoreCase); - if (m_serializedVariables != null && m_serializedVariables.Count > 0) - { - m_variables = new VariablesDictionary(); - foreach (var variable in m_serializedVariables) - { - m_variables[variable.Key] = new VariableValue(variable.Value, secretNames.Contains(variable.Key)); - } - } - - m_serializedVariables = null; - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedOptions = null; - m_serializedMaskHints = null; - m_serializedVariables = null; - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_options, ref m_serializedOptions); - SerializationHelper.Copy(ref m_maskHints, ref m_serializedMaskHints); - - if (m_variables != null && m_variables.Count > 0) - { - m_serializedVariables = new Dictionary(StringComparer.OrdinalIgnoreCase); - foreach (var variable in m_variables) - { - m_serializedVariables[variable.Key] = variable.Value?.Value; - } - } - } - - private List m_maskHints; - private Dictionary m_options; - private VariablesDictionary m_variables; - - [DataMember(Name = "Mask", EmitDefaultValue = false)] - private List m_serializedMaskHints; - - [DataMember(Name = "Options", EmitDefaultValue = false)] - private Dictionary m_serializedOptions; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private IDictionary m_serializedVariables; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/PlanGroupStatus.cs b/src/Sdk/DTWebApi/WebApi/PlanGroupStatus.cs deleted file mode 100644 index 3ec90c1f3..000000000 --- a/src/Sdk/DTWebApi/WebApi/PlanGroupStatus.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [Flags] - [DataContract] - public enum PlanGroupStatus - { - [EnumMember] - Running = 1, - - [EnumMember] - Queued = 2, - - [EnumMember] - All = Running | Queued - } -} diff --git a/src/Sdk/DTWebApi/WebApi/PlanTemplateType.cs b/src/Sdk/DTWebApi/WebApi/PlanTemplateType.cs deleted file mode 100644 index 96f5c4c35..000000000 --- a/src/Sdk/DTWebApi/WebApi/PlanTemplateType.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - public enum PlanTemplateType - { - [DataMember] - None = 0, - - [DataMember] - Designer = 1, - - [DataMember] - System = 2, - - [DataMember] - Yaml = 3, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ProjectReference.cs b/src/Sdk/DTWebApi/WebApi/ProjectReference.cs deleted file mode 100644 index cb379ebb2..000000000 --- a/src/Sdk/DTWebApi/WebApi/ProjectReference.cs +++ /dev/null @@ -1,21 +0,0 @@ -// -------------------------------------------------------------------------------------------------------------------- -// -// 2012-2023, All rights reserved. -// -// -------------------------------------------------------------------------------------------------------------------- - -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class ProjectReference - { - [DataMember] - public Guid Id { get; set; } - - [DataMember] - public string Name { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/PublishTaskGroupMetadata.cs b/src/Sdk/DTWebApi/WebApi/PublishTaskGroupMetadata.cs deleted file mode 100644 index 008342781..000000000 --- a/src/Sdk/DTWebApi/WebApi/PublishTaskGroupMetadata.cs +++ /dev/null @@ -1,20 +0,0 @@ -// -------------------------------------------------------------------------------------------------------------------- -// -// 2012-2023, All rights reserved. -// -// -------------------------------------------------------------------------------------------------------------------- - -using System; - -namespace GitHub.DistributedTask.WebApi -{ - public class PublishTaskGroupMetadata - { - public Guid TaskGroupId { get; set; } - // This is revision of task group that is getting published - public int TaskGroupRevision { get; set; } - public int ParentDefinitionRevision { get; set; } - public Boolean Preview { get; set; } - public String Comment { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ResourceLimit.cs b/src/Sdk/DTWebApi/WebApi/ResourceLimit.cs deleted file mode 100644 index cd986695b..000000000 --- a/src/Sdk/DTWebApi/WebApi/ResourceLimit.cs +++ /dev/null @@ -1,96 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class ResourceLimit - { - internal ResourceLimit( - Guid hostId, - String parallelismTag, - Boolean isHosted) - { - HostId = hostId; - ParallelismTag = parallelismTag; - IsHosted = isHosted; - } - - [DataMember] - public Guid HostId - { - get; - set; - } - - [DataMember] - public String ParallelismTag - { - get; - set; - } - - [DataMember] - public Boolean IsHosted - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32? TotalCount - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32? TotalMinutes - { - get; - set; - } - - [DataMember] - public Boolean IsPremium - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean FailedToReachAllProviders - { - get; - set; - } - - public IDictionary Data - { - get - { - if (m_resourceLimitsData == null) - { - m_resourceLimitsData = new Dictionary(); - } - - return m_resourceLimitsData; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_resourceLimitsData?.Count == 0) - { - m_resourceLimitsData = null; - } - } - - [DataMember(Name = "ResourceLimitsData", EmitDefaultValue = false)] - private IDictionary m_resourceLimitsData; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ResourceUsage.cs b/src/Sdk/DTWebApi/WebApi/ResourceUsage.cs deleted file mode 100644 index 053ad02bb..000000000 --- a/src/Sdk/DTWebApi/WebApi/ResourceUsage.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [EditorBrowsable(EditorBrowsableState.Never)] - [DataContract] - public class ResourceUsage - { - [DataMember] - public ResourceLimit ResourceLimit - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32? UsedCount - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Int32? UsedMinutes - { - get; - set; - } - - public IList RunningRequests - { - get - { - if (m_runningRequests == null) - { - m_runningRequests = new List(); - } - - return m_runningRequests; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_runningRequests?.Count == 0) - { - m_runningRequests = null; - } - } - - [DataMember(Name = "RunningRequests", EmitDefaultValue = false)] - private IList m_runningRequests; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/SecureFile.cs b/src/Sdk/DTWebApi/WebApi/SecureFile.cs deleted file mode 100644 index c9a40b2f3..000000000 --- a/src/Sdk/DTWebApi/WebApi/SecureFile.cs +++ /dev/null @@ -1,109 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class SecureFile - { - public SecureFile() - { - } - - private SecureFile(SecureFile secureFile, Boolean shallow = false) - { - this.Id = secureFile.Id; - this.Name = secureFile.Name; - this.Ticket = secureFile.Ticket; - - if (!shallow) - { - this.Properties = secureFile.Properties; - this.CreatedBy = secureFile.CreatedBy; - this.CreatedOn = secureFile.CreatedOn; - this.ModifiedBy = secureFile.ModifiedBy; - this.ModifiedOn = secureFile.ModifiedOn; - } - } - - [DataMember(EmitDefaultValue = false)] - public Guid Id - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - public IDictionary Properties - { - get - { - if (m_properties == null) - { - m_properties = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_properties; - } - set - { - m_properties = value; - } - } - - [DataMember(EmitDefaultValue = false)] - public IdentityRef CreatedBy - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime CreatedOn - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public IdentityRef ModifiedBy - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime ModifiedOn - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Ticket - { - get; - set; - } - - public SecureFile Clone() - { - return new SecureFile(this); - } - - public SecureFile CloneShallow() - { - return new SecureFile(this, true); - } - - [DataMember(EmitDefaultValue = false, Name = "Properties")] - private IDictionary m_properties; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/SecureFileActionFilter.cs b/src/Sdk/DTWebApi/WebApi/SecureFileActionFilter.cs deleted file mode 100644 index 700a458ff..000000000 --- a/src/Sdk/DTWebApi/WebApi/SecureFileActionFilter.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [Flags] - [DataContract] - public enum SecureFileActionFilter - { - [EnumMember] - None = 0, - - [EnumMember] - Manage = 2, - - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServerTaskRequestMessage.cs b/src/Sdk/DTWebApi/WebApi/ServerTaskRequestMessage.cs deleted file mode 100644 index e4b62775c..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServerTaskRequestMessage.cs +++ /dev/null @@ -1,43 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class ServerTaskRequestMessage : JobRequestMessage - { - internal ServerTaskRequestMessage() - : base(JobRequestMessageTypes.ServerTaskRequest) - { - } - - public ServerTaskRequestMessage( - TaskOrchestrationPlanReference plan, - TimelineReference timeline, - Guid jobId, - String jobName, - String jobRefName, - JobEnvironment environment, - TaskInstance taskInstance, - TaskDefinition taskDefinition) - : base(JobRequestMessageTypes.ServerJobRequest, plan, timeline, jobId, jobName, jobRefName, environment) - { - TaskDefinition = taskDefinition; - TaskInstance = taskInstance; - } - - [DataMember] - public TaskDefinition TaskDefinition - { - get; - private set; - } - - [DataMember] - public TaskInstance TaskInstance - { - get; - private set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServerTaskSectionExecutionOutput.cs b/src/Sdk/DTWebApi/WebApi/ServerTaskSectionExecutionOutput.cs deleted file mode 100644 index 8cba67674..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServerTaskSectionExecutionOutput.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi.Internal; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [ClientIgnore] - public class ServerTaskSectionExecutionOutput - { - [DataMember] - public Boolean? IsCompleted { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadLoginPromptOption.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadLoginPromptOption.cs deleted file mode 100644 index b13639f9e..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadLoginPromptOption.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum AadLoginPromptOption - { - /// - /// Do not provide a prompt option - /// - [EnumMember] - NoOption = 0, - - /// - /// Force the user to login again. - /// - [EnumMember] - Login = 1, - - /// - /// Force the user to select which account they are logging in with instead of - /// automatically picking the user up from the session state. - /// NOTE: This does not work for switching bewtween the variants of a dual-homed user. - /// - [EnumMember] - SelectAccount = 2, - - /// - /// Force the user to login again. - /// - /// Ignore current authentication state and force the user to authenticate again. This option should be used instead of Login. - /// - /// - [EnumMember] - FreshLogin = 3, - - /// - /// Force the user to login again with mfa. - /// - /// Ignore current authentication state and force the user to authenticate again. This option should be used instead of Login, if MFA is required. - /// - /// - [EnumMember] - FreshLoginWithMfa = 4 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenRequest.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenRequest.cs deleted file mode 100644 index f2de2c74d..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenRequest.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class AadOauthTokenRequest - { - [DataMember] - public String Token { get; set; } - - [DataMember] - public String Resource { get; set; } - - [DataMember] - public String TenantId { get; set; } - - [DataMember] - public Boolean Refresh { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenResult.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenResult.cs deleted file mode 100644 index 89dc4d834..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AadOauthTokenResult.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class AadOauthTokenResult - { - [DataMember] - public String AccessToken { get; set; } - - [DataMember] - public String RefreshTokenCache { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureKeyVaultPermission.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureKeyVaultPermission.cs deleted file mode 100644 index ed53bd305..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureKeyVaultPermission.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureKeyVaultPermission : AzureResourcePermission - { - [DataMember] - public String Vault { get; set; } - - public AzureKeyVaultPermission() : base(AzurePermissionResourceProviders.AzureKeyVaultPermission) - { - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroup.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroup.cs deleted file mode 100644 index db603f1e3..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroup.cs +++ /dev/null @@ -1,40 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Azure Management Group - /// - [DataContract] - public class AzureManagementGroup - { - /// - /// Azure management group name - /// - [DataMember] - [JsonProperty(PropertyName = "Name")] - public String Name { get; set; } - - /// - /// Id of azure management group - /// - [DataMember] - [JsonProperty(PropertyName = "Id")] - public String Id { get; set; } - - /// - /// Display name of azure management group - /// - [DataMember] - [JsonProperty(PropertyName = "displayName")] - public String DisplayName { get; set; } - - /// - /// Id of tenant from which azure management group belogs - /// - [DataMember] - public String TenantId { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroupQueryResult.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroupQueryResult.cs deleted file mode 100644 index 10e61b421..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureManagementGroupQueryResult.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System.Collections.Generic; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Azure management group query result - /// - [DataContract] - public class AzureManagementGroupQueryResult - { - /// - /// List of azure management groups - /// - [DataMember] - [JsonProperty("value")] - public List Value; - - /// - /// Error message in case of an exception - /// - [DataMember] - public string ErrorMessage; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermission.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermission.cs deleted file mode 100644 index 13032068f..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermission.cs +++ /dev/null @@ -1,130 +0,0 @@ -using System; -using System.Reflection; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using Newtonsoft.Json.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [JsonConverter(typeof(AzurePermissionJsonConverter))] - [KnownType(typeof(AzureKeyVaultPermission))] - [DataContract] - public abstract class AzurePermission - { - [DataMember] - public String ResourceProvider { get; set; } - - [DataMember(EmitDefaultValue = true)] - public Boolean Provisioned { get; set; } - - internal AzurePermission(String resourceProvider) - { - this.ResourceProvider = resourceProvider; - } - } - - internal sealed class AzurePermissionJsonConverter : VssSecureJsonConverter - { - public override Boolean CanRead - { - get - { - return true; - } - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(AzurePermission).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader == null) - { - throw new ArgumentNullException("reader"); - } - - if (serializer == null) - { - throw new ArgumentNullException("serializer"); - } - - if (reader.TokenType != JsonToken.StartObject) - { - return existingValue; - } - - var contract = serializer.ContractResolver.ResolveContract(objectType) as JsonObjectContract; - if (contract == null) - { - return existingValue; - } - - JsonProperty resourceProviderProperty = contract.Properties.GetClosestMatchProperty("ResourceProvider"); - if (resourceProviderProperty == null) - { - return existingValue; - } - - JToken itemTypeValue; - JObject value = JObject.Load(reader); - - if (!value.TryGetValue(resourceProviderProperty.PropertyName, StringComparison.OrdinalIgnoreCase, out itemTypeValue)) - { - return existingValue; - } - - if (itemTypeValue.Type != JTokenType.String) - { - throw new NotSupportedException("ResourceProvider property is mandatory for azure permission"); - } - - string resourceProvider = (string)itemTypeValue; - AzurePermission returnValue = null; - switch (resourceProvider) - { - case AzurePermissionResourceProviders.AzureRoleAssignmentPermission: - returnValue = new AzureRoleAssignmentPermission(); - break; - case AzurePermissionResourceProviders.AzureKeyVaultPermission: - returnValue = new AzureKeyVaultPermission(); - break; - default: - throw new NotSupportedException($"{resourceProvider} is not a supported resource provider for azure permission"); - } - - if (returnValue != null) - { - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, returnValue); - } - } - - return returnValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermissionResourceProviders.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermissionResourceProviders.cs deleted file mode 100644 index 0401d87cd..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzurePermissionResourceProviders.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - [GenerateAllConstants] - public static class AzurePermissionResourceProviders - { - public const String AzureRoleAssignmentPermission = "Microsoft.RoleAssignment"; - public const String AzureKeyVaultPermission = "Microsoft.KeyVault"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureResourcePermission.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureResourcePermission.cs deleted file mode 100644 index 60bdc4c06..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureResourcePermission.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public abstract class AzureResourcePermission : AzurePermission - { - [DataMember] - public String ResourceGroup { get; set; } - - protected AzureResourcePermission(String resourceProvider) : base(resourceProvider) - { - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureRoleAssignmentPermission.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureRoleAssignmentPermission.cs deleted file mode 100644 index a608ae89e..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureRoleAssignmentPermission.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureRoleAssignmentPermission : AzurePermission - { - - [DataMember] - public Guid RoleAssignmentId { get; set; } - - public AzureRoleAssignmentPermission() : base(AzurePermissionResourceProviders.AzureRoleAssignmentPermission) - { - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscription.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscription.cs deleted file mode 100644 index ec592bbb2..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscription.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureSubscription - { - [DataMember] - [JsonProperty(PropertyName = "displayName")] - public String DisplayName { get; set; } - - [DataMember] - [JsonProperty(PropertyName = "subscriptionId")] - public String SubscriptionId { get; set; } - - [DataMember] - public String SubscriptionTenantId { get; set; } - - [DataMember] - public String SubscriptionTenantName { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscriptionQueryResult.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscriptionQueryResult.cs deleted file mode 100644 index 998c44b9d..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/AzureSubscriptionQueryResult.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System.Collections.Generic; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class AzureSubscriptionQueryResult - { - [DataMember] - [JsonProperty("value")] - public List Value; - - [DataMember] - public string ErrorMessage; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/DataSourceBinding.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/DataSourceBinding.cs deleted file mode 100644 index e80fb9f13..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/DataSourceBinding.cs +++ /dev/null @@ -1,29 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -using CommonContracts = GitHub.DistributedTask.Common.Contracts; - -namespace GitHub.DistributedTask.WebApi -{ - public class DataSourceBinding : CommonContracts.DataSourceBindingBase - { - public DataSourceBinding() - : base() - { - } - - private DataSourceBinding(DataSourceBinding inputDefinitionToClone) - : base(inputDefinitionToClone) - { - - } - - public DataSourceBinding Clone() - { - return new DataSourceBinding(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/EndpointAuthorization.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/EndpointAuthorization.cs index dff449c35..8b7c4cc3a 100644 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/EndpointAuthorization.cs +++ b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/EndpointAuthorization.cs @@ -6,46 +6,12 @@ namespace GitHub.DistributedTask.WebApi { public sealed class EndpointAuthorizationSchemes { - public const String AzureStorage = "AzureStorage"; public const String OAuth = "OAuth"; - public const String OAuth2 = "OAuth2"; - public const String OAuthWrap = "OAuthWrap"; - public const String Certificate = "Certificate"; - public const String UsernamePassword = "UsernamePassword"; - public const String Token = "Token"; - public const String PersonalAccessToken = "PersonalAccessToken"; - public const String ServicePrincipal = "ServicePrincipal"; - public const String None = "None"; - public const String Jwt = "JWT"; - public const String InstallationToken = "InstallationToken"; } public sealed class EndpointAuthorizationParameters { - public const String Username = "Username"; - public const String Password = "Password"; - public const String Certificate = "Certificate"; public const String AccessToken = "AccessToken"; - public const String ApiToken = "ApiToken"; - public const String RefreshToken = "RefreshToken"; - public const String ServicePrincipalId = "ServicePrincipalId"; - public const String ServicePrincipalKey = "ServicePrincipalKey"; - public const String TenantId = "TenantId"; - public const String RealmName = "RealmName"; - public const String IdToken = "IdToken"; - public const String Nonce = "nonce"; - public const String Scope = "Scope"; - public const String Role = "Role"; - public const String ServerCertThumbprint = "ServerCertThumbprint"; - public const String CompleteCallbackPayload = "CompleteCallbackPayload"; - public const String ClientMail = "ClientMail"; - public const String PrivateKey = "PrivateKey"; - public const String Issuer = "Issuer"; - public const String Audience = "Audience"; - public const String StorageAccountName = "StorageAccountName"; - public const String StorageAccessKey = "StorageAccessKey"; - public const String AccessTokenType = "AccessTokenType"; - public const String Signature = "Signature"; } [DataContract] diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/SerializationHelper.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/SerializationHelper.cs index ecf94c996..1340db4bf 100644 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/SerializationHelper.cs +++ b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/SerializationHelper.cs @@ -21,47 +21,6 @@ namespace GitHub.DistributedTask.WebApi } } - public static void Copy( - ref IList source, - ref ISet target, - IEqualityComparer comparer, - Boolean clearSource = false) - { - if (source != null && source.Count > 0) - { - target = new HashSet(source, comparer); - } - - if (clearSource) - { - source = null; - } - } - - public static void Copy( - ref ISet source, - ref IList target, - Boolean clearSource = false) - { - if (source != null && source.Count > 0) - { - target = new List(source); - } - - if (clearSource) - { - source = null; - } - } - - public static void Copy( - ref Dictionary source, - ref Dictionary target, - Boolean clearSource = false) - { - Copy(ref source, ref target, EqualityComparer.Default, clearSource); - } - public static void Copy( ref IDictionary source, ref IDictionary target, @@ -70,23 +29,6 @@ namespace GitHub.DistributedTask.WebApi Copy(ref source, ref target, EqualityComparer.Default, clearSource); } - public static void Copy( - ref Dictionary source, - ref Dictionary target, - IEqualityComparer comparer, - Boolean clearSource = false) - { - if (source != null && source.Count > 0) - { - target = new Dictionary(source, comparer); - } - - if (clearSource) - { - source = null; - } - } - public static void Copy( ref IDictionary source, ref IDictionary target, diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpoint.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpoint.cs index 3eeca3525..65c133cb7 100644 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpoint.cs +++ b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpoint.cs @@ -31,8 +31,6 @@ namespace GitHub.DistributedTask.WebApi Url = endpointToClone.Url; Description = endpointToClone.Description; GroupScopeId = endpointToClone.GroupScopeId; - AdministratorsGroup = endpointToClone.AdministratorsGroup; - ReadersGroup = endpointToClone.ReadersGroup; if (endpointToClone.Authorization != null) { @@ -45,47 +43,6 @@ namespace GitHub.DistributedTask.WebApi } } - public static bool ValidateServiceEndpoint(ServiceEndpoint endpoint, ref string message) - { - if (endpoint == null) - { - message = "endpoint: null"; - return false; - } - - if (endpoint.Id == Guid.Empty) - { - message = CommonResources.EmptyGuidNotAllowed("endpoint.Id"); - return false; - } - - if (string.IsNullOrEmpty(endpoint.Name)) - { - message = string.Format("{0}:{1}", CommonResources.EmptyStringNotAllowed(), "endpoint.Name"); - return false; - } - - if (endpoint.Url == null) - { - message = "endpoint.Url: null"; - return false; - } - - if (string.IsNullOrEmpty(endpoint.Type)) - { - message = string.Format("{0}:{1}", CommonResources.EmptyStringNotAllowed(), "endpoint.Type"); - return false; - } - - if (endpoint.Authorization == null) - { - message = "endpoint.Authorization: null"; - return false; - } - - return true; - } - /// /// Gets or sets the identifier of this endpoint. /// @@ -136,17 +93,6 @@ namespace GitHub.DistributedTask.WebApi set; } - /// - /// Gets or sets the identity reference for the user who created the Service endpoint. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef CreatedBy - { - get; - set; - } - - /// /// Gets or sets the description of endpoint. /// @@ -174,26 +120,6 @@ namespace GitHub.DistributedTask.WebApi internal set; } - /// - /// Gets or sets the identity reference for the administrators group of the service endpoint. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef AdministratorsGroup - { - get; - internal set; - } - - /// - /// Gets or sets the identity reference for the readers group of the service endpoint. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef ReadersGroup - { - get; - internal set; - } - /// /// Gets the custom data associated with this endpoint. /// diff --git a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpointTypes.cs b/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpointTypes.cs deleted file mode 100644 index 4fcf8f97b..000000000 --- a/src/Sdk/DTWebApi/WebApi/ServiceEndpointLegacy/ServiceEndpointTypes.cs +++ /dev/null @@ -1,91 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.WebApi -{ - public static class ServiceEndpointTypes - { - /// - /// Azure endpoint - /// - public const String Azure = "Azure"; - - /// - /// Chef endpoint - /// - public const String Chef = "Chef"; - - /// Chef endpoint - /// - public const String ExternalTfs = "ExternalTfs"; - - /// - /// Generic endpoint - /// - public const String Generic = "Generic"; - - /// - /// GitHub endpoint - /// - public const String GitHub = "GitHub"; - - /// - /// GitHub Enterprise endpoint - /// - public const String GitHubEnterprise = "GitHubEnterprise"; - - /// - /// Bitbucket endpoint - /// - public const String Bitbucket = "Bitbucket"; - - /// - /// SSH endpoint - /// - public const String SSH = "SSH"; - - /// - /// Subversion endpoint - /// - public const String Subversion = "Subversion"; - - /// - ///Gcp endpoint - /// - public const String Gcp = "google-cloud"; - - /// - /// Subversion endpoint - /// - public const String Jenkins = "Jenkins"; - - /// - /// External Git repository - /// - public const String ExternalGit = "Git"; - - /// - /// Azure RM endpoint - /// - public const String AzureRM = "AzureRM"; - - /// - /// Azure Deployment Manager - /// - public const String AzureDeploymentManager = "AzureDeploymentManager"; - - /// - /// Azure Service Fabric - /// - public const String AzureServiceFabric = "ServiceFabric"; - - /// - /// Azure Service Fabric - /// - public const String Docker = "dockerregistry"; - - /// - /// Jira - /// - public const String Jira = "Jira"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgent.cs b/src/Sdk/DTWebApi/WebApi/TaskAgent.cs index 86fe1068f..1ca8ae94b 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskAgent.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskAgent.cs @@ -5,12 +5,6 @@ using System.Runtime.Serialization; namespace GitHub.DistributedTask.WebApi { - public static class AgentConstants - { - // 1.x agent has been deprecated. - public static readonly String Version = "0.0.0"; - } - /// /// A task agent. /// @@ -59,11 +53,6 @@ namespace GitHub.DistributedTask.WebApi { m_labels = new HashSet(agentToBeCloned.m_labels, StringComparer.OrdinalIgnoreCase); } - - if (agentToBeCloned.PendingUpdate != null) - { - this.PendingUpdate = agentToBeCloned.PendingUpdate.Clone(); - } } /// @@ -126,26 +115,6 @@ namespace GitHub.DistributedTask.WebApi set; } - /// - /// Pending update for this agent. - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentUpdate PendingUpdate - { - get; - internal set; - } - - /// - /// The agent cloud request that's currently associated with this agent. - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentCloudRequest AssignedAgentCloudRequest - { - get; - internal set; - } - /// /// The labels of the runner /// diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentCloud.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentCloud.cs deleted file mode 100644 index 0462c95c0..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentCloud.cs +++ /dev/null @@ -1,156 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentCloud - { - private TaskAgentCloud(TaskAgentCloud cloudToBeCloned) - { - this.Id = cloudToBeCloned.Id; - this.AgentCloudId = cloudToBeCloned.AgentCloudId; - this.Name = cloudToBeCloned.Name; - this.AcquireAgentEndpoint = cloudToBeCloned.AcquireAgentEndpoint; - this.ReleaseAgentEndpoint = cloudToBeCloned.ReleaseAgentEndpoint; - this.SharedSecret = cloudToBeCloned.SharedSecret; - this.Internal = cloudToBeCloned.Internal; - - if (cloudToBeCloned.GetAgentDefinitionEndpoint != null) - { - this.GetAgentDefinitionEndpoint = cloudToBeCloned.GetAgentDefinitionEndpoint; - } - - if (cloudToBeCloned.GetAgentRequestStatusEndpoint != null) - { - this.GetAgentRequestStatusEndpoint = cloudToBeCloned.GetAgentRequestStatusEndpoint; - } - - if (cloudToBeCloned.AcquisitionTimeout != null) - { - this.AcquisitionTimeout = cloudToBeCloned.AcquisitionTimeout; - } - - if (cloudToBeCloned.GetAccountParallelismEndpoint != null) - { - this.GetAccountParallelismEndpoint = cloudToBeCloned.GetAccountParallelismEndpoint; - } - - if (cloudToBeCloned.MaxParallelism != null) - { - this.MaxParallelism = cloudToBeCloned.MaxParallelism; - } - } - - public TaskAgentCloud() - { - } - - //Id is used for interacting with pool providers, AgentCloudId is internal Id - - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public Int32 AgentCloudId - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - /// - /// Gets or sets the type of the endpoint. - /// - [DataMember(EmitDefaultValue = false)] - public String Type - { - get; - set; - } - - /// - /// Signifies that this Agent Cloud is internal and should not be user-manageable - /// - [DataMember(EmitDefaultValue = false)] - public Boolean Internal - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String SharedSecret - { - get; - set; - } - - /// - /// Gets or sets a AcquireAgentEndpoint using which a request can be made to acquire new agent - /// - [DataMember] - public String AcquireAgentEndpoint - { - get; - set; - } - - [DataMember] - public String ReleaseAgentEndpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false, IsRequired = false)] - public String GetAgentDefinitionEndpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false, IsRequired = false)] - public String GetAgentRequestStatusEndpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false, IsRequired = false)] - public Int32? AcquisitionTimeout - { - get; - set; - } - - [DataMember(EmitDefaultValue = false, IsRequired = false)] - public String GetAccountParallelismEndpoint - { - get; - set; - } - - [DataMember(EmitDefaultValue = false, IsRequired = false)] - public Int32? MaxParallelism - { - get; - set; - } - - public TaskAgentCloud Clone() - { - return new TaskAgentCloud(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentCloudRequest.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentCloudRequest.cs deleted file mode 100644 index f5917fce7..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentCloudRequest.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentCloudRequest - { - private TaskAgentCloudRequest(TaskAgentCloudRequest requestToBeCloned) - { - this.AgentCloudId = requestToBeCloned.AgentCloudId; - this.RequestId = requestToBeCloned.RequestId; - this.AgentSpecification = requestToBeCloned.AgentSpecification; - this.ProvisionRequestTime = requestToBeCloned.ProvisionRequestTime; - this.ProvisionedTime = requestToBeCloned.ProvisionedTime; - this.AgentConnectedTime = requestToBeCloned.AgentConnectedTime; - this.ReleaseRequestTime = requestToBeCloned.ReleaseRequestTime; - - if (requestToBeCloned.AgentData != null) - { - this.AgentData = new JObject(requestToBeCloned.AgentData); - } - - if (requestToBeCloned.Pool != null) - { - this.Pool = requestToBeCloned.Pool.Clone(); - } - - if(requestToBeCloned.Agent != null) - { - this.Agent = requestToBeCloned.Agent.Clone(); - } - } - - public TaskAgentCloudRequest() - { - } - - [DataMember] - public Int32 AgentCloudId - { - get; - set; - } - - [DataMember] - public Guid RequestId - { - get; - set; - } - - - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskAgentReference Agent - { - get; - set; - } - - [DataMember] - public JObject AgentSpecification - { - get; - set; - } - - [DataMember] - public JObject AgentData - { - get; - set; - } - - [DataMember] - public DateTime? ProvisionRequestTime - { - get; - set; - } - - [DataMember] - public DateTime? ProvisionedTime - { - get; - set; - } - - [DataMember] - public DateTime? AgentConnectedTime - { - get; - set; - } - - [DataMember] - public DateTime? ReleaseRequestTime - { - get; - set; - } - - public TaskAgentCloudRequest Clone() - { - return new TaskAgentCloudRequest(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentCloudType.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentCloudType.cs deleted file mode 100644 index b397cb73e..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentCloudType.cs +++ /dev/null @@ -1,51 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.FormInput; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentCloudType - { - - public TaskAgentCloudType() - { - } - - /// - /// Gets or sets the name of agent cloud type. - /// - [DataMember] - public String Name - { - get; - set; - } - - /// - /// Gets or sets the display name of agnet cloud type. - /// - [DataMember(EmitDefaultValue = false)] - public String DisplayName { get; set; } - - public List InputDescriptors - { - get - { - return m_inputDescriptors ?? (m_inputDescriptors = new List()); - } - - set - { - m_inputDescriptors = value; - } - } - - /// - /// Gets or sets the input descriptors - /// - [DataMember(EmitDefaultValue = false, Name = "InputDescriptors")] - private List m_inputDescriptors; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentDelaySource.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentDelaySource.cs deleted file mode 100644 index 5b6e87c5e..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentDelaySource.cs +++ /dev/null @@ -1,48 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentDelaySource : ICloneable - { - public TaskAgentDelaySource(TaskAgentReference taskAgent, IEnumerable delays) - { - TaskAgent = taskAgent; - Delays = delays.ToList(); - } - - [DataMember] - public TaskAgentReference TaskAgent { get; } - - [DataMember] - public List Delays { get; } - - public TimeSpan TotalDelay - { - get - { - if (!m_delay.HasValue) - { - m_delay = Delays.Aggregate(TimeSpan.Zero, (sum, next) => sum + next); - } - - return m_delay.Value; - } - } - - private TimeSpan? m_delay; - - Object ICloneable.Clone() - { - return this.Clone(); - } - - public TaskAgentDelaySource Clone() - { - return new TaskAgentDelaySource(TaskAgent, new List(Delays)); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClient.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClient.cs index 337d55354..79d9bd481 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClient.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClient.cs @@ -84,172 +84,10 @@ namespace GitHub.DistributedTask.WebApi bool? includeAssignedRequest = null, bool? includeLastCompletedRequest = null, IEnumerable propertyFilters = null, - IEnumerable demands = null, Object userState = null, CancellationToken cancellationToken = default(CancellationToken)) { - IEnumerable demandStrings = null; - if (demands != null) - { - demandStrings = demands.Select(d => d.ToString()); - } - return GetAgentsAsync(poolId, agentName, includeCapabilities, includeAssignedRequest, includeLastCompletedRequest, propertyFilters, demandStrings, userState, cancellationToken); - } - - /// - /// [Preview API] Get a secure file - /// - /// Project ID - /// The unique secure file Id - /// If includeDownloadTicket is true and the caller has permissions, a download ticket is included in the response. - /// - /// The cancellation token to cancel operation. - public virtual Task GetSecureFileAsync( - Guid project, - Guid secureFileId, - bool? includeDownloadTicket = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - return GetSecureFileAsync(project, secureFileId, includeDownloadTicket, actionFilter: null, userState: userState, cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID or project name - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetSecureFilesAsync( - string project, - string namePattern = null, - bool? includeDownloadTickets = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - return GetSecureFilesAsync(project, namePattern, includeDownloadTickets, actionFilter: null, userState: userState, cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID - /// Name of the secure file to match. Can include wildcards to match multiple files. - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetSecureFilesAsync( - Guid project, - string namePattern = null, - bool? includeDownloadTickets = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - return GetSecureFilesAsync(project, namePattern, includeDownloadTickets, actionFilter: null, userState: userState, cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID or project name - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetSecureFilesByIdsAsync( - string project, - IEnumerable secureFileIds, - bool? includeDownloadTickets = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - return GetSecureFilesByIdsAsync(project, secureFileIds, includeDownloadTickets, actionFilter: null, userState: userState, cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get secure files - /// - /// Project ID - /// A list of secure file Ids - /// If includeDownloadTickets is true and the caller has permissions, a download ticket for each secure file is included in the response. - /// - /// The cancellation token to cancel operation. - public virtual Task> GetSecureFilesByIdsAsync( - Guid project, - IEnumerable secureFileIds, - bool? includeDownloadTickets = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - return GetSecureFilesByIdsAsync(project, secureFileIds, includeDownloadTickets, actionFilter: null, userState: userState, cancellationToken: cancellationToken); - } - - public async Task GetTaskContentZipAsync( - Guid taskId, - TaskVersion version, - Object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - var routeValues = new { taskId = taskId, versionString = version.ToString() }; - HttpRequestMessage requestMessage = await CreateRequestMessageAsync( - HttpMethod.Get, - TaskResourceIds.Tasks, - routeValues: routeValues, - version: m_currentApiVersion).ConfigureAwait(false); - - requestMessage.Headers.Accept.Clear(); - var header = new MediaTypeWithQualityHeaderValue("application/zip"); - header.Parameters.Add(new NameValueHeaderValue("api-version", m_currentApiVersion.ApiVersionString)); - header.Parameters.Add(new NameValueHeaderValue("res-version", "1")); - requestMessage.Headers.Accept.Add(header); - - HttpResponseMessage response = await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); - - response.EnsureSuccessStatusCode(); - - if (response.StatusCode == HttpStatusCode.NoContent) - { - throw new Exception("no content"); - } - - if (!VssStringComparer.ContentType.Equals(response.Content.Headers.ContentType.MediaType, "application/zip")) - { - throw new Exception("bad content type"); - } - - if (response.Content.Headers.ContentEncoding.Contains("gzip", StringComparer.OrdinalIgnoreCase)) - { - return new GZipStream(await response.Content.ReadAsStreamAsync().ConfigureAwait(false), CompressionMode.Decompress); - } - - return await response.Content.ReadAsStreamAsync().ConfigureAwait(false); - } - - public Task QueueAgentRequestByPoolAsync( - Int32 poolId, - IList demands, - Guid serviceOwner, - Guid hostId, - Guid scopeIdentifier, - String hubName, - Guid planId, - Guid jobId, - Object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - var request = new TaskAgentJobRequest - { - ServiceOwner = serviceOwner, - HostId = hostId, - PlanType = hubName, - ScopeId = scopeIdentifier, - PlanId = planId, - JobId = jobId - }; - - return QueueAgentRequestByPoolAsync(poolId, request, userState, cancellationToken); + return GetAgentsAsync(poolId, agentName, includeCapabilities, includeAssignedRequest, includeLastCompletedRequest, propertyFilters, null, userState, cancellationToken); } public Task RenewAgentRequestAsync( @@ -279,390 +117,6 @@ namespace GitHub.DistributedTask.WebApi return ReplaceAgentAsync(poolId, agent.Id, agent, userState, cancellationToken); } - public Task SendMessageAsync( - Int32 poolId, - Int64 requestId, - AgentJobRequestMessage request, - Object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - var message = new TaskAgentMessage - { - Body = JsonUtility.ToString(request), - MessageType = request.MessageType, - }; - - return SendMessageAsync(poolId, requestId, message, userState: userState, cancellationToken: cancellationToken); - } - - public Task SendMessageAsync( - Int32 poolId, - Int64 requestId, - JobCancelMessage cancel, - Object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - var message = new TaskAgentMessage - { - Body = JsonUtility.ToString(cancel), - MessageType = JobCancelMessage.MessageType, - }; - - return SendMessageAsync(poolId, requestId, message, userState: userState, cancellationToken: cancellationToken); - } - - public async Task UploadTaskZipAsync( - Guid taskId, - Stream fileStream, - Boolean overwrite = false, - Object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckForNull(fileStream, "fileStream"); - - HttpRequestMessage requestMessage; - - if (fileStream.Length == 0) - { - throw new Exception("file stream of length 0 not allowed."); - } - - if (fileStream.Length > 16 * 1024 * 1024) - { - throw new Exception("file stream too big"); - } - - Byte[] dataToSend = new Byte[fileStream.Length]; - - List> queryParameters = null; - if (overwrite) - { - queryParameters = new List>(); - queryParameters.Add("overwrite", "true"); - } - - var routeValues = new - { - taskId = taskId - }; - - requestMessage = await CreateRequestMessageAsync(HttpMethod.Put, - TaskResourceIds.Tasks, - routeValues: routeValues, - version: m_currentApiVersion, - queryParameters: queryParameters, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false); - - // inorder for the upload to be retryable, we need the content to be re-readable - // to ensure this we copy the chunk into a byte array and send that - // chunk size ensures we can convert the length to an int - int bytesToCopy = (int)fileStream.Length; - using (MemoryStream ms = new MemoryStream(dataToSend)) - { - await fileStream.CopyToAsync(ms, bytesToCopy, cancellationToken).ConfigureAwait(false); - } - - // set the content and the Content-Range header - HttpContent byteArrayContent = new ByteArrayContent(dataToSend, 0, bytesToCopy); - byteArrayContent.Headers.ContentLength = fileStream.Length; - byteArrayContent.Headers.ContentRange = new ContentRangeHeaderValue(0, fileStream.Length - 1, fileStream.Length); - byteArrayContent.Headers.ContentType = new MediaTypeHeaderValue("application/octet-stream"); - - requestMessage.Content = byteArrayContent; - return await SendAsync(requestMessage, userState, cancellationToken).ConfigureAwait(false); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentGroupsMetricsAsync2( - string project, - string deploymentGroupName = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("281c6308-427a-49e1-b83a-dac0f4862189"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (!string.IsNullOrEmpty(deploymentGroupName)) - { - queryParams.Add("deploymentGroupName", deploymentGroupName); - } - if (!string.IsNullOrEmpty(continuationToken)) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - processResponse: GetPagedList); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetDeploymentGroupsMetricsAsync2( - Guid project, - string deploymentGroupName = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("281c6308-427a-49e1-b83a-dac0f4862189"); - object routeValues = new { project = project }; - - List> queryParams = new List>(); - if (!string.IsNullOrEmpty(deploymentGroupName)) - { - queryParams.Add("deploymentGroupName", deploymentGroupName); - } - if (!string.IsNullOrEmpty(continuationToken)) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - processResponse: GetPagedList); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - /// - public virtual Task> GetDeploymentTargetsAsyncWithContinuationToken( - string project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - bool? partialNameMatch = null, - DeploymentTargetExpands? expand = null, - TaskAgentStatusFilter? agentStatus = null, - TaskAgentJobResultFilter? agentJobResult = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken), - Boolean? enabled = null, - IEnumerable propertyFilters = null) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (!string.IsNullOrEmpty(name)) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (agentStatus != null) - { - queryParams.Add("agentStatus", agentStatus.Value.ToString()); - } - if (agentJobResult != null) - { - queryParams.Add("agentJobResult", agentJobResult.Value.ToString()); - } - if (!string.IsNullOrEmpty(continuationToken)) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (enabled != null) - { - queryParams.Add("enabled", enabled.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.1-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - processResponse: GetPagedList); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// - /// The cancellation token to cancel operation. - /// - public virtual Task> GetDeploymentTargetsAsyncWithContinuationToken( - Guid project, - int deploymentGroupId, - IEnumerable tags = null, - string name = null, - bool? partialNameMatch = null, - DeploymentTargetExpands? expand = null, - TaskAgentStatusFilter? agentStatus = null, - TaskAgentJobResultFilter? agentJobResult = null, - string continuationToken = null, - int? top = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken), - Boolean? enabled = null, - IEnumerable propertyFilters = null) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("2f0aa599-c121-4256-a5fd-ba370e0ae7b6"); - object routeValues = new { project = project, deploymentGroupId = deploymentGroupId }; - - List> queryParams = new List>(); - if (tags != null && tags.Any()) - { - queryParams.Add("tags", string.Join(",", tags)); - } - if (!string.IsNullOrEmpty(name)) - { - queryParams.Add("name", name); - } - if (partialNameMatch != null) - { - queryParams.Add("partialNameMatch", partialNameMatch.Value.ToString()); - } - if (expand != null) - { - queryParams.Add("$expand", expand.Value.ToString()); - } - if (agentStatus != null) - { - queryParams.Add("agentStatus", agentStatus.Value.ToString()); - } - if (agentJobResult != null) - { - queryParams.Add("agentJobResult", agentJobResult.Value.ToString()); - } - if (!string.IsNullOrEmpty(continuationToken)) - { - queryParams.Add("continuationToken", continuationToken); - } - if (top != null) - { - queryParams.Add("$top", top.Value.ToString(CultureInfo.InvariantCulture)); - } - if (enabled != null) - { - queryParams.Add("enabled", enabled.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.1-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken, - processResponse: GetPagedList); - } - - protected async Task> GetPagedList(HttpResponseMessage responseMessage, CancellationToken cancellationToken) - { - var continuationToken = GetContinuationToken(responseMessage); - var list = await ReadContentAsAsync>(responseMessage, cancellationToken).ConfigureAwait(false); - return new PagedList(list, continuationToken); - } - - protected string GetContinuationToken(HttpResponseMessage responseMessage) - { - string continuationToken = null; - - IEnumerable headerValues = null; - if (responseMessage.Headers.TryGetValues("x-ms-continuationtoken", out headerValues)) - { - continuationToken = headerValues.FirstOrDefault(); - } - - return continuationToken; - } - protected Task SendAsync( HttpMethod method, Guid locationId, diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClientCompatBase.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClientCompatBase.cs deleted file mode 100644 index 5e5c50742..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentHttpClientCompatBase.cs +++ /dev/null @@ -1,372 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Net.Http; -using System.Threading; -using System.Threading.Tasks; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [ResourceArea(TaskResourceIds.AreaId)] - public abstract class TaskAgentHttpClientCompatBase : VssHttpClientBase - { - public TaskAgentHttpClientCompatBase( - Uri baseUrl, - VssCredentials credentials) - : base(baseUrl, credentials) - { - } - - public TaskAgentHttpClientCompatBase( - Uri baseUrl, - VssCredentials credentials, - VssHttpRequestSettings settings) - : base(baseUrl, credentials, settings) - { - } - - public TaskAgentHttpClientCompatBase( - Uri baseUrl, - VssCredentials credentials, - params DelegatingHandler[] handlers) - : base(baseUrl, credentials, handlers) - { - } - - public TaskAgentHttpClientCompatBase( - Uri baseUrl, - VssCredentials credentials, - VssHttpRequestSettings settings, - params DelegatingHandler[] handlers) - : base(baseUrl, credentials, settings, handlers) - { - } - - public TaskAgentHttpClientCompatBase( - Uri baseUrl, - HttpMessageHandler pipeline, - Boolean disposeHandler) - : base(baseUrl, pipeline, disposeHandler) - { - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteTaskGroupAsync( - string project, - Guid taskGroupId, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// The cancellation token to cancel operation. - public virtual async Task DeleteTaskGroupAsync( - Guid project, - Guid taskGroupId, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("DELETE"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - using (HttpResponseMessage response = await SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false)) - { - return; - } - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - string project, - Guid? taskGroupId = null, - bool? expanded = null, - Guid? taskIdFilter = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - if (taskIdFilter != null) - { - queryParams.Add("taskIdFilter", taskIdFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - Guid project, - Guid? taskGroupId = null, - bool? expanded = null, - Guid? taskIdFilter = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - if (taskIdFilter != null) - { - queryParams.Add("taskIdFilter", taskIdFilter.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("4.0-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID or project name - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - string project, - Guid? taskGroupId = null, - bool? expanded = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("3.2-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] - /// - /// Project ID - /// - /// - /// - /// The cancellation token to cancel operation. - public virtual Task> GetTaskGroupsAsync( - Guid project, - Guid? taskGroupId = null, - bool? expanded = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("6c08ffbf-dbf1-4f9a-94e5-a1cbd47005e7"); - object routeValues = new { project = project, taskGroupId = taskGroupId }; - - List> queryParams = new List>(); - if (expanded != null) - { - queryParams.Add("expanded", expanded.Value.ToString()); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion("3.2-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get information about an agent. - /// - /// The agent pool containing the agent - /// The agent ID to get information about - /// Whether to include the agent's capabilities in the response - /// Whether to include details about the agent's current work - /// Filter which custom properties will be returned - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never), Obsolete] - public virtual Task GetAgentAsync( - int poolId, - int agentId, - bool? includeCapabilities, - bool? includeAssignedRequest, - IEnumerable propertyFilters, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("e298ef32-5878-4cab-993c-043836571f42"); - object routeValues = new { poolId = poolId, agentId = agentId }; - - List> queryParams = new List>(); - if (includeCapabilities != null) - { - queryParams.Add("includeCapabilities", includeCapabilities.Value.ToString()); - } - if (includeAssignedRequest != null) - { - queryParams.Add("includeAssignedRequest", includeAssignedRequest.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - - return SendAsync( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - - /// - /// [Preview API] Get a list of agents. - /// - /// The agent pool containing the agents - /// Filter on agent name - /// Whether to include the agents' capabilities in the response - /// Whether to include details about the agents' current work - /// Filter which custom properties will be returned - /// Filter by demands the agents can satisfy - /// - /// The cancellation token to cancel operation. - [EditorBrowsable(EditorBrowsableState.Never), Obsolete] - public virtual Task> GetAgentsAsync( - int poolId, - string agentName, - bool? includeCapabilities, - bool? includeAssignedRequest, - IEnumerable propertyFilters, - IEnumerable demands, - object userState = null, - CancellationToken cancellationToken = default) - { - HttpMethod httpMethod = new HttpMethod("GET"); - Guid locationId = new Guid("e298ef32-5878-4cab-993c-043836571f42"); - object routeValues = new { poolId = poolId }; - - List> queryParams = new List>(); - if (agentName != null) - { - queryParams.Add("agentName", agentName); - } - if (includeCapabilities != null) - { - queryParams.Add("includeCapabilities", includeCapabilities.Value.ToString()); - } - if (includeAssignedRequest != null) - { - queryParams.Add("includeAssignedRequest", includeAssignedRequest.Value.ToString()); - } - if (propertyFilters != null && propertyFilters.Any()) - { - queryParams.Add("propertyFilters", string.Join(",", propertyFilters)); - } - if (demands != null && demands.Any()) - { - queryParams.Add("demands", string.Join(",", demands)); - } - - return SendAsync>( - httpMethod, - locationId, - routeValues: routeValues, - version: new ApiResourceVersion(5.1, 1), - queryParameters: queryParams, - userState: userState, - cancellationToken: cancellationToken); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJob.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJob.cs deleted file mode 100644 index 1a2089846..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJob.cs +++ /dev/null @@ -1,103 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentJob - { - public TaskAgentJob( - Guid id, - String name, - String container, - IList steps, - IDictionary sidecarContainers, - IList variables) - { - this.Id = id; - this.Name = name; - this.Container = container; - - m_variables = new List(variables); - m_steps = new List(steps); - - if (sidecarContainers?.Count > 0) - { - m_sidecarContainers = new Dictionary(sidecarContainers, StringComparer.OrdinalIgnoreCase); - } - } - - [DataMember] - public Guid Id - { - get; - } - - [DataMember] - public String Name - { - get; - } - - [DataMember(EmitDefaultValue = false)] - public String Container - { - get; - } - - public IList Steps - { - get - { - if (m_steps == null) - { - m_steps = new List(); - } - return m_steps; - } - } - - public IDictionary SidecarContainers - { - get - { - if (m_sidecarContainers == null) - { - m_sidecarContainers = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_sidecarContainers; - } - } - - public IList Variables - { - get - { - if (m_variables == null) - { - m_variables = new List(); - } - return m_variables; - } - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - if (m_sidecarContainers?.Count == 0) - { - m_sidecarContainers = null; - } - } - - [DataMember(Name = "Steps", EmitDefaultValue = false)] - private List m_steps; - - [DataMember(Name = "SidecarContainers", EmitDefaultValue = false)] - private IDictionary m_sidecarContainers; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private List m_variables; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJobRequest.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJobRequest.cs index 39c6d042d..67318d11c 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJobRequest.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskAgentJobRequest.cs @@ -45,11 +45,6 @@ namespace GitHub.DistributedTask.WebApi m_matchedAgents = requestToBeCloned.m_matchedAgents.Select(x => x.Clone()).ToList(); } - if (requestToBeCloned.m_agentDelays?.Count > 0) - { - m_agentDelays = new List(requestToBeCloned.m_agentDelays); - } - if (requestToBeCloned.ReservedAgent != null) { this.ReservedAgent = requestToBeCloned.ReservedAgent.Clone(); @@ -228,18 +223,6 @@ namespace GitHub.DistributedTask.WebApi set; } - /// - /// A list of demands required to fulfill this request. - /// - /// - [DataMember(Order = 16, EmitDefaultValue = false)] - [Obsolete("No more demands, use labels", true)] - public IList Demands - { - get; - set; - } - /// /// The agent allocated for this request. /// @@ -332,23 +315,6 @@ namespace GitHub.DistributedTask.WebApi set; } - [DataMember(Order = 26, EmitDefaultValue = false)] - public List AgentDelays - { - get - { - if (m_agentDelays == null) - { - m_agentDelays = new List(); - } - return m_agentDelays; - } - internal set - { - m_agentDelays = value; - } - } - [DataMember(Order = 27, EmitDefaultValue = false)] public TimeSpan? ExpectedDuration { @@ -435,8 +401,6 @@ namespace GitHub.DistributedTask.WebApi private List m_matchedAgents; - private List m_agentDelays; - private IDictionary m_requestAgentData; [DataMember(Name = "MatchedAgents", Order = 18, EmitDefaultValue = false)] diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJobResultFilter.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJobResultFilter.cs deleted file mode 100644 index eed282b4f..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJobResultFilter.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// This is useful in getting a list of deployment targets, filtered by the result of their last job. - /// - [Flags] - [DataContract] - public enum TaskAgentJobResultFilter - { - /// - /// Only those deployment targets on which last job failed (**Abandoned**, **Canceled**, **Failed**, **Skipped**). - /// - [EnumMember] - Failed = 1, - - /// - /// Only those deployment targets on which last job Passed (**Succeeded**, **Succeeded with issues**). - /// - [EnumMember] - Passed = 2, - - /// - /// Only those deployment targets that never executed a job. - /// - [EnumMember] - NeverDeployed = 4, - - /// - /// All deployment targets. - /// - [EnumMember] - All = Failed | Passed | NeverDeployed - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJobStep.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJobStep.cs deleted file mode 100644 index d585ce90c..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJobStep.cs +++ /dev/null @@ -1,90 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentJobStep - { - [DataContract] - public enum TaskAgentJobStepType - { - [DataMember] - Task = 1, - - [DataMember] - Action = 2 - } - - [DataMember(EmitDefaultValue = false)] - public TaskAgentJobStepType Type - { - get; - set; - } - - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public Boolean Enabled - { - get; - set; - } - - [DataMember] - public String Condition - { - get; - set; - } - - [DataMember] - public Boolean ContinueOnError - { - get; - set; - } - - [DataMember] - public Int32 TimeoutInMinutes - { - get; - set; - } - - [DataMember] - public TaskAgentJobTask Task - { - get; - set; - } - - [DataMember] - public IDictionary Env - { - get; - set; - } - - [DataMember] - public IDictionary Inputs - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJobTask.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJobTask.cs deleted file mode 100644 index 9266101e0..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJobTask.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentJobTask - { - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public String Version - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentJobVariable.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentJobVariable.cs deleted file mode 100644 index 54d1eb8e1..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentJobVariable.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentJobVariable - { - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public String Value - { - get; - set; - } - - [DataMember] - public Boolean Secret - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPool.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPool.cs index 273b5b92e..08cf73032 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPool.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskAgentPool.cs @@ -23,7 +23,6 @@ namespace GitHub.DistributedTask.WebApi private TaskAgentPool(TaskAgentPool poolToBeCloned) { this.AutoProvision = poolToBeCloned.AutoProvision; - this.CreatedBy = poolToBeCloned.CreatedBy?.Clone(); this.CreatedOn = poolToBeCloned.CreatedOn; this.Id = poolToBeCloned.Id; this.IsHosted = poolToBeCloned.IsHosted; @@ -31,18 +30,10 @@ namespace GitHub.DistributedTask.WebApi this.Scope = poolToBeCloned.Scope; this.Size = poolToBeCloned.Size; this.PoolType = poolToBeCloned.PoolType; - this.Owner = poolToBeCloned.Owner?.Clone(); this.AgentCloudId = poolToBeCloned.AgentCloudId; this.TargetSize = poolToBeCloned.TargetSize; this.IsLegacy = poolToBeCloned.IsLegacy; -#pragma warning disable 0618 - this.AdministratorsGroup = poolToBeCloned.AdministratorsGroup?.Clone(); - this.GroupScopeId = poolToBeCloned.GroupScopeId; - this.Provisioned = poolToBeCloned.Provisioned; - this.ServiceAccountsGroup = poolToBeCloned.ServiceAccountsGroup?.Clone(); -#pragma warning restore 0618 - if (poolToBeCloned.m_properties != null) { m_properties = new PropertiesCollection(poolToBeCloned.m_properties); @@ -101,27 +92,6 @@ namespace GitHub.DistributedTask.WebApi set; } - /// - /// Creator of the pool. The creator of the pool is automatically added into the - /// administrators group for the pool on creation. - /// - [DataMember] - public IdentityRef CreatedBy - { - get; - set; - } - - /// - /// Owner or administrator of the pool. - /// - [DataMember] - public IdentityRef Owner - { - get; - set; - } - /// /// Properties which may be used to extend the storage fields available /// for a given machine instance. @@ -142,54 +112,6 @@ namespace GitHub.DistributedTask.WebApi } } - #region Obsolete Properties - - /// - /// Gets the scope identifier for groups/roles which are owned by this pool. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public Guid GroupScopeId - { - get; - internal set; - } - - /// - /// Gets a value indicating whether or not roles have been provisioned for this pool. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public Boolean Provisioned - { - get; - internal set; - } - - /// - /// Gets the administrators group for this agent pool. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public IdentityRef AdministratorsGroup - { - get; - internal set; - } - - /// - /// Gets the service accounts group for this agent pool. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public IdentityRef ServiceAccountsGroup - { - get; - internal set; - } - - #endregion - public new TaskAgentPool Clone() { return new TaskAgentPool(this); diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolActionFilter.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolActionFilter.cs deleted file mode 100644 index 83c5472e9..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolActionFilter.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Filters pools based on whether the calling user has permission to use or manage the pool. - /// - [Flags] - [DataContract] - public enum TaskAgentPoolActionFilter - { - [EnumMember] - None = 0, - - [EnumMember] - Manage = 2, - - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceDefinition.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceDefinition.cs deleted file mode 100644 index 9a4e5e595..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceDefinition.cs +++ /dev/null @@ -1,168 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentPoolMaintenanceDefinition - { - internal TaskAgentPoolMaintenanceDefinition() - { - } - - private TaskAgentPoolMaintenanceDefinition(TaskAgentPoolMaintenanceDefinition maintenanceDefinitionToBeCloned) - { - this.Enabled = maintenanceDefinitionToBeCloned.Enabled; - this.JobTimeoutInMinutes = maintenanceDefinitionToBeCloned.JobTimeoutInMinutes; - this.MaxConcurrentAgentsPercentage = maintenanceDefinitionToBeCloned.MaxConcurrentAgentsPercentage; - - if (maintenanceDefinitionToBeCloned.Pool != null) - { - this.Pool = new TaskAgentPoolReference - { - Id = maintenanceDefinitionToBeCloned.Pool.Id, - Name = maintenanceDefinitionToBeCloned.Pool.Name, - Scope = maintenanceDefinitionToBeCloned.Pool.Scope, - PoolType = maintenanceDefinitionToBeCloned.Pool.PoolType - }; - } - - this.m_options = maintenanceDefinitionToBeCloned.Options.Clone(); - this.m_retentionPolicy = maintenanceDefinitionToBeCloned.RetentionPolicy.Clone(); - this.m_scheduleSetting = maintenanceDefinitionToBeCloned.ScheduleSetting.Clone(); - } - - /// - /// Id - /// - [DataMember] - public Int32 Id - { - get; - internal set; - } - - /// - /// Pool reference for the maintenance definition - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - - /// - /// Enable maintenance - /// - [DataMember] - public Boolean Enabled - { - get; - set; - } - - /// - /// Maintenance job timeout per agent - /// - [DataMember] - public Int32 JobTimeoutInMinutes - { - get; - set; - } - - /// - /// Max percentage of agents within a pool running maintenance job at given time - /// - [DataMember] - public Int32 MaxConcurrentAgentsPercentage - { - get; - set; - } - - /// - /// Maintenance option for the definition - /// - public TaskAgentPoolMaintenanceOptions Options - { - get - { - if (m_options == null) - { - m_options = new TaskAgentPoolMaintenanceOptions() - { - WorkingDirectoryExpirationInDays = 0, - }; - } - - return m_options; - } - internal set - { - m_options = value; - } - } - - /// - /// The retention setting for the pool maintenance definition. - /// - public TaskAgentPoolMaintenanceRetentionPolicy RetentionPolicy - { - get - { - if (m_retentionPolicy == null) - { - m_retentionPolicy = new TaskAgentPoolMaintenanceRetentionPolicy() - { - NumberOfHistoryRecordsToKeep = 1, - }; - } - - return m_retentionPolicy; - } - internal set - { - m_retentionPolicy = value; - } - } - - /// - /// The schedule setting for the pool maintenance job. - /// - public TaskAgentPoolMaintenanceSchedule ScheduleSetting - { - get - { - if (m_scheduleSetting == null) - { - m_scheduleSetting = new TaskAgentPoolMaintenanceSchedule() - { - DaysToBuild = TaskAgentPoolMaintenanceScheduleDays.None, - }; - } - - return m_scheduleSetting; - } - internal set - { - m_scheduleSetting = value; - } - } - - public TaskAgentPoolMaintenanceDefinition Clone() - { - return new TaskAgentPoolMaintenanceDefinition(this); - } - - [DataMember(EmitDefaultValue = false, Name = "Options")] - public TaskAgentPoolMaintenanceOptions m_options; - - [DataMember(EmitDefaultValue = false, Name = "RetentionPolicy")] - private TaskAgentPoolMaintenanceRetentionPolicy m_retentionPolicy; - - [DataMember(EmitDefaultValue = false, Name = "ScheduleSetting")] - private TaskAgentPoolMaintenanceSchedule m_scheduleSetting; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJob.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJob.cs deleted file mode 100644 index 4d1f5647f..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJob.cs +++ /dev/null @@ -1,169 +0,0 @@ -using GitHub.Services.WebApi; -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentPoolMaintenanceJob - { - internal TaskAgentPoolMaintenanceJob() - { - } - - /// - /// Id of the maintenance job - /// - [DataMember] - public Int32 JobId - { - get; - internal set; - } - - /// - /// Pool reference for the maintenance job - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - - /// - /// Orchestration/Plan Id for the maintenance job - /// - [DataMember] - public Guid OrchestrationId - { - get; - internal set; - } - - /// - /// The maintenance definition for the maintenance job - /// - [DataMember] - public Int32 DefinitionId - { - get; - set; - } - - /// - /// Status of the maintenance job - /// - [DataMember] - public TaskAgentPoolMaintenanceJobStatus Status - { - get; - set; - } - - /// - /// The maintenance job result - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolMaintenanceJobResult? Result - { - get; - internal set; - } - - /// - /// Time that the maintenance job was queued - /// - [DataMember(EmitDefaultValue = false)] - public DateTime? QueueTime - { - get; - internal set; - } - - /// - /// Time that the maintenance job was started - /// - [DataMember(EmitDefaultValue = false)] - public DateTime? StartTime - { - get; - internal set; - } - - /// - /// Time that the maintenance job was completed - /// - [DataMember(EmitDefaultValue = false)] - public DateTime? FinishTime - { - get; - internal set; - } - - /// - /// The identity that queued the maintenance job - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef RequestedBy - { - get; - internal set; - } - - /// - /// The total error counts during the maintenance job - /// - [DataMember] - public Int32 ErrorCount - { - get; - internal set; - } - - /// - /// The total warning counts during the maintenance job - /// - [DataMember] - public Int32 WarningCount - { - get; - internal set; - } - - /// - /// The log download url for the maintenance job - /// - [DataMember] - public String LogsDownloadUrl - { - get; - internal set; - } - - - /// - /// All agents that the maintenance job will run on - /// - public List TargetAgents - { - get - { - if (m_targetAgents == null) - { - m_targetAgents = new List(); - } - - return m_targetAgents; - } - internal set - { - m_targetAgents = value; - } - } - - [DataMember(EmitDefaultValue = false, Name = "TargetAgents")] - private List m_targetAgents; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobResult.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobResult.cs deleted file mode 100644 index 525947ba0..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobResult.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskAgentPoolMaintenanceJobResult - { - [EnumMember] - Succeeded = 1, - - [EnumMember] - Failed = 2, - - [EnumMember] - Canceled = 4, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobStatus.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobStatus.cs deleted file mode 100644 index a8c594f7b..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobStatus.cs +++ /dev/null @@ -1,21 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskAgentPoolMaintenanceJobStatus - { - [EnumMember] - InProgress = 1, - - [EnumMember] - Completed = 2, - - [EnumMember] - Cancelling = 4, - - [EnumMember] - Queued = 8, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobTargetAgent.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobTargetAgent.cs deleted file mode 100644 index e200ef5ec..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceJobTargetAgent.cs +++ /dev/null @@ -1,41 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskAgentPoolMaintenanceJobTargetAgent - { - internal TaskAgentPoolMaintenanceJobTargetAgent() - { - } - - [DataMember] - public Int32 JobId - { - get; - set; - } - - [DataMember] - public TaskAgentReference Agent - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolMaintenanceJobStatus? Status - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolMaintenanceJobResult? Result - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceOptions.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceOptions.cs deleted file mode 100644 index 332c32b3f..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceOptions.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskAgentPoolMaintenanceOptions - { - internal TaskAgentPoolMaintenanceOptions() - { - } - - private TaskAgentPoolMaintenanceOptions(TaskAgentPoolMaintenanceOptions maintenanceOptionToBeCloned) - { - this.WorkingDirectoryExpirationInDays = maintenanceOptionToBeCloned.WorkingDirectoryExpirationInDays; - } - - /// - /// time to consider a System.DefaultWorkingDirectory is stale - /// - [DataMember] - public Int32 WorkingDirectoryExpirationInDays - { - get; - set; - } - - public TaskAgentPoolMaintenanceOptions Clone() - { - return new TaskAgentPoolMaintenanceOptions(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceRetentionPolicy.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceRetentionPolicy.cs deleted file mode 100644 index e5bb9d57a..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceRetentionPolicy.cs +++ /dev/null @@ -1,47 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskAgentPoolMaintenanceRetentionPolicy - { - internal TaskAgentPoolMaintenanceRetentionPolicy() - { } - - private TaskAgentPoolMaintenanceRetentionPolicy(TaskAgentPoolMaintenanceRetentionPolicy maintenanceRetentionPolicyToBeCloned) - { - this.NumberOfHistoryRecordsToKeep = maintenanceRetentionPolicyToBeCloned.NumberOfHistoryRecordsToKeep; - } - - /// - /// Number of records to keep for maintenance job executed with this definition. - /// - [DataMember] - public Int32 NumberOfHistoryRecordsToKeep - { - get - { - return m_numberOfHistoryRecordsToKeep; - } - internal set - { - if (value < 1) - { - m_numberOfHistoryRecordsToKeep = 1; - } - else - { - m_numberOfHistoryRecordsToKeep = value; - } - } - } - - public TaskAgentPoolMaintenanceRetentionPolicy Clone() - { - return new TaskAgentPoolMaintenanceRetentionPolicy(this); - } - - private Int32 m_numberOfHistoryRecordsToKeep; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceSchedule.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceSchedule.cs deleted file mode 100644 index a931287ef..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceSchedule.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskAgentPoolMaintenanceSchedule - { - internal TaskAgentPoolMaintenanceSchedule() - { - this.DaysToBuild = TaskAgentPoolMaintenanceScheduleDays.None; - } - - private TaskAgentPoolMaintenanceSchedule(TaskAgentPoolMaintenanceSchedule maintenanceScheduleToBeCloned) - { - this.ScheduleJobId = maintenanceScheduleToBeCloned.ScheduleJobId; - this.StartHours = maintenanceScheduleToBeCloned.StartHours; - this.StartMinutes = maintenanceScheduleToBeCloned.StartMinutes; - this.TimeZoneId = maintenanceScheduleToBeCloned.TimeZoneId; - this.DaysToBuild = maintenanceScheduleToBeCloned.DaysToBuild; - } - - /// - /// The Job Id of the Scheduled job that will queue the pool maintenance job. - /// - [DataMember] - public Guid ScheduleJobId { get; set; } - - /// - /// Time zone of the build schedule (string representation of the time zone id) - /// - [DataMember] - public String TimeZoneId { get; set; } - - /// - /// Local timezone hour to start - /// - [DataMember] - public Int32 StartHours { get; set; } - - /// - /// Local timezone minute to start - /// - [DataMember] - public Int32 StartMinutes { get; set; } - - /// - /// Days for a build (flags enum for days of the week) - /// - [DataMember] - public TaskAgentPoolMaintenanceScheduleDays DaysToBuild { get; set; } - - public TaskAgentPoolMaintenanceSchedule Clone() - { - return new TaskAgentPoolMaintenanceSchedule(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceScheduleDays.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceScheduleDays.cs deleted file mode 100644 index e96d34572..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolMaintenanceScheduleDays.cs +++ /dev/null @@ -1,62 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskAgentPoolMaintenanceScheduleDays - { - /// - /// Do not run. - /// - [EnumMember] - None = 0, - - /// - /// Run on Monday. - /// - [EnumMember] - Monday = 1, - - /// - /// Run on Tuesday. - /// - [EnumMember] - Tuesday = 2, - - /// - /// Run on Wednesday. - /// - [EnumMember] - Wednesday = 4, - - /// - /// Run on Thursday. - /// - [EnumMember] - Thursday = 8, - - /// - /// Run on Friday. - /// - [EnumMember] - Friday = 16, - - /// - /// Run on Saturday. - /// - [EnumMember] - Saturday = 32, - - /// - /// Run on Sunday. - /// - [EnumMember] - Sunday = 64, - - /// - /// Run on all days of the week. - /// - [EnumMember] - All = Monday | Tuesday | Wednesday | Thursday | Friday | Saturday | Sunday, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolType.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolType.cs index d69fc2092..91afb1cbb 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentPoolType.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskAgentPoolType.cs @@ -12,12 +12,6 @@ namespace GitHub.DistributedTask.WebApi /// A typical pool of task agents /// [EnumMember] - Automation = 1, - - /// - /// A deployment pool - /// - [EnumMember] - Deployment = 2 + Automation = 1 } } diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentQueue.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentQueue.cs deleted file mode 100644 index 73dee04ee..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentQueue.cs +++ /dev/null @@ -1,97 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// An agent queue. - /// - [DataContract] - public class TaskAgentQueue - { - public TaskAgentQueue() - { - } - - private TaskAgentQueue(TaskAgentQueue queueToBeCloned) - { - this.Id = queueToBeCloned.Id; - this.ProjectId = queueToBeCloned.ProjectId; - this.Name = queueToBeCloned.Name; -#pragma warning disable 0618 - this.GroupScopeId = queueToBeCloned.GroupScopeId; - this.Provisioned = queueToBeCloned.Provisioned; -#pragma warning restore 0618 - if (queueToBeCloned.Pool != null) - { - this.Pool = queueToBeCloned.Pool.Clone(); - } - } - - /// - /// ID of the queue - /// - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - /// - /// Project ID - /// - [DataMember(EmitDefaultValue = false)] - public Guid ProjectId - { - get; - set; - } - - /// - /// Name of the queue - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Pool reference for this queue - /// - [DataMember(EmitDefaultValue = false)] - public TaskAgentPoolReference Pool - { - get; - set; - } - - #region Obsolete Properties - - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public Guid GroupScopeId - { - get; - set; - } - - [EditorBrowsable(EditorBrowsableState.Never)] - [Obsolete("This property is no longer used and will be removed in a future version.", false)] - public Boolean Provisioned - { - get; - set; - } - - #endregion - - public TaskAgentQueue Clone() - { - return new TaskAgentQueue(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentQueueActionFilter.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentQueueActionFilter.cs deleted file mode 100644 index 69f832336..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentQueueActionFilter.cs +++ /dev/null @@ -1,22 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Filters queues based on whether the calling user has permission to use or manage the queue. - /// - [Flags] - [DataContract] - public enum TaskAgentQueueActionFilter - { - [EnumMember] - None = 0, - - [EnumMember] - Manage = 2, - - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentStatusFilter.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentStatusFilter.cs deleted file mode 100644 index ed531c13e..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentStatusFilter.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// This is useful in getting a list of deployment targets, filtered by the deployment agent status. - /// - [Flags] - [DataContract] - public enum TaskAgentStatusFilter - { - /// - /// Only deployment targets that are offline. - /// - [EnumMember] - Offline = 1, - - /// - /// Only deployment targets that are online. - /// - [EnumMember] - Online = 2, - - /// - /// All deployment targets. - /// - [EnumMember] - All = Offline | Online - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentUpdate.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentUpdate.cs deleted file mode 100644 index cc9928a73..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentUpdate.cs +++ /dev/null @@ -1,115 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Details about an agent update. - /// - [DataContract] - public class TaskAgentUpdate - { - internal TaskAgentUpdate() - { - } - - private TaskAgentUpdate(TaskAgentUpdate agentUpdateToBeCloned) - { - this.CurrentState = agentUpdateToBeCloned.CurrentState; - if (agentUpdateToBeCloned.SourceVersion != null) - { - this.SourceVersion = agentUpdateToBeCloned.SourceVersion.Clone(); - } - if (agentUpdateToBeCloned.TargetVersion != null) - { - this.TargetVersion = agentUpdateToBeCloned.TargetVersion.Clone(); - } - if (agentUpdateToBeCloned.RequestTime != null) - { - this.RequestTime = agentUpdateToBeCloned.RequestTime; - } - if (agentUpdateToBeCloned.RequestedBy != null) - { - this.RequestedBy = agentUpdateToBeCloned.RequestedBy.Clone(); - } - if (agentUpdateToBeCloned.Reason != null) - { - switch (agentUpdateToBeCloned.Reason.Code) - { - case TaskAgentUpdateReasonType.Manual: - this.Reason = (agentUpdateToBeCloned.Reason as TaskAgentManualUpdate).Clone(); - break; - case TaskAgentUpdateReasonType.MinAgentVersionRequired: - this.Reason = (agentUpdateToBeCloned.Reason as TaskAgentMinAgentVersionRequiredUpdate).Clone(); - break; - } - } - } - - /// - /// Source agent version of the update. - /// - [DataMember] - public PackageVersion SourceVersion - { - get; - internal set; - } - - /// - /// Target agent version of the update. - /// - [DataMember] - public PackageVersion TargetVersion - { - get; - internal set; - } - - /// - /// Date on which this update was requested. - /// - [DataMember] - public DateTime? RequestTime - { - get; - internal set; - } - - /// - /// Identity which requested this update. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef RequestedBy - { - get; - internal set; - } - - /// - /// Current state of this agent update. - /// - [DataMember(EmitDefaultValue = false)] - public String CurrentState - { - get; - set; - } - - /// - /// Reason for this update. - /// - [DataMember] - public TaskAgentUpdateReason Reason - { - get; - set; - } - - public TaskAgentUpdate Clone() - { - return new TaskAgentUpdate(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskAgentUpdateReason.cs b/src/Sdk/DTWebApi/WebApi/TaskAgentUpdateReason.cs deleted file mode 100644 index 099c61a2f..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskAgentUpdateReason.cs +++ /dev/null @@ -1,178 +0,0 @@ -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskAgentUpdateReasonType - { - [EnumMember] - Manual = 1, - - [EnumMember] - MinAgentVersionRequired = 2, - } - - internal sealed class TaskAgentUpdateReasonJsonConverter : VssSecureJsonConverter - { - public override Boolean CanConvert(Type objectType) - { - return typeof(TaskAgentUpdateReason).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - Object newValue = null; - JToken propertyValue; - JObject value = JObject.Load(reader); - - if (value.TryGetValue("Code", StringComparison.OrdinalIgnoreCase, out propertyValue)) - { - if (propertyValue.Type == JTokenType.String) - { - TaskAgentUpdateReasonType code; - if (Enum.TryParse((String)propertyValue, out code)) - { - switch (code) - { - case TaskAgentUpdateReasonType.Manual: - newValue = new TaskAgentManualUpdate(); - break; - - case TaskAgentUpdateReasonType.MinAgentVersionRequired: - newValue = new TaskAgentMinAgentVersionRequiredUpdate(); - break; - } - - } - } - } - - if (newValue == null) - { - return existingValue; - } - - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - // The virtual method returns false for CanWrite so this should never be invoked - throw new NotSupportedException(); - } - } - - [DataContract] - [ServiceEventObjectAttribute] - [JsonConverter(typeof(TaskAgentUpdateReasonJsonConverter))] - public abstract class TaskAgentUpdateReason - { - protected TaskAgentUpdateReason(TaskAgentUpdateReasonType code) - { - this.Code = code; - } - - [DataMember] - public TaskAgentUpdateReasonType Code { get; private set; } - } - - [DataContract] - public class TaskAgentManualUpdate : TaskAgentUpdateReason - { - [JsonConstructor] - internal TaskAgentManualUpdate() : - base(TaskAgentUpdateReasonType.Manual) - { - } - - public TaskAgentManualUpdate Clone() - { - return new TaskAgentManualUpdate(); - } - } - - [DataContract] - public class TaskAgentMinAgentVersionRequiredUpdate : TaskAgentUpdateReason - { - [JsonConstructor] - internal TaskAgentMinAgentVersionRequiredUpdate() : - base(TaskAgentUpdateReasonType.MinAgentVersionRequired) - { - } - - private TaskAgentMinAgentVersionRequiredUpdate(TaskAgentMinAgentVersionRequiredUpdate updateToBeCloned) : - base(TaskAgentUpdateReasonType.MinAgentVersionRequired) - { - if (updateToBeCloned.MinAgentVersion != null) - { - this.MinAgentVersion = updateToBeCloned.MinAgentVersion.Clone(); - } - if (updateToBeCloned.JobDefinition != null) - { - this.JobDefinition = updateToBeCloned.JobDefinition.Clone(); - } - if (updateToBeCloned.JobOwner != null) - { - this.JobOwner = updateToBeCloned.JobOwner.Clone(); - } - } - - [DataMember] - public Demand MinAgentVersion - { - get; - set; - } - - [DataMember] - public TaskOrchestrationOwner JobDefinition - { - get; - set; - } - - [DataMember] - public TaskOrchestrationOwner JobOwner - { - get; - set; - } - - public TaskAgentMinAgentVersionRequiredUpdate Clone() - { - return new TaskAgentMinAgentVersionRequiredUpdate(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskDefinition.cs b/src/Sdk/DTWebApi/WebApi/TaskDefinition.cs deleted file mode 100644 index 65c5a8288..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskDefinition.cs +++ /dev/null @@ -1,552 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; -using System.Runtime.Serialization; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [DebuggerDisplay("Id: {Id}, Name: {Name}, Version: {Version}")] - public class TaskDefinition - { - public TaskDefinition() - { - this.DefinitionType = TaskDefinitionType.Task; - } - - protected TaskDefinition(TaskDefinition taskDefinitionToClone) - { - if (taskDefinitionToClone.AgentExecution != null) - { - this.AgentExecution = taskDefinitionToClone.AgentExecution.Clone(); - } - - if (taskDefinitionToClone.PreJobExecution != null) - { - this.m_preJobExecution = new Dictionary(taskDefinitionToClone.m_preJobExecution); - } - - if (taskDefinitionToClone.Execution != null) - { - this.m_execution = new Dictionary(taskDefinitionToClone.m_execution); - } - - if (taskDefinitionToClone.PostJobExecution != null) - { - this.m_postJobExecution = new Dictionary(taskDefinitionToClone.m_postJobExecution); - } - - this.Author = taskDefinitionToClone.Author; - this.Category = taskDefinitionToClone.Category; - this.HelpMarkDown = taskDefinitionToClone.HelpMarkDown; - this.HelpUrl = taskDefinitionToClone.HelpUrl; - this.ContentsUploaded = taskDefinitionToClone.ContentsUploaded; - - if (taskDefinitionToClone.m_visibilities != null) - { - this.m_visibilities = new List(taskDefinitionToClone.m_visibilities); - } - - if (taskDefinitionToClone.m_runsOn != null) - { - this.m_runsOn = new List(taskDefinitionToClone.m_runsOn); - } - - if (this.m_runsOn == null) - { - this.m_runsOn = new List(TaskRunsOnConstants.DefaultValue); - } - - if (taskDefinitionToClone.m_demands != null) - { - this.m_demands = new List(taskDefinitionToClone.m_demands.Select(x => x.Clone())); - } - - this.Description = taskDefinitionToClone.Description; - this.FriendlyName = taskDefinitionToClone.FriendlyName; - this.HostType = taskDefinitionToClone.HostType; - this.IconUrl = taskDefinitionToClone.IconUrl; - this.Id = taskDefinitionToClone.Id; - - if (taskDefinitionToClone.m_inputs != null) - { - this.m_inputs = new List(taskDefinitionToClone.m_inputs.Select(x => x.Clone())); - } - - if (taskDefinitionToClone.m_satisfies != null) - { - this.m_satisfies = new List(taskDefinitionToClone.m_satisfies); - } - - if (taskDefinitionToClone.m_sourceDefinitions != null) - { - this.m_sourceDefinitions = new List(taskDefinitionToClone.m_sourceDefinitions.Select(x => x.Clone())); - } - - if (taskDefinitionToClone.m_dataSourceBindings != null) - { - this.m_dataSourceBindings = new List(taskDefinitionToClone.m_dataSourceBindings.Select(x => x.Clone())); - } - - if (taskDefinitionToClone.m_groups != null) - { - this.m_groups = new List(taskDefinitionToClone.m_groups.Select(x => x.Clone())); - } - - if (taskDefinitionToClone.m_outputVariables != null) - { - this.m_outputVariables = new List(taskDefinitionToClone.m_outputVariables.Select(x => x.Clone())); - } - - this.InstanceNameFormat = taskDefinitionToClone.InstanceNameFormat; - this.MinimumAgentVersion = taskDefinitionToClone.MinimumAgentVersion; - this.Name = taskDefinitionToClone.Name; - this.PackageLocation = taskDefinitionToClone.PackageLocation; - this.PackageType = taskDefinitionToClone.PackageType; - this.ServerOwned = taskDefinitionToClone.ServerOwned; - this.SourceLocation = taskDefinitionToClone.SourceLocation; - this.Version = taskDefinitionToClone.Version.Clone(); - this.ContributionIdentifier = taskDefinitionToClone.ContributionIdentifier; - this.ContributionVersion = taskDefinitionToClone.ContributionVersion; - this.Deprecated = taskDefinitionToClone.Deprecated; - this.Disabled = taskDefinitionToClone.Disabled; - this.DefinitionType = taskDefinitionToClone.DefinitionType; - this.ShowEnvironmentVariables = taskDefinitionToClone.ShowEnvironmentVariables; - this.Preview = taskDefinitionToClone.Preview; - this.ReleaseNotes = taskDefinitionToClone.ReleaseNotes; - - if (this.DefinitionType == null) - { - this.DefinitionType = TaskDefinitionType.Task; - } - } - - // - // Members to identify this task - // - [DataMember(EmitDefaultValue = false)] - public Guid Id - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskVersion Version - { - get; - set; - } - - [Obsolete("Ecosystem property is not currently supported.")] - [DataMember(EmitDefaultValue = false)] - public String Ecosystem - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean ServerOwned - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean ContentsUploaded - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String IconUrl - { - get; - set; - } - - // - // Location Information for acquisition - // - [DataMember(EmitDefaultValue = false)] - public String HostType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String PackageType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String PackageLocation - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String SourceLocation - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String MinimumAgentVersion - { - get; - set; - } - - // - // Helpful Metadata for discovery and designer - // - [DataMember(EmitDefaultValue = false)] - public String FriendlyName - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Category - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String HelpMarkDown - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String HelpUrl - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String ReleaseNotes - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Preview - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Deprecated - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String ContributionIdentifier - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String ContributionVersion - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Disabled - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String DefinitionType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean ShowEnvironmentVariables - { - get; - set; - } - - public IList Visibility - { - get - { - if (m_visibilities == null) - { - m_visibilities = new List(); - } - return m_visibilities; - } - } - - public IList RunsOn - { - get - { - if (m_runsOn == null) - { - m_runsOn = new List(TaskRunsOnConstants.DefaultValue); - } - - return m_runsOn; - } - } - - [DataMember(EmitDefaultValue = false)] - public String Author { get; set; } - - [DataMember(EmitDefaultValue = false)] - public IList Demands - { - get - { - if (m_demands == null) - { - m_demands = new List(); - } - return m_demands; - } - } - - [DataMember(EmitDefaultValue = false)] - public IList Groups - { - get - { - if (m_groups == null) - { - m_groups = new List(); - } - return m_groups; - } - } - - [DataMember(EmitDefaultValue = false)] - public IList Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new List(); - } - return m_inputs; - } - } - - [DataMember(EmitDefaultValue = false)] - public IList Satisfies - { - get - { - if (m_satisfies == null) - { - m_satisfies = new List(); - } - return m_satisfies; - } - } - - [DataMember(EmitDefaultValue = false)] - public IList SourceDefinitions - { - get - { - if (m_sourceDefinitions == null) - { - m_sourceDefinitions = new List(); - } - return m_sourceDefinitions; - } - } - - [DataMember(EmitDefaultValue = false)] - public IList DataSourceBindings - { - get - { - if (m_dataSourceBindings == null) - { - m_dataSourceBindings = new List(); - } - return m_dataSourceBindings; - } - } - - [DataMember(EmitDefaultValue = false)] - public String InstanceNameFormat - { - get; - set; - } - - // - // Execution members - // - [DataMember(EmitDefaultValue = false)] - public IDictionary PreJobExecution - { - get - { - if (m_preJobExecution == null) - { - m_preJobExecution = new Dictionary(); - } - return m_preJobExecution; - } - } - - [DataMember(EmitDefaultValue = false)] - public IDictionary Execution - { - get - { - if (m_execution == null) - { - m_execution = new Dictionary(); - } - return m_execution; - } - } - - [DataMember(EmitDefaultValue = false)] - public IDictionary PostJobExecution - { - get - { - if (m_postJobExecution == null) - { - m_postJobExecution = new Dictionary(); - } - return m_postJobExecution; - } - } - - [DataMember(EmitDefaultValue = false)] - public TaskExecution AgentExecution - { - get; - set; - } - - public IList OutputVariables - { - get - { - if (m_outputVariables == null) - { - m_outputVariables = new List(); - } - return m_outputVariables; - } - } - - internal TaskDefinition Clone() - { - return new TaskDefinition(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedVisibilities, ref m_visibilities, true); - SerializationHelper.Copy(ref m_serializedRunsOn, ref m_runsOn, true); - RenameLegacyRunsOnValues(m_runsOn); - SerializationHelper.Copy(ref m_serializedOutputVariables, ref m_outputVariables, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_visibilities, ref m_serializedVisibilities); - RenameLegacyRunsOnValues(m_runsOn); - SerializationHelper.Copy(ref m_runsOn, ref m_serializedRunsOn); - SerializationHelper.Copy(ref m_outputVariables, ref m_serializedOutputVariables); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedVisibilities = null; - m_serializedRunsOn = null; - m_serializedOutputVariables = null; - } - - private static void RenameLegacyRunsOnValues(IList runsOn) - { - for (int i = 0; i < runsOn?.Count(); i++) - { - if (runsOn[i].Equals(TaskRunsOnConstants.RunsOnMachineGroup, StringComparison.OrdinalIgnoreCase)) - { - runsOn[i] = TaskRunsOnConstants.RunsOnDeploymentGroup; - } - } - } - - // - // Private - // - [DataMember(Name = "Visibility", EmitDefaultValue = false)] - private List m_serializedVisibilities; - - [DataMember(Name = "RunsOn", EmitDefaultValue = false)] - private List m_serializedRunsOn; - - [DataMember(Name = "OutputVariables", EmitDefaultValue = false)] - private List m_serializedOutputVariables; - - private Dictionary m_preJobExecution; - private Dictionary m_execution; - private Dictionary m_postJobExecution; - private List m_demands; - private List m_inputs; - private List m_satisfies; - private List m_sourceDefinitions; - private List m_dataSourceBindings; - private List m_groups; - private List m_outputVariables; - private List m_visibilities; - private List m_runsOn; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskDefinitionEndpoint.cs b/src/Sdk/DTWebApi/WebApi/TaskDefinitionEndpoint.cs deleted file mode 100644 index 7480da311..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskDefinitionEndpoint.cs +++ /dev/null @@ -1,87 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskDefinitionEndpoint - { - /// - /// The scope as understood by Connected Services. - /// Essentialy, a project-id for now. - /// - [DataMember] - public String Scope - { - get; - set; - } - - /// - /// URL to GET. - /// - [DataMember] - public String Url - { - get; - set; - } - - /// - /// An XPath/Json based selector to filter response returned by fetching - /// the endpoint Url. An XPath based selector must be prefixed with - /// the string "xpath:". A Json based selector must be prefixed with "jsonpath:". - /// - /// The following selector defines an XPath for extracting nodes named 'ServiceName'. - /// - /// endpoint.Selector = "xpath://ServiceName"; - /// - /// - /// - [DataMember] - public String Selector - { - get; - set; - } - - /// - /// An Json based keyselector to filter response returned by fetching - /// the endpoint Url.A Json based keyselector must be prefixed with "jsonpath:". - /// KeySelector can be used to specify the filter to get the keys for the values specified with Selector. - /// - /// The following keyselector defines an Json for extracting nodes named 'ServiceName'. - /// - /// endpoint.KeySelector = "jsonpath://ServiceName"; - /// - /// - /// - [DataMember] - public String KeySelector - { - get; - set; - } - - /// - /// An ID that identifies a service connection to be used for authenticating - /// endpoint requests. - /// - [DataMember] - public String ConnectionId - { - get; - set; - } - - /// - /// TaskId that this endpoint belongs to. - /// - [DataMember] - public String TaskId - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskDefinitionReference.cs b/src/Sdk/DTWebApi/WebApi/TaskDefinitionReference.cs deleted file mode 100644 index 28acbcba0..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskDefinitionReference.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskDefinitionReference - { - public TaskDefinitionReference() - { - // Default is Task - this.DefinitionType = TaskDefinitionType.Task; - } - - private TaskDefinitionReference(TaskDefinitionReference definitionReference) - { - this.Id = definitionReference.Id; - this.VersionSpec = definitionReference.VersionSpec; - - // If it is null, we set it to task - this.DefinitionType = definitionReference.DefinitionType ?? TaskDefinitionType.Task; - } - - /// - /// Gets or sets the unique identifier of task. - /// - [DataMember(IsRequired = true)] - public Guid Id { get; set; } - - /// - /// Gets or sets the version specification of task. - /// - [DataMember(IsRequired = true)] - public String VersionSpec { get; set; } - - /// - /// Gets or sets the definition type. Values can be 'task' or 'metaTask'. - /// - [DataMember(IsRequired = true)] - public String DefinitionType - { - get - { - return this.m_definitionType ?? (this.m_definitionType = TaskDefinitionType.Task); - } - - set - { - this.m_definitionType = value; - } - } - - public override bool Equals(object obj) - { - var toEqual = (TaskDefinitionReference)obj; - if (toEqual == null) - { - return false; - } - - return this.Id.Equals(toEqual.Id) && - (this.VersionSpec?.Equals(toEqual.VersionSpec) ?? this.VersionSpec == toEqual.VersionSpec) && - (this.DefinitionType?.Equals(toEqual.DefinitionType) ?? this.DefinitionType == toEqual.DefinitionType); - } - - public override int GetHashCode() - { - return this.ToString().GetHashCode(); - } - - internal TaskDefinitionReference Clone() - { - return new TaskDefinitionReference(this); - } - - private String m_definitionType; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskDefinitionType.cs b/src/Sdk/DTWebApi/WebApi/TaskDefinitionType.cs deleted file mode 100644 index 83bf7eaee..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskDefinitionType.cs +++ /dev/null @@ -1,12 +0,0 @@ - -using System; - -namespace GitHub.DistributedTask.WebApi -{ - public class TaskDefinitionType - { - public const String Task = "task"; - - public const String MetaTask = "metaTask"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskExecution.cs b/src/Sdk/DTWebApi/WebApi/TaskExecution.cs deleted file mode 100644 index 32b02264c..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskExecution.cs +++ /dev/null @@ -1,68 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskExecution - { - public TaskExecution() - { - } - - private TaskExecution(TaskExecution taskExecutionToBeCloned) - { - if (taskExecutionToBeCloned.ExecTask != null) - { - this.ExecTask = taskExecutionToBeCloned.ExecTask.Clone(); - } - - if (taskExecutionToBeCloned.PlatformInstructions != null) - { - this.PlatformInstructions = new Dictionary>(taskExecutionToBeCloned.PlatformInstructions, StringComparer.OrdinalIgnoreCase); - } - } - - /// - /// The utility task to run. Specifying this means that this task definition is simply a meta task to call another task. - /// This is useful for tasks that call utility tasks like powershell and commandline - /// - [DataMember(Order = 10, EmitDefaultValue = false)] - public TaskReference ExecTask - { - get; - set; - } - - /// - /// If a task is going to run code, then this provides the type/script etc... information by platform. - /// For example, it might look like. - /// net45: { - /// typeName: "GitHub.Automation.Tasks.PowerShellTask", - /// assemblyName: "GitHub.Automation.Tasks.PowerShell.dll" - /// } - /// net20: { - /// typeName: "GitHub.Automation.Tasks.PowerShellTask", - /// assemblyName: "GitHub.Automation.Tasks.PowerShell.dll" - /// } - /// java: { - /// jar: "powershelltask.tasks.automation.teamfoundation.microsoft.com", - /// } - /// node: { - /// script: "powershellhost.js", - /// } - /// - [DataMember(Order = 20, EmitDefaultValue = false)] - public Dictionary> PlatformInstructions - { - get; - set; - } - - internal TaskExecution Clone() - { - return new TaskExecution(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroup.cs b/src/Sdk/DTWebApi/WebApi/TaskGroup.cs deleted file mode 100644 index 1d57777ea..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroup.cs +++ /dev/null @@ -1,173 +0,0 @@ -using System; -using System.Runtime.Serialization; -using System.Collections.Generic; -using System.Linq; - -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskGroup: TaskDefinition - { - /// - /// A task group lets you to encapsulate a sequence of tasks already defined in a build definition, a release definition or a task group into a single reusable task. - /// - public TaskGroup() - { - this.DefinitionType = TaskDefinitionType.MetaTask; - } - - private TaskGroup(TaskGroup definition) : base(definition) - { - this.DefinitionType = TaskDefinitionType.MetaTask; - - this.Owner = definition.Owner; - this.Revision = definition.Revision; - this.CreatedOn = definition.CreatedOn; - this.ModifiedOn = definition.ModifiedOn; - this.Comment = definition.Comment; - this.ParentDefinitionId = definition.ParentDefinitionId; - - if (definition.Tasks != null) - { - this.Tasks = new List(definition.Tasks.Select(x => x.Clone())); - } - - if (definition.CreatedBy != null) - { - this.CreatedBy = definition.CreatedBy.Clone(); - } - - if (definition.ModifiedBy != null) - { - this.ModifiedBy = definition.ModifiedBy.Clone(); - } - } - - public IList Tasks - { - get - { - if (m_tasks == null) - { - m_tasks = new List(); - } - - return m_tasks; - } - set - { - if (value == null) - { - m_tasks = new List(); - } - else - { - this.m_tasks = value; - } - } - } - - /// - /// Gets or sets the owner. - /// - [DataMember(EmitDefaultValue = false)] - public String Owner - { - get; - set; - } - - /// - /// Gets or sets revision. - /// - [DataMember] - public Int32 Revision - { - get; - set; - } - - /// - /// Gets or sets the identity who created. - /// - [DataMember] - public IdentityRef CreatedBy - { - get; - set; - } - - /// - /// Gets or sets date on which it got created. - /// - [DataMember] - public DateTime CreatedOn - { - get; - set; - } - - /// - /// Gets or sets the identity who modified. - /// - [DataMember] - public IdentityRef ModifiedBy - { - get; - set; - } - - /// - /// Gets or sets date on which it got modified. - /// - [DataMember] - public DateTime ModifiedOn - { - get; - set; - } - - /// - /// Gets or sets comment. - /// - [DataMember(EmitDefaultValue = false)] - public String Comment - { - get; - set; - } - - /// - /// Gets or sets parent task group Id. This is used while creating a draft task group. - /// - [DataMember(EmitDefaultValue = false)] - public Guid? ParentDefinitionId - { - get; - set; - } - - /// - /// Gets or sets as 'true' to indicate as deleted, 'false' otherwise. - /// - [DataMember(EmitDefaultValue = false)] - public bool Deleted - { - get; - set; - } - - internal new TaskGroup Clone() - { - return new TaskGroup(this); - } - - /// - /// Gets or sets the tasks. - /// - [DataMember(Name = "Tasks")] - private IList m_tasks; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupCreateParameter.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupCreateParameter.cs deleted file mode 100644 index 0ac49e6c8..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupCreateParameter.cs +++ /dev/null @@ -1,140 +0,0 @@ -using System; -using System.Runtime.Serialization; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskGroupCreateParameter - { - /// - /// Sets name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - - /// - /// Sets friendly name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String FriendlyName { get; set; } - - /// - /// Sets author name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Author { get; set; } - - /// - /// Sets description of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description { get; set; } - - /// - /// Sets parent task group Id. This is used while creating a draft task group. - /// - [DataMember(EmitDefaultValue = false)] - public Guid? ParentDefinitionId { get; set; } - - /// - /// Sets url icon of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String IconUrl { get; set; } - - /// - /// Sets display name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String InstanceNameFormat { get; set; } - - /// - /// Sets category of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Category { get; set; } - - /// - /// Sets version of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public TaskVersion Version { get; set; } - - public IList RunsOn - { - get - { - if (m_runsOn == null) - { - m_runsOn = new List(TaskRunsOnConstants.DefaultValue); - } - - return m_runsOn; - } - } - - public IList Tasks - { - get - { - if (m_tasks == null) - { - m_tasks = new List(); - } - - return m_tasks; - } - } - - public IList Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new List(); - } - return m_inputs; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedRunsOn, ref m_runsOn, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_runsOn, ref m_serializedRunsOn); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedRunsOn = null; - } - - /// - /// Sets RunsOn of the task group. Value can be 'Agent', 'Server' or 'DeploymentGroup'. - /// - [DataMember(Name = "RunsOn", EmitDefaultValue = false)] - private List m_serializedRunsOn; - - /// - /// Sets tasks for the task group. - /// - [DataMember(Name = "Tasks", EmitDefaultValue = false)] - private IList m_tasks; - - /// - /// Sets input for the task group. - /// - [DataMember(Name = "Inputs", EmitDefaultValue = false)] - private List m_inputs; - - private List m_runsOn; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupDefinition.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupDefinition.cs deleted file mode 100644 index 191ed3e0d..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupDefinition.cs +++ /dev/null @@ -1,96 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskGroupDefinition - { - public TaskGroupDefinition() - { - IsExpanded = false; - } - - private TaskGroupDefinition(TaskGroupDefinition inputDefinitionToClone) - { - this.IsExpanded = inputDefinitionToClone.IsExpanded; - this.Name = inputDefinitionToClone.Name; - this.DisplayName = inputDefinitionToClone.DisplayName; - this.VisibleRule = inputDefinitionToClone.VisibleRule; - - if (inputDefinitionToClone.m_tags != null) - { - this.m_tags = new List(inputDefinitionToClone.m_tags); - } - } - - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String DisplayName - { - get; - set; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean IsExpanded - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String VisibleRule - { - get; - set; - } - - public IList Tags - { - get - { - if (m_tags == null) - { - m_tags = new List(); - } - return m_tags; - } - } - - public TaskGroupDefinition Clone() - { - return new TaskGroupDefinition(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedTags, ref m_tags, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_tags, ref m_serializedTags); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedTags = null; - } - - [DataMember(Name = "Tags", EmitDefaultValue = false)] - private List m_serializedTags; - - private List m_tags; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupExpands.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupExpands.cs deleted file mode 100644 index b9868d577..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupExpands.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace GitHub.DistributedTask.WebApi -{ - using System; - - [Flags] - public enum TaskGroupExpands - { - None = 0, - Tasks = 2, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupQueryOrder.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupQueryOrder.cs deleted file mode 100644 index c21840569..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupQueryOrder.cs +++ /dev/null @@ -1,30 +0,0 @@ -// -------------------------------------------------------------------------------------------------------------------- -// -// 2012-2023, All rights reserved. -// -// -------------------------------------------------------------------------------------------------------------------- - -namespace GitHub.DistributedTask.WebApi -{ - using System.Runtime.Serialization; - - /// - /// Specifies the desired ordering of taskGroups. - /// - [DataContract] - public enum TaskGroupQueryOrder - { - /// - /// Order by createdon ascending. - /// - [EnumMember] - CreatedOnAscending = 0, - - /// - /// Order by createdon descending. - /// - [EnumMember] - CreatedOnDescending = 1, - - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupRevision.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupRevision.cs deleted file mode 100644 index 7f13ec8c2..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupRevision.cs +++ /dev/null @@ -1,34 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskGroupRevision - { - [DataMember] - public Guid TaskGroupId { get; set; } - - [DataMember] - public Int32 Revision { get; set; } - - [DataMember] - public Int32 MajorVersion { get; set; } - - [DataMember] - public IdentityRef ChangedBy { get; set; } - - [DataMember] - public DateTime ChangedDate { get; set; } - - [DataMember] - public AuditAction ChangeType { get; set; } - - [DataMember] - public Int32 FileId { get; set; } - - [DataMember] - public String Comment { get; set; } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupStep.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupStep.cs deleted file mode 100644 index e20fd2775..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupStep.cs +++ /dev/null @@ -1,156 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Represents tasks in the task group. - /// - [DataContract] - public class TaskGroupStep - { - public TaskGroupStep() - { - } - - private TaskGroupStep(TaskGroupStep taskGroupStep) - { - this.DisplayName = taskGroupStep.DisplayName; - this.AlwaysRun = taskGroupStep.AlwaysRun; - this.ContinueOnError = taskGroupStep.ContinueOnError; - this.Enabled = taskGroupStep.Enabled; - this.TimeoutInMinutes = taskGroupStep.TimeoutInMinutes; - this.Inputs = new Dictionary(taskGroupStep.Inputs); - - if (taskGroupStep.m_environment != null) - { - foreach (var property in taskGroupStep.m_environment) - { - this.Environment[property.Key] = property.Value; - } - } - - this.Task = taskGroupStep.Task.Clone(); - } - - /// - /// Gets or sets the display name. - /// - [DataMember] - public String DisplayName - { - get - { - if (this.m_displayName == null) - { - this.m_displayName = String.Empty; - } - - return this.m_displayName; - } - set - { - this.m_displayName = value; - } - } - - /// - /// Gets or sets as 'true' to run the task always, 'false' otherwise. - /// - [DataMember] - public bool AlwaysRun { get; set; } - - /// - /// Gets or sets as 'true' to continue on error, 'false' otherwise. - /// - [DataMember] - public bool ContinueOnError { get; set; } - - /// - /// Gets or sets condition for the task. - /// - [DataMember(EmitDefaultValue = false)] - public String Condition { get; set; } - - /// - /// Gets or sets as task is enabled or not. - /// - [DataMember] - public bool Enabled { get; set; } - - /// - /// Gets or sets the maximum time, in minutes, that a task is allowed to execute on agent before being cancelled by server. A zero value indicates an infinite timeout. - /// - [DataMember] - public int TimeoutInMinutes { get; set; } - - /// - /// Gets or sets dictionary of inputs. - /// - [DataMember] - public IDictionary Inputs { get; set; } - - public IDictionary Environment - { - get - { - if (m_environment == null) - { - m_environment = new Dictionary(StringComparer.Ordinal); - } - return m_environment; - } - } - - /// - /// Gets dictionary of environment variables. - /// - [DataMember(Name = "Environment", EmitDefaultValue = false)] - private Dictionary m_environment; - - /// - /// Gets or sets the reference of the task. - /// - [DataMember] - public TaskDefinitionReference Task { get; set; } - - public static bool EqualsAndOldTaskInputsAreSubsetOfNewTaskInputs( - TaskGroupStep oldTaskGroupStep, - TaskGroupStep newTaskGroupStep) - { - if (!oldTaskGroupStep.DisplayName.Equals(newTaskGroupStep.DisplayName) - || oldTaskGroupStep.AlwaysRun != newTaskGroupStep.AlwaysRun - || oldTaskGroupStep.Enabled != newTaskGroupStep.Enabled - || oldTaskGroupStep.ContinueOnError != newTaskGroupStep.ContinueOnError - || !oldTaskGroupStep.Task.Equals(newTaskGroupStep.Task)) - { - return false; - } - - if (!(oldTaskGroupStep.Inputs != null && newTaskGroupStep.Inputs != null - && oldTaskGroupStep.Inputs.Keys.All(key => newTaskGroupStep.Inputs.ContainsKey(key) - && newTaskGroupStep.Inputs[key].Equals(oldTaskGroupStep.Inputs[key])))) - { - return false; - } - - if (!(oldTaskGroupStep.Environment != null - && oldTaskGroupStep.Environment.Keys.All(key => newTaskGroupStep.Environment.ContainsKey(key) - && newTaskGroupStep.Environment[key].Equals(oldTaskGroupStep.Environment[key])))) - { - return false; - } - - return true; - } - - internal TaskGroupStep Clone() - { - return new TaskGroupStep(this); - } - - private String m_displayName; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskGroupUpdateParameter.cs b/src/Sdk/DTWebApi/WebApi/TaskGroupUpdateParameter.cs deleted file mode 100644 index 0c9d7ea8a..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskGroupUpdateParameter.cs +++ /dev/null @@ -1,158 +0,0 @@ -using System; -using System.Runtime.Serialization; -using System.Collections.Generic; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskGroupUpdateParameter - { - /// - /// Sets the unique identifier of this field. - /// - [DataMember(EmitDefaultValue = false)] - public Guid Id { get; set; } - - /// - /// Sets name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name { get; set; } - - /// - /// Sets friendly name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String FriendlyName { get; set; } - - /// - /// Sets author name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Author { get; set; } - - /// - /// Sets description of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description { get; set; } - - /// - /// Sets comment of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Comment { get; set; } - - /// - /// Sets revision of the task group. - /// - [DataMember] - public Int32 Revision { get; set; } - - /// - /// Gets or sets parent task group Id. This is used while creating a draft task group. - /// - [DataMember(EmitDefaultValue = false)] - public Guid? ParentDefinitionId { get; set; } - - /// - /// Sets url icon of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String IconUrl { get; set; } - - /// - /// Sets display name of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String InstanceNameFormat { get; set; } - - /// - /// Sets category of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public String Category { get; set; } - - /// - /// Sets version of the task group. - /// - [DataMember(EmitDefaultValue = false)] - public TaskVersion Version { get; set; } - - public IList Tasks - { - get - { - if (m_tasks == null) - { - m_tasks = new List(); - } - - return m_tasks; - } - } - - public IList Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new List(); - } - return m_inputs; - } - } - - public IList RunsOn - { - get - { - if (m_runsOn == null) - { - m_runsOn = new List(TaskRunsOnConstants.DefaultValue); - } - - return m_runsOn; - } - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedRunsOn, ref m_runsOn, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_runsOn, ref m_serializedRunsOn); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedRunsOn = null; - } - - /// - /// Sets tasks for the task group. - /// - [DataMember(Name = "Tasks")] - private IList m_tasks; - - /// - /// Sets input for the task group. - /// - [DataMember(Name = "Inputs", EmitDefaultValue = false)] - private List m_inputs; - - /// - /// Sets RunsOn of the task group. Value can be 'Agent', 'Server' or 'DeploymentGroup'. - /// - [DataMember(Name = "RunsOn", EmitDefaultValue = false)] - private List m_serializedRunsOn; - - private List m_runsOn; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskHttpClient.cs b/src/Sdk/DTWebApi/WebApi/TaskHttpClient.cs index c0691ff6c..fcc1ab6ce 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskHttpClient.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskHttpClient.cs @@ -1,5 +1,4 @@ -using GitHub.DistributedTask.Pipelines.Runtime; -using GitHub.Services.Common; +using GitHub.Services.Common; using GitHub.Services.WebApi; using System; using System.Collections.Generic; @@ -128,20 +127,6 @@ namespace GitHub.DistributedTask.WebApi cancellationToken); } - public Task GetAgentRequestJobAsync( - Guid scopeIdentifier, - String planType, - String orchestrationId, - CancellationToken cancellationToken = default(CancellationToken), - Object userState = null) - { - return base.GetJobInstanceAsync(scopeIdentifier, - planType, - orchestrationId, - userState, - cancellationToken); - } - private readonly ApiResourceVersion m_currentApiVersion = new ApiResourceVersion(2.0, 1); } } diff --git a/src/Sdk/DTWebApi/WebApi/TaskHubLicenseDetails.cs b/src/Sdk/DTWebApi/WebApi/TaskHubLicenseDetails.cs deleted file mode 100644 index 33d637793..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskHubLicenseDetails.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskHubLicenseDetails - { - public static readonly Int32 DefaultFreeLicenseCount = 0; - - [DataMember(Name = "FreeLicenseCount")] - public Int32 FreePrivateLicenseCount; - - [DataMember] - public Int32 FreeHostedLicenseCount; - - [DataMember] - public Int32 EnterpriseUsersCount; - - /// - /// Self-hosted licenses purchased from VSTS directly. - /// - [DataMember(Name = "PurchasedLicenseCount")] - public Int32 PurchasedPrivateLicenseCount; - - /// - /// Microsoft-hosted licenses purchased from VSTS directly. - /// - [DataMember] - public Int32 PurchasedHostedLicenseCount; - - [DataMember] - public Boolean HostedLicensesArePremium; - - /// - /// Microsoft-hosted licenses purchased from secondary marketplaces. - /// - public List MarketplacePurchasedHostedLicenses - { - get - { - if (m_marketplacePurchasedHostedLicenses == null) - { - m_marketplacePurchasedHostedLicenses = new List(); - } - return m_marketplacePurchasedHostedLicenses; - } - } - - [DataMember] - public Int32 TotalLicenseCount; - - [DataMember] - public Boolean HasLicenseCountEverUpdated; - - [DataMember] - public Int32 MsdnUsersCount; - - [DataMember] - public Int32 HostedAgentMinutesFreeCount; - - [DataMember] - public Int32 HostedAgentMinutesUsedCount; - - [DataMember] - public Boolean FailedToReachAllProviders; - - [DataMember] - public Int32 TotalPrivateLicenseCount; - - [DataMember] - public Int32 TotalHostedLicenseCount; - - [DataMember(Name = "MarketplacePurchasedHostedLicenses", EmitDefaultValue = false)] - private List m_marketplacePurchasedHostedLicenses; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskInputDefinition.cs b/src/Sdk/DTWebApi/WebApi/TaskInputDefinition.cs deleted file mode 100644 index 6d4c79cca..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskInputDefinition.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using CommonContracts = GitHub.DistributedTask.Common.Contracts; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskInputDefinition : CommonContracts.TaskInputDefinitionBase - { - public TaskInputDefinition() - : base() - { - } - - private TaskInputDefinition(TaskInputDefinition inputDefinitionToClone) - : base(inputDefinitionToClone) - { - } - - private TaskInputDefinition(TaskInputDefinition inputDefinitionToClone, ISecuredObject securedObject) - : base(inputDefinitionToClone, securedObject) - { - } - - public TaskInputDefinition Clone() - { - return new TaskInputDefinition(this); - } - - public override CommonContracts.TaskInputDefinitionBase Clone(ISecuredObject securedObject) - { - return base.Clone(securedObject); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskInputType.cs b/src/Sdk/DTWebApi/WebApi/TaskInputType.cs deleted file mode 100644 index 3d1227dd1..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskInputType.cs +++ /dev/null @@ -1,15 +0,0 @@ -using CommonContracts = GitHub.DistributedTask.Common.Contracts; -using System.Runtime.Serialization; -using System; - -namespace GitHub.DistributedTask.WebApi -{ - public static class TaskInputType - { - public const String String = CommonContracts.TaskInputType.String; - public const String Repository = CommonContracts.TaskInputType.Repository; - public const String Boolean = CommonContracts.TaskInputType.Boolean; - public const String KeyValue = CommonContracts.TaskInputType.KeyValue; - public const String FilePath = CommonContracts.TaskInputType.FilePath; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskInstance.cs b/src/Sdk/DTWebApi/WebApi/TaskInstance.cs deleted file mode 100644 index 884e81748..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskInstance.cs +++ /dev/null @@ -1,130 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskInstance : TaskReference - { - public TaskInstance() - { - // Enabled defaults to true - this.Enabled = true; - } - - private TaskInstance(TaskInstance taskToBeCloned) - : base(taskToBeCloned) - { - this.InstanceId = taskToBeCloned.InstanceId; - this.DisplayName = taskToBeCloned.DisplayName; - this.Enabled = taskToBeCloned.Enabled; - this.Condition = taskToBeCloned.Condition; - this.ContinueOnError = taskToBeCloned.ContinueOnError; - this.AlwaysRun = taskToBeCloned.AlwaysRun; - this.TimeoutInMinutes = taskToBeCloned.TimeoutInMinutes; - this.RefName = taskToBeCloned.RefName; - - if (taskToBeCloned.m_environment != null) - { - m_environment = new Dictionary(taskToBeCloned.m_environment, StringComparer.Ordinal); - } - } - - [DataMember] - public Guid InstanceId - { - get; - set; - } - - [DataMember] - public String DisplayName - { - get; - set; - } - - [DataMember] - public Boolean Enabled - { - get; - set; - } - - [DataMember] - public String Condition - { - get; - set; - } - - [DataMember] - public Boolean ContinueOnError - { - get; - set; - } - - [DataMember] - public Boolean AlwaysRun - { - get; - set; - } - - [DataMember] - public int TimeoutInMinutes - { - get; - set; - } - - [DataMember] - public String RefName - { - get; - set; - } - - public IDictionary Environment - { - get - { - if (m_environment == null) - { - m_environment = new Dictionary(StringComparer.Ordinal); - } - return m_environment; - } - } - - public override TaskReference Clone() - { - return new TaskInstance(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedEnvironment, ref m_environment, StringComparer.Ordinal, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_environment, ref m_serializedEnvironment); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedEnvironment = null; - } - - private IDictionary m_environment; - - [DataMember(EmitDefaultValue = false, Name = "Environment")] - private IDictionary m_serializedEnvironment; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationContainer.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationContainer.cs deleted file mode 100644 index ed97476e1..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationContainer.cs +++ /dev/null @@ -1,116 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskOrchestrationContainer : TaskOrchestrationItem, IOrchestrationProcess - { - public TaskOrchestrationContainer() - : base(TaskOrchestrationItemType.Container) - { - ContinueOnError = true; - MaxConcurrency = Int32.MaxValue; - } - - [DataMember(EmitDefaultValue = false)] - public Boolean Parallel - { - get; - set; - } - - public List Children - { - get - { - if (m_children == null) - { - m_children = new List(); - } - - return m_children; - } - } - - [DataMember(EmitDefaultValue = false)] - public TaskOrchestrationContainer Rollback - { - get; - set; - } - - [DataMember(EmitDefaultValue = true)] - public Boolean ContinueOnError - { - get; - set; - } - - [DataMember(EmitDefaultValue = true)] - public Int32 MaxConcurrency - { - get; - set; - } - - /// - /// Get additional specifications for this container. - /// - /// - /// This provides an extensibility for consumers of DT SDK to pass additional data - /// to Orchestrations. Each Orchestration is free to interpret this data as appropriate. - /// - public IDictionary Data - { - get - { - if (m_data == null) - { - m_data = new Dictionary(); - } - - return m_data; - } - } - - OrchestrationProcessType IOrchestrationProcess.ProcessType - { - get - { - return OrchestrationProcessType.Container; - } - } - - public IEnumerable GetJobs() - { - var containerQueue = new Queue(); - containerQueue.Enqueue(this); - - while (containerQueue.Count > 0) - { - var currentContainer = containerQueue.Dequeue(); - foreach (var item in currentContainer.Children) - { - switch (item.ItemType) - { - case TaskOrchestrationItemType.Container: - containerQueue.Enqueue((TaskOrchestrationContainer)item); - break; - - case TaskOrchestrationItemType.Job: - yield return item as TaskOrchestrationJob; - break; - } - } - } - } - - [DataMember(Name = "Children")] - private List m_children; - - [DataMember(Name = "Data", EmitDefaultValue = false)] - private IDictionary m_data; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItem.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItem.cs deleted file mode 100644 index d271834ac..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItem.cs +++ /dev/null @@ -1,24 +0,0 @@ -using Newtonsoft.Json; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [KnownType(typeof(TaskOrchestrationContainer))] - [KnownType(typeof(TaskOrchestrationJob))] - [JsonConverter(typeof(TaskOrchestrationItemJsonConverter))] - public abstract class TaskOrchestrationItem - { - protected TaskOrchestrationItem(TaskOrchestrationItemType itemType) - { - this.ItemType = itemType; - } - - [DataMember] - public TaskOrchestrationItemType ItemType - { - get; - private set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemJsonConverter.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemJsonConverter.cs deleted file mode 100644 index f8ead8415..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemJsonConverter.cs +++ /dev/null @@ -1,100 +0,0 @@ -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using Newtonsoft.Json.Serialization; -using System; -using System.Reflection; - -namespace GitHub.DistributedTask.WebApi -{ - internal sealed class TaskOrchestrationItemJsonConverter : VssSecureJsonConverter - { - public override Boolean CanConvert(Type objectType) - { - return typeof(TaskOrchestrationItem).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - var contract = serializer.ContractResolver.ResolveContract(objectType) as JsonObjectContract; - if (contract == null) - { - return existingValue; - } - - JsonProperty property = contract.Properties.GetClosestMatchProperty("ItemType"); - if (property == null) - { - return existingValue; - } - - JToken itemTypeValue; - TaskOrchestrationItemType itemType; - JObject value = JObject.Load(reader); - if (!value.TryGetValue(property.PropertyName, out itemTypeValue)) - { - return existingValue; - } - else - { - if (itemTypeValue.Type == JTokenType.Integer) - { - itemType = (TaskOrchestrationItemType)(Int32)itemTypeValue; - } - else if (itemTypeValue.Type != JTokenType.String || - !Enum.TryParse((String)itemTypeValue, true, out itemType)) - { - return existingValue; - } - } - - Object newValue = null; - switch (itemType) - { - case TaskOrchestrationItemType.Container: - newValue = new TaskOrchestrationContainer(); - break; - - case TaskOrchestrationItemType.Job: - newValue = new TaskOrchestrationJob(); - break; - } - - if (value != null) - { - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - // The virtual method returns false for CanWrite so this should never be invoked - throw new NotSupportedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemType.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemType.cs deleted file mode 100644 index 51755c3a5..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationItemType.cs +++ /dev/null @@ -1,14 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskOrchestrationItemType - { - [EnumMember] - Container, - - [EnumMember] - Job, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationJob.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationJob.cs deleted file mode 100644 index fc6787215..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationJob.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public sealed class TaskOrchestrationJob : TaskOrchestrationItem - { - internal TaskOrchestrationJob() - : base(TaskOrchestrationItemType.Job) - { - this.ExecutionMode = JobExecutionModeTypes.Agent; - } - - public TaskOrchestrationJob( - Guid instanceId, - String name, - String refName, - string executionMode = JobExecutionModeTypes.Agent) - : base(TaskOrchestrationItemType.Job) - { - this.InstanceId = instanceId; - this.Name = name; - this.RefName = refName; - this.ExecutionMode = executionMode; - } - - private TaskOrchestrationJob(TaskOrchestrationJob jobToBeCloned) - : base(jobToBeCloned.ItemType) - { - this.InstanceId = jobToBeCloned.InstanceId; - this.Name = jobToBeCloned.Name; - this.RefName = jobToBeCloned.RefName; - this.ExecutionMode = jobToBeCloned.ExecutionMode; - this.ExecutionTimeout = jobToBeCloned.ExecutionTimeout; - - if (jobToBeCloned.ExecuteAs != null) - { - this.ExecuteAs = new IdentityRef - { - DisplayName = jobToBeCloned.ExecuteAs.DisplayName, - Id = jobToBeCloned.ExecuteAs.Id, - ImageUrl = jobToBeCloned.ExecuteAs.ImageUrl, - IsAadIdentity = jobToBeCloned.ExecuteAs.IsAadIdentity, - IsContainer = jobToBeCloned.ExecuteAs.IsContainer, - ProfileUrl = jobToBeCloned.ExecuteAs.ProfileUrl, - UniqueName = jobToBeCloned.ExecuteAs.UniqueName, - Url = jobToBeCloned.ExecuteAs.Url, - }; - } - - if (jobToBeCloned.m_demands != null) - { - m_demands = jobToBeCloned.Demands.Select(x => x.Clone()).ToList(); - } - - if (jobToBeCloned.m_variables != null) - { - m_variables = new Dictionary(jobToBeCloned.m_variables, StringComparer.OrdinalIgnoreCase); - } - - if (jobToBeCloned.m_tasks != null) - { - m_tasks = jobToBeCloned.m_tasks.Select(x => (TaskInstance)x.Clone()).ToList(); - } - } - - [DataMember] - public Guid InstanceId - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public String RefName - { - get; - set; - } - - [DataMember] - public string ExecutionMode - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public IdentityRef ExecuteAs - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TimeSpan? ExecutionTimeout - { - get; - set; - } - - public List Demands - { - get - { - if (m_demands == null) - { - m_demands = new List(); - } - - return m_demands; - } - } - - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - return m_variables; - } - } - - public List Tasks - { - get - { - if (m_tasks == null) - { - m_tasks = new List(); - } - - return m_tasks; - } - } - - public TaskOrchestrationJob Clone() - { - return new TaskOrchestrationJob(this); - } - - [DataMember(Name = "Demands", EmitDefaultValue = false)] - private List m_demands; - - [DataMember(Name = "Variables", EmitDefaultValue = false)] - private IDictionary m_variables; - - [DataMember(Name = "Tasks", EmitDefaultValue = false)] - private List m_tasks; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlan.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlan.cs deleted file mode 100644 index 11e1cd18f..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlan.cs +++ /dev/null @@ -1,145 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskOrchestrationPlan : TaskOrchestrationPlanReference - { - [DataMember(EmitDefaultValue = false)] - public DateTime? StartTime - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public DateTime? FinishTime - { - get; - set; - } - - [DataMember] - public TaskOrchestrationPlanState State - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskResult? Result - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String ResultCode - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TimelineReference Timeline - { - get; - set; - } - - public PlanEnvironment Environment - { - get - { - return m_environment; - } - set - { - m_environment = value; - m_processEnvironment = value; - } - } - - public TaskOrchestrationContainer Implementation - { - get - { - return m_implementation; - } - set - { - m_process = value; - m_implementation = value; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public IOrchestrationProcess Process - { - get - { - return m_process; - } - set - { - m_process = value; - m_implementation = value as TaskOrchestrationContainer; - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public IOrchestrationEnvironment ProcessEnvironment - { - get - { - return m_processEnvironment; - } - set - { - m_processEnvironment = value; - m_environment = value as PlanEnvironment; - } - } - - [DataMember(EmitDefaultValue = false)] - public Guid RequestedById - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public Guid RequestedForId - { - get; - set; - } - - internal PlanTemplateType TemplateType - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public TaskLogReference InitializationLog - { - get; - set; - } - - // Currently these members are not serialized on the wire since that would technically be an API break for - // the 1.0 version. While additive, existing clients wouldn't understand it and could blow up. Until this - // public model is finalized we will not send this data over the wire and will not revision the API. - private IOrchestrationProcess m_process; - private IOrchestrationEnvironment m_processEnvironment; - - [DataMember(Name = "Environment", EmitDefaultValue = false)] - private PlanEnvironment m_environment; - - [DataMember(Name = "Implementation", EmitDefaultValue = false)] - private TaskOrchestrationContainer m_implementation; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanGroupsQueueMetrics.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanGroupsQueueMetrics.cs deleted file mode 100644 index ddd426e8d..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanGroupsQueueMetrics.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskOrchestrationPlanGroupsQueueMetrics - { - [DataMember] - public PlanGroupStatus Status - { - get; - set; - } - - [DataMember] - public Int32 Count - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanReference.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanReference.cs index 895580316..54b61e600 100644 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanReference.cs +++ b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanReference.cs @@ -62,13 +62,6 @@ namespace GitHub.DistributedTask.WebApi set; } - [IgnoreDataMember] - public OrchestrationProcessType ProcessType - { - get; - internal set; - } - [DataMember] public TaskOrchestrationOwner Definition { diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanState.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanState.cs deleted file mode 100644 index 8fc0b654a..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationPlanState.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public enum TaskOrchestrationPlanState - { - [EnumMember] - InProgress = 1, - - [EnumMember] - Queued = 2, - - [EnumMember] - Completed = 4, - - [EnumMember] - Throttled = 8 - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlan.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlan.cs deleted file mode 100644 index ee2ffeef2..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlan.cs +++ /dev/null @@ -1,72 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskOrchestrationQueuedPlan - { - [DataMember] - public Guid PlanId - { - get; - set; - } - - [DataMember] - public Guid ScopeIdentifier - { - get; - set; - } - - [DataMember] - public String PlanGroup - { - get; - set; - } - - [DataMember] - public Int32 QueuePosition - { - get; - set; - } - - [DataMember] - public Int32 PoolId - { - get; - set; - } - - [DataMember] - public DateTime QueueTime - { - get; - set; - } - - [DataMember] - public DateTime? AssignTime - { - get; - set; - } - - [DataMember] - public TaskOrchestrationOwner Definition - { - get; - set; - } - - [DataMember] - public TaskOrchestrationOwner Owner - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlanGroup.cs b/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlanGroup.cs deleted file mode 100644 index fd5b57576..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOrchestrationQueuedPlanGroup.cs +++ /dev/null @@ -1,61 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskOrchestrationQueuedPlanGroup - { - [DataMember] - public ProjectReference Project - { - get; - internal set; - } - - [DataMember] - public String PlanGroup - { - get; - internal set; - } - - [DataMember] - public Int32 QueuePosition - { - get; - internal set; - } - - [DataMember] - public List Plans - { - get - { - if (this._plans == null) - { - this._plans = new List(); - } - - return this._plans; - } - } - - [DataMember] - public TaskOrchestrationOwner Definition - { - get; - set; - } - - [DataMember] - public TaskOrchestrationOwner Owner - { - get; - set; - } - - private List _plans; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskOutputVariable.cs b/src/Sdk/DTWebApi/WebApi/TaskOutputVariable.cs deleted file mode 100644 index e2ba44d2c..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskOutputVariable.cs +++ /dev/null @@ -1,38 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskOutputVariable - { - public TaskOutputVariable() - { - } - - private TaskOutputVariable(TaskOutputVariable outputDefinitionToClone) - { - this.Name = outputDefinitionToClone.Name; - this.Description = outputDefinitionToClone.Description; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - public TaskOutputVariable Clone() - { - return new TaskOutputVariable(this); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskReference.cs b/src/Sdk/DTWebApi/WebApi/TaskReference.cs deleted file mode 100644 index 5dfbdc3c9..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskReference.cs +++ /dev/null @@ -1,87 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskReference : ITaskDefinitionReference - { - public TaskReference() - { - } - - protected TaskReference(TaskReference taskToBeCloned) - { - this.Id = taskToBeCloned.Id; - this.Name = taskToBeCloned.Name; - this.Version = taskToBeCloned.Version; - - if (taskToBeCloned.m_inputs != null) - { - m_inputs = new Dictionary(taskToBeCloned.m_inputs, StringComparer.OrdinalIgnoreCase); - } - } - - [DataMember] - public Guid Id - { - get; - set; - } - - [DataMember] - public String Name - { - get; - set; - } - - [DataMember] - public String Version - { - get; - set; - } - - public IDictionary Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - return m_inputs; - } - } - - public virtual TaskReference Clone() - { - return new TaskReference(this); - } - - [OnDeserialized] - private void OnDeserialized(StreamingContext context) - { - SerializationHelper.Copy(ref m_serializedInputs, ref m_inputs, StringComparer.OrdinalIgnoreCase, true); - } - - [OnSerializing] - private void OnSerializing(StreamingContext context) - { - SerializationHelper.Copy(ref m_inputs, ref m_serializedInputs); - } - - [OnSerialized] - private void OnSerialized(StreamingContext context) - { - m_serializedInputs = null; - } - - private IDictionary m_inputs; - - [DataMember(EmitDefaultValue = false, Name = "Inputs")] - private IDictionary m_serializedInputs; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskRunsOnConstants.cs b/src/Sdk/DTWebApi/WebApi/TaskRunsOnConstants.cs deleted file mode 100644 index fdddf9e10..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskRunsOnConstants.cs +++ /dev/null @@ -1,23 +0,0 @@ -using System.Collections.Generic; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - [GenerateAllConstants] - public class TaskRunsOnConstants - { - public const string RunsOnAgent = "Agent"; - public const string RunsOnMachineGroup = "MachineGroup"; - public const string RunsOnDeploymentGroup = "DeploymentGroup"; - public const string RunsOnServer = "Server"; - - public static readonly List DefaultValue = new List { RunsOnAgent, RunsOnDeploymentGroup }; - - public static readonly List RunsOnAllTypes = new List - { - RunsOnAgent, - RunsOnDeploymentGroup, - RunsOnServer, - }; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskSourceDefinition.cs b/src/Sdk/DTWebApi/WebApi/TaskSourceDefinition.cs deleted file mode 100644 index 698c0bb08..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskSourceDefinition.cs +++ /dev/null @@ -1,35 +0,0 @@ -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using CommonContracts = GitHub.DistributedTask.Common.Contracts; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskSourceDefinition : CommonContracts.TaskSourceDefinitionBase - { - public TaskSourceDefinition() - : base() - { - } - - private TaskSourceDefinition(TaskSourceDefinition inputDefinitionToClone) - : base(inputDefinitionToClone) - { - } - - private TaskSourceDefinition(TaskSourceDefinition inputDefinitionToClone, ISecuredObject securedObject) - : base(inputDefinitionToClone, securedObject) - { - } - - public TaskSourceDefinition Clone() - { - return new TaskSourceDefinition(this); - } - - public override CommonContracts.TaskSourceDefinitionBase Clone(ISecuredObject securedObject) - { - return new TaskSourceDefinition(this, securedObject); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskVersion.cs b/src/Sdk/DTWebApi/WebApi/TaskVersion.cs deleted file mode 100644 index b10d0a89a..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskVersion.cs +++ /dev/null @@ -1,182 +0,0 @@ -using GitHub.Services.Common; -using System; -using System.Globalization; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class TaskVersion : IComparable, IEquatable - { - public TaskVersion() - { - } - - public TaskVersion(String version) - { - Int32 major, minor, patch; - String semanticVersion; - - VersionParser.ParseVersion(version, out major, out minor, out patch, out semanticVersion); - Major = major; - Minor = minor; - Patch = patch; - - if (semanticVersion != null) - { - if (semanticVersion.Equals("test", StringComparison.OrdinalIgnoreCase)) - { - IsTest = true; - } - else - { - throw new ArgumentException("semVer"); - } - } - } - - private TaskVersion(TaskVersion taskVersionToClone) - { - this.IsTest = taskVersionToClone.IsTest; - this.Major = taskVersionToClone.Major; - this.Minor = taskVersionToClone.Minor; - this.Patch = taskVersionToClone.Patch; - } - - [DataMember] - public Int32 Major - { - get; - set; - } - - [DataMember] - public Int32 Minor - { - get; - set; - } - - [DataMember] - public Int32 Patch - { - get; - set; - } - - [DataMember] - public Boolean IsTest - { - get; - set; - } - - public TaskVersion Clone() - { - return new TaskVersion(this); - } - - public static implicit operator String(TaskVersion version) - { - return version.ToString(); - } - - public override String ToString() - { - String suffix = String.Empty; - if (IsTest) - { - suffix = "-test"; - } - - return String.Format(CultureInfo.InvariantCulture, "{0}.{1}.{2}{3}", Major, Minor, Patch, suffix); - } - - public override int GetHashCode() - { - return this.ToString().GetHashCode(); - } - - public Int32 CompareTo(TaskVersion other) - { - Int32 rc = Major.CompareTo(other.Major); - if (rc == 0) - { - rc = Minor.CompareTo(other.Minor); - if (rc == 0) - { - rc = Patch.CompareTo(other.Patch); - if (rc == 0 && this.IsTest != other.IsTest) - { - rc = this.IsTest ? -1 : 1; - } - } - } - - return rc; - } - - public Boolean Equals(TaskVersion other) - { - if (other is null) - { - return false; - } - - return this.CompareTo(other) == 0; - } - - public override bool Equals(object obj) - { - return Equals(obj as TaskVersion); - } - - public static Boolean operator ==(TaskVersion v1, TaskVersion v2) - { - if (v1 is null) - { - return v2 is null; - } - - return v1.Equals(v2); - } - - public static Boolean operator !=(TaskVersion v1, TaskVersion v2) - { - if (v1 is null) - { - return !(v2 is null); - } - - return !v1.Equals(v2); - } - - public static Boolean operator <(TaskVersion v1, TaskVersion v2) - { - ArgumentUtility.CheckForNull(v1, nameof(v1)); - ArgumentUtility.CheckForNull(v2, nameof(v2)); - return v1.CompareTo(v2) < 0; - } - - public static Boolean operator >(TaskVersion v1, TaskVersion v2) - { - ArgumentUtility.CheckForNull(v1, nameof(v1)); - ArgumentUtility.CheckForNull(v2, nameof(v2)); - return v1.CompareTo(v2) > 0; - } - - public static Boolean operator <=(TaskVersion v1, TaskVersion v2) - { - ArgumentUtility.CheckForNull(v1, nameof(v1)); - ArgumentUtility.CheckForNull(v2, nameof(v2)); - return v1.CompareTo(v2) <= 0; - } - - public static Boolean operator >=(TaskVersion v1, TaskVersion v2) - { - ArgumentUtility.CheckForNull(v1, nameof(v1)); - ArgumentUtility.CheckForNull(v2, nameof(v2)); - return v1.CompareTo(v2) >= 0; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TaskVersionSpec.cs b/src/Sdk/DTWebApi/WebApi/TaskVersionSpec.cs deleted file mode 100644 index a8617d287..000000000 --- a/src/Sdk/DTWebApi/WebApi/TaskVersionSpec.cs +++ /dev/null @@ -1,239 +0,0 @@ -using GitHub.Services.Common; -using System; -using System.Collections.Generic; -using System.Globalization; -using System.Linq; -using System.Text; - -namespace GitHub.DistributedTask.WebApi -{ - public sealed class TaskVersionSpec - { - /// - /// Gets or sets the major version component. - /// - public Int32? Major - { - get; - set; - } - - /// - /// Gets or sets the minor version component. - /// - public Int32? Minor - { - get; - set; - } - - /// - /// Gets or sets the patch version component. - /// - public Int32? Patch - { - get; - set; - } - - /// - /// Gets or sets a value locking the semantic version to test. - /// - public Boolean IsTest - { - get; - set; - } - - /// - /// Provides a string representation of the version specification. - /// - /// A printable string representation of a version specification - public override String ToString() - { - StringBuilder sb = new StringBuilder(); - if (this.Major == null) - { - sb.Append("*"); - } - else - { - sb.Append(this.Major.Value); - if (this.Minor != null) - { - sb.AppendFormat(CultureInfo.InvariantCulture, ".{0}", this.Minor.Value); - if (this.Patch != null) - { - sb.AppendFormat(CultureInfo.InvariantCulture, ".{0}", this.Patch.Value); - } - else - { - sb.Append(".*"); - } - } - else - { - sb.Append(".*"); - } - } - - if (this.IsTest) - { - sb.Append("-test"); - } - - return sb.ToString(); - } - - /// - /// Provides an explicit conversion constructor for converting from a String. - /// - /// The version specification string - /// A version specification object - /// When the provided version string is not valid - public static explicit operator TaskVersionSpec(String version) - { - return Parse(version); - } - - /// - /// Finds the closest version match for the current specification. If no match can be found then a null - /// value is returned. - /// - /// The list of versions available for matching - /// The version which matches the specification if found; otherwise, null - public TaskVersion Match(IEnumerable versions) - { - ArgumentUtility.CheckForNull(versions, nameof(versions)); - - // Do not evaluate until the end so we only actually iterate the list a single time. Since LINQ returns - // lazy evaluators from the Where method, we can avoid multiple iterations by leaving the variable - // as IEnumerable and performing the iteration after all clauses have been concatenated. - var matchedVersions = versions.Where(x => x.IsTest == this.IsTest); - if (this.Major != null) - { - matchedVersions = matchedVersions.Where(x => x.Major == this.Major); - if (this.Minor != null) - { - matchedVersions = matchedVersions.Where(x => x.Minor == this.Minor); - if (this.Patch != null) - { - matchedVersions = matchedVersions.Where(x => x.Patch == this.Patch); - } - } - } - - return matchedVersions.OrderByDescending(x => x).FirstOrDefault(); - } - - public TaskDefinition Match(IEnumerable definitions) - { - ArgumentUtility.CheckForNull(definitions, nameof(definitions)); - - // Do not evaluate until the end so we only actually iterate the list a single time. Since LINQ returns - // lazy evaluators from the Where method, we can avoid multiple iterations by leaving the variable - // as IEnumerable and performing the iteration after all clauses have been concatenated. - var matchedDefinitions = definitions.Where(x => x.Version.IsTest == this.IsTest); - if (this.Major != null) - { - matchedDefinitions = matchedDefinitions.Where(x => x.Version.Major == this.Major); - if (this.Minor != null) - { - matchedDefinitions = matchedDefinitions.Where(x => x.Version.Minor == this.Minor); - if (this.Patch != null) - { - matchedDefinitions = matchedDefinitions.Where(x => x.Version.Patch == this.Patch); - } - } - } - - return matchedDefinitions.OrderByDescending(x => x.Version).FirstOrDefault(); - } - - public static TaskVersionSpec Parse(String version) - { - TaskVersionSpec versionSpec; - if (!TryParse(version, out versionSpec)) - { - throw new ArgumentException(String.Format(CultureInfo.InvariantCulture, "The value {0} is not a valid version specification", version), "version"); - } - return versionSpec; - } - - public static Boolean TryParse( - String version, - out TaskVersionSpec versionSpec) - { - String[] versionComponents = version.Split(new[] { '.' }, StringSplitOptions.RemoveEmptyEntries); - if (versionComponents.Length < 1 || versionComponents.Length > 3) - { - versionSpec = null; - return false; - } - - Int32? major = null; - Int32? minor = null; - Int32? patch = null; - Boolean isTest = false; - String lastComponent = versionComponents[versionComponents.Length - 1]; - if (lastComponent.EndsWith("-test", StringComparison.OrdinalIgnoreCase)) - { - isTest = true; - versionComponents[versionComponents.Length - 1] = lastComponent.Remove(lastComponent.Length - "-test".Length); - } - - if (versionComponents.Length == 1) - { - if (!TryParseVersionComponent(version, "major", versionComponents[0], true, out major)) - { - versionSpec = null; - return false; - } - } - else if (versionComponents.Length == 2) - { - if (!TryParseVersionComponent(version, "major", versionComponents[0], false, out major) || - !TryParseVersionComponent(version, "minor", versionComponents[1], true, out minor)) - { - versionSpec = null; - return false; - } - } - else - { - if (!TryParseVersionComponent(version, "major", versionComponents[0], false, out major) || - !TryParseVersionComponent(version, "minor", versionComponents[1], false, out minor) || - !TryParseVersionComponent(version, "patch", versionComponents[2], true, out patch)) - { - versionSpec = null; - return false; - } - } - - versionSpec = new TaskVersionSpec { Major = major, Minor = minor, Patch = patch, IsTest = isTest }; - return true; - } - - private static Boolean TryParseVersionComponent( - String version, - String name, - String value, - Boolean allowStar, - out Int32? versionValue) - { - versionValue = null; - - Int32 parsedVersion; - if (Int32.TryParse(value, out parsedVersion)) - { - versionValue = parsedVersion; - } - else if (!allowStar || value != "*") - { - return false; - } - - return true; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/TimelineRecord.cs b/src/Sdk/DTWebApi/WebApi/TimelineRecord.cs index 5c5334f2f..8403c3ac2 100644 --- a/src/Sdk/DTWebApi/WebApi/TimelineRecord.cs +++ b/src/Sdk/DTWebApi/WebApi/TimelineRecord.cs @@ -58,11 +58,6 @@ namespace GitHub.DistributedTask.WebApi }; } - if (recordToBeCloned.Task != null) - { - this.Task = recordToBeCloned.Task.Clone(); - } - if (recordToBeCloned.m_issues?.Count> 0) { this.Issues.AddRange(recordToBeCloned.Issues.Select(i => i.Clone())); @@ -238,13 +233,6 @@ namespace GitHub.DistributedTask.WebApi } } - [DataMember(EmitDefaultValue = false, Order = 70)] - public TaskReference Task - { - get; - set; - } - [DataMember(Order = 100)] public Uri Location { diff --git a/src/Sdk/DTWebApi/WebApi/ValidationItem.cs b/src/Sdk/DTWebApi/WebApi/ValidationItem.cs deleted file mode 100644 index c5c45341b..000000000 --- a/src/Sdk/DTWebApi/WebApi/ValidationItem.cs +++ /dev/null @@ -1,60 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - [KnownType(typeof(ExpressionValidationItem))] - [KnownType(typeof(InputValidationItem))] - [JsonConverter(typeof(ValidationItemJsonConverter))] - public class ValidationItem - { - protected ValidationItem(String type) - { - this.Type = type; - } - - /// - /// Type of validation item - /// - [DataMember(EmitDefaultValue = false)] - public String Type - { - get; - private set; - } - - /// - /// Value to validate. - /// The conditional expression to validate for the input for "expression" type - /// Eg:eq(variables['Build.SourceBranch'], 'refs/heads/master');eq(value, 'refs/heads/master') - /// - [DataMember(EmitDefaultValue = false)] - public String Value - { - get; - set; - } - - /// - /// Tells whether the current input is valid or not - /// - [DataMember(EmitDefaultValue = false)] - public Boolean? IsValid - { - get; - set; - } - - /// - /// Reason for input validation failure - /// - [DataMember(EmitDefaultValue = false)] - public String Reason - { - get; - set; - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ValidationItemJsonConverter.cs b/src/Sdk/DTWebApi/WebApi/ValidationItemJsonConverter.cs deleted file mode 100644 index c3ee45c76..000000000 --- a/src/Sdk/DTWebApi/WebApi/ValidationItemJsonConverter.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; -using System.Reflection; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; -using Newtonsoft.Json.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - internal sealed class ValidationItemJsonConverter : VssSecureJsonConverter - { - public override Boolean CanConvert(Type objectType) - { - return typeof(ValidationItem).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - if (reader.TokenType != JsonToken.StartObject) - { - return null; - } - - Object newValue = null; - - if (objectType == typeof(ExpressionValidationItem)) - { - newValue = new ExpressionValidationItem(); - } - else if (objectType == typeof(InputValidationItem)) - { - newValue = new InputValidationItem(); - } - - JObject value = JObject.Load(reader); - - if (newValue == null) - { - var contract = serializer.ContractResolver.ResolveContract(objectType) as JsonObjectContract; - if (contract == null) - { - return existingValue; - } - - JsonProperty property = contract.Properties.GetClosestMatchProperty("Type"); - if (property == null) - { - return existingValue; - } - - JToken itemTypeValue; - String itemType = InputValidationTypes.Expression; - if (value.TryGetValue(property.PropertyName, out itemTypeValue) - && itemTypeValue.Type == JTokenType.String) - { - itemType = (String)itemTypeValue; - } - - switch (itemType) - { - case InputValidationTypes.Expression: - newValue = new ExpressionValidationItem(); - break; - case InputValidationTypes.Input: - newValue = new InputValidationItem(); - break; - } - } - - if (value != null) - { - using (JsonReader objectReader = value.CreateReader()) - { - serializer.Populate(objectReader, newValue); - } - } - - return newValue; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - // The virtual method returns false for CanWrite so this should never be invoked - throw new NotSupportedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ValidationRequest.cs b/src/Sdk/DTWebApi/WebApi/ValidationRequest.cs deleted file mode 100644 index d50009aac..000000000 --- a/src/Sdk/DTWebApi/WebApi/ValidationRequest.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [DataContract] - public class InputValidationRequest - { - public IDictionary Inputs - { - get - { - if (m_inputs == null) - { - m_inputs = new Dictionary(StringComparer.Ordinal); - } - - return m_inputs; - } - } - - [DataMember(Name = "Inputs")] - private Dictionary m_inputs; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/ValidationTypes.cs b/src/Sdk/DTWebApi/WebApi/ValidationTypes.cs deleted file mode 100644 index 7c6391b18..000000000 --- a/src/Sdk/DTWebApi/WebApi/ValidationTypes.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - [GenerateAllConstants] - public static class InputValidationTypes - { - public const String Expression = "expression"; - public const String Input = "input"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroup.cs b/src/Sdk/DTWebApi/WebApi/VariableGroup.cs deleted file mode 100644 index 8f6bb2f4a..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroup.cs +++ /dev/null @@ -1,244 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// A variable group is a collection of related variables. - /// - [JsonConverter(typeof(VariableGroupJsonConverter))] - [DataContract] - public class VariableGroup - { - public VariableGroup() - { - } - - private VariableGroup(VariableGroup group) - { - this.Id = group.Id; - this.Type = group.Type; - this.Name = group.Name; - this.Description = group.Description; - this.ProviderData = group.ProviderData; - this.CreatedBy = group.CreatedBy; - this.CreatedOn = group.CreatedOn; - this.ModifiedBy = group.ModifiedBy; - this.ModifiedOn = group.ModifiedOn; - this.IsShared = group.IsShared; - this.Variables = group.Variables.ToDictionary(x => x.Key, x => x.Value.Clone()); - } - - /// - /// Gets or sets id of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public Int32 Id - { - get; - set; - } - - /// - /// Gets or sets type of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Type - { - get; - set; - } - - /// - /// Gets or sets name of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Gets or sets description of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - /// - /// Gets or sets provider data. - /// - [DataMember(EmitDefaultValue = false)] - public VariableGroupProviderData ProviderData - { - get; - set; - } - - /// - /// Gets or sets the identity who created the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef CreatedBy - { - get; - set; - } - - /// - /// Gets or sets the time when variable group was created. - /// - [DataMember(EmitDefaultValue = false)] - public DateTime CreatedOn - { - get; - set; - } - - /// - /// Gets or sets the identity who modified the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public IdentityRef ModifiedBy - { - get; - set; - } - - /// - /// Gets or sets the time when variable group was modified - /// - [DataMember(EmitDefaultValue = false)] - public DateTime ModifiedOn - { - get; - set; - } - - /// - /// Indicates whether variable group is shared with other projects or not. - /// - [DataMember(EmitDefaultValue = true)] - public Boolean IsShared - { - get; - set; - } - - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - return m_variables; - } - set - { - if (value == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - else - { - m_variables = new Dictionary(value, StringComparer.OrdinalIgnoreCase); - } - } - } - - public VariableGroup Clone() - { - return new VariableGroup(this); - } - - /// - /// Gets or sets variables contained in the variable group. - /// - [DataMember(EmitDefaultValue = false, Name = "Variables")] - private Dictionary m_variables; - } - - internal sealed class VariableGroupJsonConverter : VssSecureJsonConverter - { - public override Boolean CanRead - { - get - { - return true; - } - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(VariableGroup).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - var variableGroupJsonObject = JObject.Load(reader); - var variablesJsonObject = variableGroupJsonObject.GetValue("Variables", StringComparison.OrdinalIgnoreCase); - var providerDataJsonObject = variableGroupJsonObject.GetValue("ProviderData", StringComparison.OrdinalIgnoreCase); - - String variablesJson = null; - if (variablesJsonObject != null) - { - variablesJson = variablesJsonObject.ToString(); - } - - String providerDataJson = null; - if (providerDataJsonObject != null) - { - providerDataJson = providerDataJsonObject.ToString(); - } - - VariableGroup variableGroup = new VariableGroup(); - using (var objectReader = variableGroupJsonObject.CreateReader()) - { - serializer.Populate(objectReader, variableGroup); - } - - if (String.IsNullOrEmpty(variableGroup.Type)) - { - // To handle backward compat with clients making api calls without type - variableGroup.Type = VariableGroupType.Vsts; - } - - variableGroup.PopulateVariablesAndProviderData(variablesJson, providerDataJson); - - return variableGroup; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupActionFilter.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupActionFilter.cs deleted file mode 100644 index d5edb907e..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupActionFilter.cs +++ /dev/null @@ -1,19 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - [Flags] - [DataContract] - public enum VariableGroupActionFilter - { - [EnumMember] - None = 0, - - [EnumMember] - Manage = 2, - - [EnumMember] - Use = 16, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupParameters.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupParameters.cs deleted file mode 100644 index c455cdfe4..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupParameters.cs +++ /dev/null @@ -1,159 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; -using System.Text; -using System.Threading.Tasks; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using Newtonsoft.Json.Linq; - -namespace GitHub.DistributedTask.WebApi -{ - [JsonConverter(typeof(VariableGroupParametersJsonConverter))] - [DataContract] - public class VariableGroupParameters - { - /// - /// Sets type of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Type - { - get; - set; - } - - /// - /// Sets name of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - /// - /// Sets description of the variable group. - /// - [DataMember(EmitDefaultValue = false)] - public String Description - { - get; - set; - } - - /// - /// Sets provider data. - /// - [DataMember(EmitDefaultValue = false)] - public VariableGroupProviderData ProviderData - { - get; - set; - } - - public IDictionary Variables - { - get - { - if (m_variables == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - - return m_variables; - } - set - { - if (value == null) - { - m_variables = new Dictionary(StringComparer.OrdinalIgnoreCase); - } - else - { - m_variables = new Dictionary(value, StringComparer.OrdinalIgnoreCase); - } - } - } - - /// - /// Sets variables contained in the variable group. - /// - [DataMember(EmitDefaultValue = false, Name = "Variables")] - private Dictionary m_variables; - } - - internal sealed class VariableGroupParametersJsonConverter : VssSecureJsonConverter - { - public override Boolean CanRead - { - get - { - return true; - } - } - - public override Boolean CanWrite - { - get - { - return false; - } - } - - public override Boolean CanConvert(Type objectType) - { - return typeof(VariableGroupParameters).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - public override Object ReadJson( - JsonReader reader, - Type objectType, - Object existingValue, - JsonSerializer serializer) - { - var variableGroupJsonObject = JObject.Load(reader); - var variablesJsonObject = variableGroupJsonObject.GetValue("Variables", StringComparison.OrdinalIgnoreCase); - var providerDataJsonObject = variableGroupJsonObject.GetValue("ProviderData", StringComparison.OrdinalIgnoreCase); - - String variablesJson = null; - if (variablesJsonObject != null) - { - variablesJson = variablesJsonObject.ToString(); - } - - String providerDataJson = null; - if (providerDataJsonObject != null) - { - providerDataJson = providerDataJsonObject.ToString(); - } - - VariableGroupParameters variableGroupParameters = new VariableGroupParameters(); - using (var objectReader = variableGroupJsonObject.CreateReader()) - { - serializer.Populate(objectReader, variableGroupParameters); - } - - if (String.IsNullOrEmpty(variableGroupParameters.Type)) - { - // To handle backward compat with clients making api calls without type - variableGroupParameters.Type = VariableGroupType.Vsts; - } - - variableGroupParameters.PopulateVariablesAndProviderData(variablesJson, providerDataJson); - - return variableGroupParameters; - } - - public override void WriteJson( - JsonWriter writer, - Object value, - JsonSerializer serializer) - { - throw new NotImplementedException(); - } - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupProviderData.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupProviderData.cs deleted file mode 100644 index 1f90d1310..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupProviderData.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Defines provider data of the variable group. - /// - [KnownType(typeof(AzureKeyVaultVariableGroupProviderData))] - [DataContract] - public class VariableGroupProviderData - { - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupQueryOrder.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupQueryOrder.cs deleted file mode 100644 index e8736c18e..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupQueryOrder.cs +++ /dev/null @@ -1,29 +0,0 @@ -// -------------------------------------------------------------------------------------------------------------------- -// -// 2012-2023, All rights reserved. -// -// -------------------------------------------------------------------------------------------------------------------- - -namespace GitHub.DistributedTask.WebApi -{ - using System.Runtime.Serialization; - - /// - /// Specifies the desired ordering of variableGroups. - /// - [DataContract] - public enum VariableGroupQueryOrder - { - /// - /// Order by id ascending. - /// - [EnumMember] - IdAscending = 0, - - /// - /// Order by id descending. - /// - [EnumMember] - IdDescending = 1, - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupType.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupType.cs deleted file mode 100644 index 8c7e5f40d..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupType.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using GitHub.Services.Common; - -namespace GitHub.DistributedTask.WebApi -{ - [GenerateAllConstants] - public static class VariableGroupType - { - public const String Vsts = "Vsts"; - public const String AzureKeyVault = "AzureKeyVault"; - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableGroupUtility.cs b/src/Sdk/DTWebApi/WebApi/VariableGroupUtility.cs deleted file mode 100644 index 1de79ddf8..000000000 --- a/src/Sdk/DTWebApi/WebApi/VariableGroupUtility.cs +++ /dev/null @@ -1,318 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using GitHub.Services.WebApi; - -namespace GitHub.DistributedTask.WebApi -{ - /// - /// Utility class to perform operations on Variable groups. - /// - public static class VariableGroupUtility - { - public static VariableValue Clone(this VariableValue value) - { - if (keyVaultVariableType == value.GetType()) - { - return new AzureKeyVaultVariableValue((AzureKeyVaultVariableValue)value); - } - - return new VariableValue(value); - } - - public static void PopulateVariablesAndProviderData(this VariableGroup group, String variablesJson, String providerDataJson) - { - switch (group.Type) - { - case VariableGroupType.Vsts: - if (variablesJson != null) - { - group.Variables = JsonUtility.FromString>(variablesJson); - } - - if (providerDataJson != null) - { - group.ProviderData = JsonUtility.FromString(providerDataJson); - } - - break; - - case VariableGroupType.AzureKeyVault: - if (variablesJson != null) - { - var azureKeyVaultVariableValues = JsonUtility.FromString>(variablesJson); - if (azureKeyVaultVariableValues != null) - { - foreach (var azureKeyVaultVariableValue in azureKeyVaultVariableValues) - { - group.Variables[azureKeyVaultVariableValue.Key] = azureKeyVaultVariableValue.Value; - } - } - } - - if (providerDataJson != null) - { - group.ProviderData = JsonUtility.FromString(providerDataJson); - } - - break; - } - } - - public static void PopulateVariablesAndProviderData(this VariableGroupParameters variableGroupParameters, String variablesJson, String providerDataJson) - { - switch (variableGroupParameters.Type) - { - case VariableGroupType.Vsts: - if (variablesJson != null) - { - variableGroupParameters.Variables = JsonUtility.FromString>(variablesJson); - } - - if (providerDataJson != null) - { - variableGroupParameters.ProviderData = JsonUtility.FromString(providerDataJson); - } - - break; - - case VariableGroupType.AzureKeyVault: - if (variablesJson != null) - { - var azureKeyVaultVariableValues = JsonUtility.FromString>(variablesJson); - if (azureKeyVaultVariableValues != null) - { - foreach (var azureKeyVaultVariableValue in azureKeyVaultVariableValues) - { - variableGroupParameters.Variables[azureKeyVaultVariableValue.Key] = azureKeyVaultVariableValue.Value; - } - } - } - - if (providerDataJson != null) - { - variableGroupParameters.ProviderData = JsonUtility.FromString(providerDataJson); - } - - break; - } - } - - /// - /// Get list of cloned variable groups - /// - /// - /// - public static IList CloneVariableGroups(IList source) - { - var clonedVariableGroups = new List(); - if (source == null) - { - return clonedVariableGroups; - } - - foreach (var group in source) - { - if (group != null) - { - clonedVariableGroups.Add(group.Clone()); - } - } - - return clonedVariableGroups; - } - - /// - /// Replace secret values in group variables with null - /// - /// Variable groups to be cleared for secret variables - /// List of cleared variable groups - public static IList ClearSecrets(IList variableGroups) - { - var groups = new List(); - - if (variableGroups == null) - { - return groups; - } - - foreach (var group in variableGroups) - { - if (group != null) - { - var clearedGroup = group.Clone(); - - // Replacing secret variable's value with null - foreach (var variable in clearedGroup.Variables) - { - if (variable.Value != null && variable.Value.IsSecret) - { - variable.Value.Value = null; - } - } - - groups.Add(clearedGroup); - } - } - - return groups; - } - - /// - /// Replace all secrets in variables with null - /// - /// Variable set - /// Dictionary of variables - public static IDictionary ClearSecrets(IDictionary variables) - { - var dictionary = new Dictionary(StringComparer.OrdinalIgnoreCase); - - if (variables == null) - { - return dictionary; - } - - foreach (var kvp in variables) - { - if (kvp.Value != null) - { - var clonedValue = kvp.Value.Clone(); - - if (kvp.Value.IsSecret) - { - clonedValue.Value = null; - } - - dictionary[kvp.Key] = clonedValue; - } - } - - return dictionary; - } - - /// - /// Check if any variable group has variable with secret value - /// - /// Variable groups to check if contains any secret variable with value. - /// Result - public static bool HasSecretWithValue(IList variableGroups) - { - if (variableGroups == null || variableGroups.Count == 0) - { - return false; - } - - foreach (var group in variableGroups) - { - if (group != null && HasSecretWithValue(group.Variables)) - { - return true; - } - } - - return false; - } - - /// - /// Check if Variables has any secret value - /// - /// Variable set to check for any secret value - /// - public static bool HasSecretWithValue(IDictionary variables) - { - if (variables == null || variables.Count == 0) - { - return false; - } - - return variables.Any(s => s.Value != null && - s.Value.IsSecret && - !String.IsNullOrEmpty(s.Value.Value)); - } - - /// - /// Check if any secret variable exists in variable group - /// - /// Variable groups to check if contains any secret variable - /// Result - public static bool HasSecret(IList variableGroups) - { - if (variableGroups == null || variableGroups.Count == 0) - { - return false; - } - - foreach (var group in variableGroups) - { - if (group != null && HasSecret(group.Variables)) - { - return true; - } - } - - return false; - } - - /// - /// Check if variable set contains any secret variable - /// - /// Variable set to be checked for secret variable - /// - public static bool HasSecret(IDictionary variables) - { - if (variables != null) - { - return variables.Any(v => v.Value != null && v.Value.IsSecret); - } - - return false; - } - - /// - /// Copies secrets from source variable groups to target variable groups - /// - /// Source variable groups - /// Target variable groups - /// - public static void FillSecrets( - IList sourceGroups, - IList targetGroups) - { - if (sourceGroups == null || sourceGroups.Count == 0) - { - return; - } - - if (targetGroups == null) - { - throw new ArgumentNullException("targetGroups"); - } - - foreach (var sourceGroup in sourceGroups) - { - var targetGroup = targetGroups.FirstOrDefault(group => group.Id == sourceGroup.Id); - - if (targetGroup != null) - { - if (sourceGroup.Variables == null || sourceGroup.Variables.Count == 0) - { - // nothing to fill - continue; - } - - if (targetGroup.Variables == null) - { - throw new ArgumentNullException(nameof(targetGroup.Variables)); - } - - foreach (var variable in sourceGroup.Variables.Where(x => x.Value.IsSecret)) - { - targetGroup.Variables[variable.Key] = variable.Value.Clone(); - } - } - } - } - - private static Type keyVaultVariableType = typeof(AzureKeyVaultVariableValue); - } -} diff --git a/src/Sdk/DTWebApi/WebApi/VariableUtility.cs b/src/Sdk/DTWebApi/WebApi/VariableUtility.cs index ae537b47c..8d0ff3e6e 100644 --- a/src/Sdk/DTWebApi/WebApi/VariableUtility.cs +++ b/src/Sdk/DTWebApi/WebApi/VariableUtility.cs @@ -13,309 +13,9 @@ namespace GitHub.DistributedTask.WebApi { public static class VariableUtility { - public static EnableAccessTokenType GetEnableAccessTokenType(IDictionary variables) + public static VariableValue Clone(this VariableValue value) { - EnableAccessTokenType type; - if (variables != null && - variables.TryGetValue(WellKnownDistributedTaskVariables.EnableAccessToken, out VariableValue enableVariable) && - enableVariable != null) - { - Enum.TryParse(enableVariable.Value, true, out type); - } - else - { - type = EnableAccessTokenType.None; - } - - return type; + return new VariableValue(value); } - - public static Boolean IsVariable(String value) - { - return s_variableReferenceRegex.Value.IsMatch(value); - } - - /// - /// Replaces variables by recursively cloning tokens in a JObject or JArray by - /// Walks tokens and uses ExpandVariables(string, vars) to resolve all string tokens - /// - /// root token must be a JObject or JArray - /// key value variables to replace in the $(xxx) format - /// root token of cloned tree - public static JToken ExpandVariables(JToken token, IDictionary replacementDictionary, bool useMachineVariables = true) - { - var mapFuncs = new Dictionary> - { - { - JTokenType.String, - (t) => VariableUtility.ExpandVariables(t.ToString(), replacementDictionary, useMachineVariables) - } - }; - - return token.Map(mapFuncs); - } - - public static JToken ExpandVariables( - JToken token, - VariablesDictionary additionalVariableReplacements, - Boolean useMachineVariables) - { - return ExpandVariables(token, (IDictionary)additionalVariableReplacements, useMachineVariables); - } - - /// - /// Replaces multiple variable sets by recursively cloning tokens in a JObject or JArray. - /// Walks tokens and uses ExpandVariables(string, vars) for each set of variables on all string tokens - /// - /// root token must be a JObject or JArray - /// list of replacement key value pairs in the $(xxx) format - /// root token of cloned tree - public static JToken ExpandVariables(JToken token, IList> replacementsList) - { - var mapFuncs = new Dictionary> - { - { - JTokenType.String, - (t) => replacementsList.Aggregate(t, (current, replacementVariables) => ExpandVariables(current.ToString(), replacementVariables)) - } - }; - - return token.Map(mapFuncs); - } - - /// - /// An overload method for ExpandVariables - /// Expand variables in the input provided using the dictionary and the machine's environment variables - /// - public static String ExpandVariables(String input, IDictionary additionalVariableReplacements) - { - return ExpandVariables(input, additionalVariableReplacements, true); - } - - /// - /// Replaces variable references of the form $(variable) with the corresponding replacement value. Values - /// populated into the environment directly are used first. If no value is found in the automation environment - /// then the machine environment variables will be used as a fall back. - /// - /// The value which should be analyzed for environment variables and updated accordingly - /// Use the machine's environment variables when it is true - /// A new value with all variables expanded to their current value based on the environment - public static String ExpandVariables(String input, IDictionary additionalVariableReplacements, bool useMachineVariables) - { - // Do a quick up-front check against a regular expression to determine whether or not there is any - // reason to allocate memory to replace values in the input - if (!s_variableReferenceRegex.Value.IsMatch(input)) - { - return input; - } - - StringBuilder sb = new StringBuilder(input); - List referencedVariables = GetReferencedVariables(input); - for (Int32 i = 0; i < referencedVariables.Count; i++) - { - // The variable reference is of the format $(variable), so we start at index 2 and cut off the last ')' - // character by extracting a length of 3 less than the original length. - String variableName = referencedVariables[i].Substring(2, referencedVariables[i].Length - 3); - - String replacementValue; - if (!additionalVariableReplacements.TryGetValue(variableName, out replacementValue) && useMachineVariables) - { - replacementValue = System.Environment.GetEnvironmentVariable(variableName); - } - - if (replacementValue != null) - { - sb.Replace(referencedVariables[i], replacementValue); - } - } - - return sb.ToString(); - } - - /// - /// Replaces variable references of the form $(variable) with the corresponding replacement value. Values - /// populated into the environment directly are used first. If no value is found in the automation environment - /// then the machine environment variables will be used as a fall back. - /// - /// The value which should be analyzed for environment variables and updated accordingly - /// Use the machine's environment variables when it is true - /// A new value with all variables expanded to their current value based on the environment - public static String ExpandVariables( - String input, - VariablesDictionary additionalVariableReplacements, - Boolean useMachineVariables, - Boolean maskSecrets = false) - { - return ExpandVariables(input, (IDictionary)additionalVariableReplacements, useMachineVariables, maskSecrets); - } - - /// - /// Replaces variable references of the form $(variable) with the corresponding replacement value. Values - /// populated into the environment directly are used first. If no value is found in the automation environment - /// then the machine environment variables will be used as a fall back. - /// - /// The value which should be analyzed for environment variables and updated accordingly - /// Use the machine's environment variables when it is true - /// A new value with all variables expanded to their current value based on the environment - public static String ExpandVariables( - String input, - IDictionary additionalVariableReplacements, - Boolean useMachineVariables, - Boolean maskSecrets = false) - { - if (String.IsNullOrEmpty(input)) - { - return input; - } - - StringBuilder sb = new StringBuilder(input); - List referencedVariables = GetReferencedVariables(input); - for (Int32 i = 0; i < referencedVariables.Count; i++) - { - // The variable reference is of the format $(variable), so we start at index 2 and cut off the last ')' - // character by extracting a length of 3 less than the original length. - String variableName = referencedVariables[i].Substring(2, referencedVariables[i].Length - 3); - - VariableValue replacementValue; - if (!additionalVariableReplacements.TryGetValue(variableName, out replacementValue) && useMachineVariables) - { - replacementValue = new VariableValue { Value = System.Environment.GetEnvironmentVariable(variableName) }; - } - - if (replacementValue != null) - { - var value = replacementValue.Value; - if (replacementValue.IsSecret && maskSecrets) - { - value = "***"; - } - - sb.Replace(referencedVariables[i], value); - } - } - - return sb.ToString(); - } - - /// - /// Replaces variable references of the form variables['variable_name'] with corresponding replacement values - /// - /// Task condition - /// List of variables and their replacement values - /// - public static String ExpandConditionVariables(String condition, IDictionary additionalVariableReplacements, bool useMachineVariables) - { - // Do a quick up-front check against a regular expression to determine whether or not there is any - // reason to allocate memory to replace values in the input - if (!s_conditionVariableReferenceRegex.Value.IsMatch(condition)) - { - return condition; - } - - StringBuilder sb = new StringBuilder(condition); - MatchCollection matches = s_conditionVariableReferenceRegex.Value.Matches(condition); - - for (Int32 i = 0; i < matches.Count; i++) - { - if (matches[i].Length != 0 && matches[i].Groups.Count >= 2) - { - String referencedVariable = matches[i].Groups[0].Value; - String variableName = matches[i].Groups[1].Value; - - String replacementValue; - if (!additionalVariableReplacements.TryGetValue(variableName, out replacementValue) && useMachineVariables) - { - replacementValue = System.Environment.GetEnvironmentVariable(variableName); - } - - if (replacementValue != null) - { - string convertedValue = PrepareReplacementStringForConditions(replacementValue); - sb.Replace(referencedVariable, convertedValue); - } - } - } - - return sb.ToString(); - } - - /// - /// Prepare replacement string from the given input. For a normal input, add ' around it. - /// Convert a variable of format ${var} to variables['var'] to suit custom conditions - /// - /// input replacement value - /// - public static String PrepareReplacementStringForConditions(String replacementValue) - { - if (replacementValue == null || !IsVariable(replacementValue)) - { - return String.Format(CultureInfo.InvariantCulture, c_conditionReplacementFormat, replacementValue); - } - - List variables = GetReferencedVariables(replacementValue); - - if (variables.Count != 1 || replacementValue.Trim() != variables[0]) - { - return String.Format(CultureInfo.InvariantCulture, c_conditionReplacementFormat, replacementValue); - } - - // Start from index 2 [after $( ] and continue till last but one - string variableName = variables[0].Substring(2, variables[0].Length - 3); - return string.Format(CultureInfo.InvariantCulture, c_conditionVariableFormat, variableName); - } - - private static List GetReferencedVariables(String input) - { - Int32 nestedCount = -1; - Boolean insideMatch = false; - StringBuilder currentMatch = new StringBuilder(); - HashSet result = new HashSet(); - for (int i = 0; i < input.Length; i++) - { - if (!insideMatch && input[i] == '$' && i + 1 < input.Length && input[i + 1] == '(') - { - insideMatch = true; - } - - if (insideMatch) - { - currentMatch.Append(input[i]); - } - - if (insideMatch && input[i] == '(') - { - nestedCount++; - } - - if (insideMatch && input[i] == ')') - { - if (nestedCount == 0) - { - result.Add(currentMatch.ToString()); - currentMatch.Clear(); - insideMatch = false; - nestedCount = -1; - } - else - { - nestedCount--; - } - } - } - - if (insideMatch || nestedCount >= 0) - { - // We didn't finish the last match, that means it isn't correct so we will ignore it - Debug.Fail("We didn't finish the last match!!!!!"); - } - - return result.ToList(); - } - - private static readonly Lazy s_variableReferenceRegex = new Lazy(() => new Regex(@"\$\(([^)]+)\)", RegexOptions.Singleline | RegexOptions.Compiled), true); - private static readonly Lazy s_conditionVariableReferenceRegex = new Lazy(() => new Regex(@"variables\['([^']+)\']", RegexOptions.Singleline | RegexOptions.Compiled), true); - private const String c_conditionReplacementFormat = "'{0}'"; - private const String c_variableFormat = "$({0})"; - private const String c_conditionVariableFormat = "variables['{0}']"; } } diff --git a/src/Sdk/DTWebApi/WebApi/VariableValue.cs b/src/Sdk/DTWebApi/WebApi/VariableValue.cs index 99e1d8597..178590ceb 100644 --- a/src/Sdk/DTWebApi/WebApi/VariableValue.cs +++ b/src/Sdk/DTWebApi/WebApi/VariableValue.cs @@ -4,7 +4,6 @@ using System.Runtime.Serialization; namespace GitHub.DistributedTask.WebApi { [DataContract] - [KnownType(typeof(AzureKeyVaultVariableValue))] public class VariableValue { public VariableValue() diff --git a/src/Sdk/DTWebApi/WebApi/WellKnownDistributedTaskVariables.cs b/src/Sdk/DTWebApi/WebApi/WellKnownDistributedTaskVariables.cs index d0c80f868..a5495bc03 100644 --- a/src/Sdk/DTWebApi/WebApi/WellKnownDistributedTaskVariables.cs +++ b/src/Sdk/DTWebApi/WebApi/WellKnownDistributedTaskVariables.cs @@ -4,50 +4,6 @@ namespace GitHub.DistributedTask.WebApi { public static class WellKnownDistributedTaskVariables { - public static readonly String AccessToken = "system.accessToken"; - public static readonly String AccessTokenScope = "system.connection.accessTokenScope"; - public static readonly String AzureUserAgent = "AZURE_HTTP_USER_AGENT"; - public static readonly String CollectionId = "system.collectionId"; - public static readonly String CollectionUrl = "system.collectionUri"; - public static readonly String Culture = "system.culture"; - public static readonly String DefinitionId = "system.definitionId"; - public static readonly String DefinitionName = "system.definitionName"; - public static readonly String EnableAccessToken = "system.enableAccessToken"; - public static readonly String HostType = "system.hosttype"; - public static readonly String HubVersion = "system.hubversion"; - public static readonly String IsScheduled = "system.isScheduled"; - public static readonly String JobAttempt = "system.jobAttempt"; - public static readonly String JobDisplayName = "system.jobDisplayName"; public static readonly String JobId = "system.jobId"; - public static readonly String JobIdentifier = "system.jobIdentifier"; - public static readonly String JobName = "system.jobName"; - public static readonly String JobParallelismTag = "system.jobParallelismTag"; - public static readonly String JobPositionInPhase = "System.JobPositionInPhase"; - public static readonly String JobStatus = "system.jobStatus"; - public static readonly String MsDeployUserAgent = "MSDEPLOY_HTTP_USER_AGENT"; - public static readonly String ParallelExecutionType = "System.ParallelExecutionType"; - public static readonly String PhaseAttempt = "system.phaseAttempt"; - public static readonly String PhaseDisplayName = "system.phaseDisplayName"; - public static readonly String PhaseId = "system.phaseId"; - public static readonly String PhaseName = "system.phaseName"; - public static readonly String PipelineStartTime = "system.pipelineStartTime"; - public static readonly String PlanId = "system.planId"; - public static readonly String RestrictSecrets = "system.restrictSecrets"; - public static readonly String RetainDefaultEncoding = "agent.retainDefaultEncoding"; - public static readonly String ServerType = "system.servertype"; - public static readonly String StageAttempt = "system.stageAttempt"; - public static readonly String StageDisplayName = "system.stageDisplayName"; - public static readonly String StageId = "system.stageId"; - public static readonly String StageName = "system.stageName"; - public static readonly String System = "system"; - public static readonly String TFCollectionUrl = "system.teamFoundationCollectionUri"; - public static readonly String TaskDefinitionsUrl = "system.taskDefinitionsUri"; - public static readonly String TaskDisplayName = "system.taskDisplayName"; - public static readonly String TaskInstanceId = "system.taskInstanceId"; - public static readonly String TaskInstanceName = "system.taskInstanceName"; - public static readonly String TeamProject = "system.teamProject"; - public static readonly String TeamProjectId = "system.teamProjectId"; - public static readonly String TimelineId = "system.timelineId"; - public static readonly String TotalJobsInPhase = "System.TotalJobsInPhase"; } } diff --git a/src/Sdk/DTWebApi/WebApi/WellKnownPackageTypes.cs b/src/Sdk/DTWebApi/WebApi/WellKnownPackageTypes.cs deleted file mode 100644 index 3b088c7b0..000000000 --- a/src/Sdk/DTWebApi/WebApi/WellKnownPackageTypes.cs +++ /dev/null @@ -1,9 +0,0 @@ -using System; - -namespace GitHub.DistributedTask.WebApi -{ - public static class WellKnownPackageTypes - { - public static readonly String Agent = "agent"; - } -} diff --git a/src/Sdk/InternalsVisibleTo.cs b/src/Sdk/InternalsVisibleTo.cs index 42a5445ae..1aeebd320 100644 --- a/src/Sdk/InternalsVisibleTo.cs +++ b/src/Sdk/InternalsVisibleTo.cs @@ -1,9 +1,4 @@ using System.Runtime.CompilerServices; -// [assembly: InternalsVisibleTo("Runner.Common")] -// [assembly: InternalsVisibleTo("Runner.PluginHost")] -//[assembly: InternalsVisibleTo("Runner.Plugins")] -// [assembly: InternalsVisibleTo("Runner.Listener")] -// [assembly: InternalsVisibleTo("Runner.Sdk")] [assembly: InternalsVisibleTo("Runner.Worker")] [assembly: InternalsVisibleTo("Test")] \ No newline at end of file diff --git a/src/Sdk/Namespaces.cs b/src/Sdk/Namespaces.cs index d2b8143cd..e71d84f41 100644 --- a/src/Sdk/Namespaces.cs +++ b/src/Sdk/Namespaces.cs @@ -1,8 +1,16 @@ -namespace AsyncFixer +namespace AsyncFixer { } -namespace GitHub.DistributedTask.Common.Contracts +namespace GitHub.Actions.Pipelines.WebApi +{ +} + +namespace GitHub.Actions.Pipelines.WebApi.Contracts +{ +} + +namespace GitHub.Build.WebApi { } @@ -10,7 +18,23 @@ namespace GitHub.DistributedTask.Expressions { } -namespace GitHub.DistributedTask.Expressions.CollectionAccessors +namespace GitHub.DistributedTask.Expressions2 +{ +} + +namespace GitHub.DistributedTask.Expressions2.Sdk +{ +} + +namespace GitHub.DistributedTask.Expressions2.Sdk.Functions +{ +} + +namespace GitHub.DistributedTask.Expressions2.Sdk.Operators +{ +} + +namespace GitHub.DistributedTask.Expressions2.Tokens { } @@ -30,18 +54,10 @@ namespace GitHub.DistributedTask.ObjectTemplating.Tokens { } -namespace GitHub.DistributedTask.Orchestration.Server.Artifacts -{ -} - namespace GitHub.DistributedTask.Pipelines { } -namespace GitHub.DistributedTask.Pipelines.Artifacts -{ -} - namespace GitHub.DistributedTask.Pipelines.ContextData { } @@ -54,10 +70,6 @@ namespace GitHub.DistributedTask.Pipelines.ObjectTemplating { } -namespace GitHub.DistributedTask.Pipelines.Runtime -{ -} - namespace GitHub.DistributedTask.Pipelines.Validation { } @@ -70,6 +82,10 @@ namespace GitHub.GraphProfile.WebApi { } +namespace GitHub.Services +{ +} + namespace GitHub.Services.Account { } @@ -90,10 +106,6 @@ namespace GitHub.Services.CentralizedFeature { } -namespace GitHub.Services.Client -{ -} - namespace GitHub.Services.ClientNotification { } @@ -142,6 +154,10 @@ namespace GitHub.Services.FileContainer { } +namespace GitHub.Services.FileContainer.Client +{ +} + namespace GitHub.Services.FormInput { } @@ -282,6 +298,10 @@ namespace GitHub.Services.WebApi { } +namespace GitHub.Services.WebApi.Exceptions +{ +} + namespace GitHub.Services.WebApi.Internal { } diff --git a/src/Sdk/Resources/ContentResources.g.cs b/src/Sdk/Resources/ContentResources.g.cs deleted file mode 100644 index d9c4970c9..000000000 --- a/src/Sdk/Resources/ContentResources.g.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System.Globalization; - -namespace GitHub.Services.Content.Common -{ - public static class ContentResources - { - - public static string InvalidHexString(object arg0) - { - const string Format = @"Invalid hex string. The string value provided {0} is not a valid hex string."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string ArtifactBillingException() - { - const string Format = @"Artifact cannot be uploaded because max quantity has been exceeded or the payment instrument is invalid."; - return Format; - } - } -} diff --git a/src/Sdk/Resources/GraphResources.g.cs b/src/Sdk/Resources/GraphResources.g.cs deleted file mode 100644 index 067dd6539..000000000 --- a/src/Sdk/Resources/GraphResources.g.cs +++ /dev/null @@ -1,92 +0,0 @@ -using System.Globalization; - -namespace GitHub.Services.WebApi -{ - public static class GraphResources - { - - public static string CannotEditChildrenOfNonGroup(object arg0) - { - const string Format = @"VS403339: Cannot add or remove child from graph subject with descriptor '{0}' because it is not a group."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string EmptySubjectDescriptorNotAllowed(object arg0) - { - const string Format = @"VS403350: The empty subject descriptor is not a valid value for parameter '{0}'"; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string WellKnownSidNotAllowed(object arg0) - { - const string Format = @"VS403350: Well-known SIDs are not valid for the parameter '{0}'"; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string GraphMembershipNotFound(object arg0, object arg1) - { - const string Format = @"VS403328: The graph membership for member descriptor '{0}' and container descriptor '{1}' could not be found. You may need to create this membership in the enclosing enterprise or organization."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0, arg1); - } - - public static string GraphSubjectNotFound(object arg0) - { - const string Format = @"VS403325: The graph subject with descriptor '{0}' could not be found. You may need to create the subject in the enclosing enterprise, or add organization-level memberships to make a subject in the enterprise visible in the enclosing organization"; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string InvalidGraphLegacyDescriptor(object arg0) - { - const string Format = @"VS860018: The provided legacy descriptor '{0}' is not a valid legacy descriptor for this end point."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string InvalidGraphMemberCuid(object arg0) - { - const string Format = @"VS403323: Cannot find graph member storage key for cuid: {0}"; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string InvalidGraphMemberStorageKey(object arg0) - { - const string Format = @"VS403324: Cannot find graph member cuid for storage key {0}"; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string InvalidGraphSubjectDescriptor(object arg0) - { - const string Format = @"VS860021: The provided descriptor '{0}' is not a valid graph subject descriptor for this end point."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string StorageKeyNotFound(object arg0) - { - const string Format = @"VS403369: The storage key for descriptor '{0}' could not be found."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string SubjectDescriptorNotFoundWithIdentityDescriptor(object arg0) - { - const string Format = @"VS403370: The subject descriptor for identity descriptor '{0}' could not be found."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string SubjectDescriptorNotFoundWithStorageKey(object arg0) - { - const string Format = @"VS403368: The subject descriptor for storage key '{0}' could not be found."; - return string.Format(CultureInfo.CurrentCulture, Format, arg0); - } - - public static string IdentifierLengthOutOfRange() - { - const string Format = @"Given identifier length is out of range of valid values."; - return Format; - } - - public static string SubjectTypeLengthOutOfRange() - { - const string Format = @"Given subject type length is out of range of valid values."; - return Format; - } - } -} diff --git a/src/Sdk/Sdk.csproj b/src/Sdk/Sdk.csproj index 769d4931e..ae11fd81f 100644 --- a/src/Sdk/Sdk.csproj +++ b/src/Sdk/Sdk.csproj @@ -8,7 +8,7 @@ portable-net45+win8 NU1701;NU1603 $(Version) - NETSTANDARD;NET_STANDARD;TRACE + TRACE 7.3 true true @@ -22,7 +22,6 @@ - diff --git a/src/Sdk/WebApi/WebApi/Attributes.cs b/src/Sdk/WebApi/WebApi/Attributes.cs index 375d8debe..51e13db1e 100644 --- a/src/Sdk/WebApi/WebApi/Attributes.cs +++ b/src/Sdk/WebApi/WebApi/Attributes.cs @@ -18,60 +18,6 @@ namespace GitHub.Services.WebApi public readonly Guid AreaId; } - /// - /// Use in conjunction with JsonCompatConverter. This attribute describes a model property or field change at a particular API version. - /// - [AttributeUsage(AttributeTargets.Property | AttributeTargets.Field, AllowMultiple = true)] - public sealed class CompatPropertyAttribute : Attribute - { - /// - /// This attribute describes a model property or field change at a particular API version. - /// - /// Old name of the serialized property. - /// The major version component of the max version of the api to support the old property name. - /// The minor version component of the max version of the api to support the old property name. - public CompatPropertyAttribute(String oldName, Int32 majorApiVersion, Int32 minorApiVersion = 0) - { - OldName = oldName; - MaxApiVersion = new Version(majorApiVersion, minorApiVersion); - } - - /// - /// Old name of the serialized property. - /// - public String OldName { get; private set; } - - /// - /// The max version of the api to support the old property name. - /// - public Version MaxApiVersion { get; private set; } - } - - /// - /// This tells the client generator to set this property to the content of the repsonse - /// - [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] - public sealed class ClientResponseContentAttribute : Attribute - { - public ClientResponseContentAttribute() - { - } - } - - /// - /// This tells the client generator to set this property to the header value from the response. This should only be added to types of IEnumerable<String> - /// - [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] - public sealed class ClientResponseHeaderAttribute : Attribute - { - public ClientResponseHeaderAttribute(string headerName) - { - HeaderName = headerName; - } - - public string HeaderName { get; private set; } - } - /// /// Tells the client generator to create meta data for this model, even if it is not referenced directly or indirectly from the client. /// @@ -160,18 +106,4 @@ namespace GitHub.Services.WebApi /// public TimeSpan Timeout { get; private set; } } - - /// - /// Indicates which headers are considered to contain sensitive information by a particular HttpClient. - /// - [AttributeUsage(AttributeTargets.Class)] - public sealed class ClientSensitiveHeaderAttribute : Attribute - { - public string HeaderName { get; set; } - - public ClientSensitiveHeaderAttribute(string headerName) - { - HeaderName = headerName; - } - } } diff --git a/src/Sdk/WebApi/WebApi/Constants.cs b/src/Sdk/WebApi/WebApi/Constants.cs index a94c76230..782772c16 100644 --- a/src/Sdk/WebApi/WebApi/Constants.cs +++ b/src/Sdk/WebApi/WebApi/Constants.cs @@ -5,42 +5,11 @@ using System.Runtime.Serialization; namespace GitHub.Services.WebApi { - // !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! - // This will not be like MS.TF.Framework.Common! - // If your service does not ship in SPS or the Framework SDK you cannot put your stuff here! - // It goes in your own assembly! - // !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! - [GenerateAllConstants] public static class ServiceInstanceTypes { - // !!!!!!!!!!!!!!!!!! - // This class is sealed to new guids -- please define your instance type constant in your own assembly - // !!!!!!!!!!!!!!!!!! - - public const String MPSString = "00000000-0000-8888-8000-000000000000"; - public static readonly Guid MPS = new Guid(MPSString); - - public const String SPSString = "951917AC-A960-4999-8464-E3F0AA25B381"; - public static readonly Guid SPS = new Guid(SPSString); - - public const String TFSString = "00025394-6065-48CA-87D9-7F5672854EF7"; - public static readonly Guid TFS = new Guid(TFSString); - public const String TFSOnPremisesString = "87966EAA-CB2A-443F-BE3C-47BD3B5BF3CB"; public static readonly Guid TFSOnPremises = new Guid(TFSOnPremisesString); - - [Obsolete] - public const String SpsExtensionString = "00000024-0000-8888-8000-000000000000"; - [Obsolete] - public static readonly Guid SpsExtension = new Guid(SpsExtensionString); - - public const String SDKSampleString = "FFFFFFFF-0000-8888-8000-000000000000"; - public static readonly Guid SDKSample = new Guid(SDKSampleString); - - // !!!!!!!!!!!!!!!!!! - // This class is sealed to new guids -- please define your instance type constant in your own assembly - // !!!!!!!!!!!!!!!!!! } /// diff --git a/src/Sdk/WebApi/WebApi/Contracts/Common/SocialDescriptor.cs b/src/Sdk/WebApi/WebApi/Contracts/Common/SocialDescriptor.cs deleted file mode 100644 index ea7daa83d..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Common/SocialDescriptor.cs +++ /dev/null @@ -1,345 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.Graph; -using System.Xml.Serialization; -using System.Xml; -using System.Xml.Schema; -using GitHub.Services.WebApi; -using System.Linq; -using System.Reflection; -using System.ComponentModel; -using System.Globalization; - -namespace GitHub.Services.Common -{ - [TypeConverter(typeof(SocialDescriptorConverter))] - public struct SocialDescriptor : IEquatable, IXmlSerializable - { - public SocialDescriptor(string socialType, string identifier) - { - ValidateSocialType(socialType); - ValidateIdentifier(identifier); - - SocialType = NormalizeSocialType(socialType); - Identifier = identifier; - } - - [DataMember] - public string SocialType { get; private set; } - - [DataMember] - public string Identifier { get; private set; } - - public override string ToString() - { - if (this == default(SocialDescriptor)) - { - return null; - } - - return string.Concat( - Constants.SocialDescriptorPrefix, - SocialType, - Constants.SocialDescriptorPartsSeparator, - PrimitiveExtensions.ToBase64StringNoPaddingFromString(Identifier)); - } - - public static SocialDescriptor FromString(string socialDescriptorString) - { - if (string.IsNullOrEmpty(socialDescriptorString)) - { - return default(SocialDescriptor); - } - - if (!socialDescriptorString.StartsWith(Constants.SocialDescriptorPrefix)) - { - return new SocialDescriptor(Constants.SocialType.Unknown, socialDescriptorString); - } - - if (socialDescriptorString.Length < Constants.SocialDescriptorPolicies.MinSocialDescriptorStringLength) - { - return new SocialDescriptor(Constants.SocialType.Unknown, socialDescriptorString); - } - - var tokens = socialDescriptorString.Split(new char[] { Constants.SocialDescriptorPartsSeparator }, 3); - if (tokens.Length != 2) - { - return new SocialDescriptor(Constants.SocialType.Unknown, socialDescriptorString); - } - - string moniker = tokens[0].Substring(1); - string identifier = tokens[1]; - - try - { - return new SocialDescriptor(moniker, PrimitiveExtensions.FromBase64StringNoPaddingToString(identifier)); - } - catch { } - - return new SocialDescriptor(Constants.SocialType.Unknown, socialDescriptorString); - } - - /// - /// Parses a string of comma separated social descriptors into a enumerable list of objects. - /// - /// empty enumerable if parameter 'descriptors' is null or empty - public static IEnumerable FromCommaSeperatedStrings(string descriptors) - { - if (string.IsNullOrEmpty(descriptors)) - { - return Enumerable.Empty(); - } - - return descriptors.Split(Constants.SocialListSeparator).Where(descriptor => !string.IsNullOrEmpty(descriptor)).Select(descriptor => FromString(descriptor)); - } - - #region Equality and Compare - - #region Implement IEquatable to avoid boxing - public bool Equals(SocialDescriptor socialDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(SocialType, socialDescriptor.SocialType) && - StringComparer.Ordinal.Equals(Identifier, socialDescriptor.Identifier); // The Social Identifier can be case sensitive, hence avoiding the case ignore check - } - #endregion - - public override bool Equals(object obj) - { - return obj is SocialDescriptor && this == (SocialDescriptor)obj; - } - - public override int GetHashCode() - { - if (this == default(SocialDescriptor)) - { - return 0; - } - - int hashCode = 7443; // "large" prime to start the seed - - // Bitshifting and subtracting once is an efficient way to multiply by our second "large" prime, 0x7ffff = 524287 - hashCode = (hashCode << 19) - hashCode + StringComparer.OrdinalIgnoreCase.GetHashCode(SocialType); - hashCode = (hashCode << 19) - hashCode + StringComparer.Ordinal.GetHashCode(Identifier); - - return hashCode; - } - - public static bool operator ==(SocialDescriptor left, SocialDescriptor right) - { - return left.Equals(right); - } - - public static bool operator !=(SocialDescriptor left, SocialDescriptor right) - { - return !left.Equals(right); - } - - public static implicit operator string(SocialDescriptor socialDescriptor) - { - return socialDescriptor.ToString(); - } - - internal static int Compare(SocialDescriptor left, SocialDescriptor right) - { - int retValue = StringComparer.OrdinalIgnoreCase.Compare(left.SocialType, right.SocialType); - - if (0 == retValue) - { - retValue = StringComparer.Ordinal.Compare(left.Identifier, right.Identifier); - } - - return retValue; - } - - private static string NormalizeSocialType(String socialType) - { - // Look up the string in the static dictionary. If we get a hit, then - // we'll use that string for the social type instead. This saves memory - // as well as improves compare/equals performance when comparing descriptors, - // since Object.ReferenceEquals will return true a lot more often - if (!Constants.SocialTypeMap.TryGetValue(socialType, out string normalizedSocialType)) - { - normalizedSocialType = socialType; - } - - return normalizedSocialType; - } - #endregion - - #region Validation - //Copied from TFCommonUtil.cs - private static void ValidateSocialType(string socialType) - { - if (string.IsNullOrEmpty(socialType)) - { - throw new ArgumentNullException(nameof(socialType)); - } - - if (socialType.Length < Constants.SocialDescriptorPolicies.MinSocialTypeLength || socialType.Length > Constants.SocialDescriptorPolicies.MaxSocialTypeLength) - { - throw new ArgumentOutOfRangeException(nameof(socialType), socialType, GraphResources.SubjectTypeLengthOutOfRange()); - } - } - - private static void ValidateIdentifier(string identifier) - { - if (string.IsNullOrEmpty(identifier)) - { - throw new ArgumentNullException(nameof(identifier)); - } - } - - #endregion - - #region XML Serialization - XmlSchema IXmlSerializable.GetSchema() { return null; } - - void IXmlSerializable.ReadXml(XmlReader reader) - { - ArgumentUtility.CheckForNull(reader, nameof(reader)); - - var isEmptyElement = reader.IsEmptyElement; - - reader.ReadStartElement(); - - if (isEmptyElement) - { - return; - } - - if (reader.NodeType == XmlNodeType.Text) - { - var sourceDescriptor = FromString(reader.ReadContentAsString()); - SocialType = sourceDescriptor.SocialType; - Identifier = sourceDescriptor.Identifier; - } - else - { - while (reader.IsStartElement()) - { - switch (reader.Name) - { - case nameof(SocialType): - var socialType = reader.ReadElementContentAsString(); - ValidateSocialType(socialType); - SocialType = socialType; - break; - case nameof(Identifier): - var identifier = reader.ReadElementContentAsString(); - ValidateIdentifier(identifier); - Identifier = identifier; - break; - default: - reader.ReadOuterXml(); - break; - } - } - } - - reader.ReadEndElement(); - } - - void IXmlSerializable.WriteXml(XmlWriter writer) - { - ArgumentUtility.CheckForNull(writer, nameof(writer)); - - if (Equals(default(SocialDescriptor))) - { - return; - } - - writer.WriteElementString(nameof(SocialType), SocialType); - writer.WriteElementString(nameof(Identifier), Identifier); - } - #endregion - } - - public class SocialDescriptorComparer : IComparer, IEqualityComparer - { - private SocialDescriptorComparer() { } - - public int Compare(SocialDescriptor left, SocialDescriptor right) - { - return SocialDescriptor.Compare(left, right); - } - - public bool Equals(SocialDescriptor left, SocialDescriptor right) - { - return left == right; - } - - public int GetHashCode(SocialDescriptor socialDescriptor) - { - return socialDescriptor.GetHashCode(); - } - - public static SocialDescriptorComparer Instance { get; } = new SocialDescriptorComparer(); - } - - public static class SocialDescriptorExtensions - { - public static bool IsGitHubSocialType(this SocialDescriptor socialDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(socialDescriptor.SocialType ?? String.Empty, Constants.SocialType.GitHub); - } - - public static bool IsSocialType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.ToString().StartsWith(Constants.SocialDescriptorPrefix); - } - } - - /// - /// Converter to support data contract serialization. - /// - /// - /// This class should only be used to convert a descriptor string from the client back into a string - /// tuple SocialDescriptor type on the server. The client should be unaware that this tuple relationship exists - /// and this should not permit that relationship to leak to the client. - /// - /// Specifically, this is provided so that the MVC router can convert a string => SocialDescriptor so - /// that we can use the [ClientParameterType(typeof(string))] SocialDescriptor socialDescriptor) convenience in each - /// controller method. - /// - public class SocialDescriptorConverter : TypeConverter - { - public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType) - { - return sourceType == typeof(string) || base.CanConvertFrom(context, sourceType); - } - - public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) - { - return destinationType == typeof(string) || base.CanConvertTo(context, destinationType); - } - - public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value) - { - if (value is string) - { - return SocialDescriptor.FromString((string)value); - } - - return base.ConvertFrom(context, culture, value); - } - - public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType) - { - if (destinationType == typeof(string) && value is SocialDescriptor) - { - SocialDescriptor socialDescriptor = (SocialDescriptor)value; - if (socialDescriptor == default(SocialDescriptor)) - { - // socialDescriptor.ToString() returns null in the case of default(SocialDescriptor) - // and null can not be deserialized when the object is a struct. - return string.Empty; - } - - return socialDescriptor.ToString(); - } - - return base.ConvertTo(context, culture, value, destinationType); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Common/SubjectDescriptor.cs b/src/Sdk/WebApi/WebApi/Contracts/Common/SubjectDescriptor.cs deleted file mode 100644 index b931f222a..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Common/SubjectDescriptor.cs +++ /dev/null @@ -1,519 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.Graph; -using System.Xml.Serialization; -using System.Xml; -using System.Xml.Schema; -using GitHub.Services.WebApi; -using System.Linq; -using System.Reflection; -using System.ComponentModel; -using System.Globalization; - -namespace GitHub.Services.Common -{ - [TypeConverter(typeof(SubjectDescriptorConverter))] - public struct SubjectDescriptor : IEquatable, IXmlSerializable - { - public SubjectDescriptor(string subjectType, string identifier) - { - ValidateSubjectType(subjectType); - ValidateIdentifier(identifier); - - SubjectType = NormalizeSubjectType(subjectType); - Identifier = identifier; - } - - [DataMember] - public string SubjectType { get; private set; } - - [DataMember] - public string Identifier { get; private set; } - - public override string ToString() - { - if (this == default(SubjectDescriptor)) - { - return null; - } - - return string.Concat( - SubjectType, - Constants.SubjectDescriptorPartsSeparator, - PrimitiveExtensions.ToBase64StringNoPaddingFromString(Identifier)); - } - - public static SubjectDescriptor FromString(string subjectDescriptorString) - { - if (string.IsNullOrEmpty(subjectDescriptorString)) - { - return default(SubjectDescriptor); - } - - if (subjectDescriptorString.Length < Constants.SubjectDescriptorPolicies.MinSubjectDescriptorStringLength) - { - return new SubjectDescriptor(Constants.SubjectType.Unknown, subjectDescriptorString); - } - - int splitIndex = subjectDescriptorString.IndexOf(Constants.SubjectDescriptorPartsSeparator, Constants.SubjectDescriptorPolicies.MinSubjectTypeLength, 3); - - // Either the separator is not there, or it's before the MinSubjectTypeLength or it's at the end the string; either way it's wrong. - if (splitIndex < 3 || splitIndex == subjectDescriptorString.Length - 1) - { - return new SubjectDescriptor(Constants.SubjectType.Unknown, subjectDescriptorString); - } - - string moniker = subjectDescriptorString.Substring(0, splitIndex); - string identifier = subjectDescriptorString.Substring(splitIndex + 1); - - try - { - return new SubjectDescriptor(moniker, PrimitiveExtensions.FromBase64StringNoPaddingToString(identifier)); - } - catch { } - - return new SubjectDescriptor(Constants.SubjectType.Unknown, subjectDescriptorString); - } - - /// - /// Parses a string of comma separated subject descriptors into a enumerable list of objects. - /// - /// empty enumerable if parameter 'descriptors' is null or empty - public static IEnumerable FromCommaSeperatedStrings(string descriptors) - { - if (string.IsNullOrEmpty(descriptors)) - { - return Enumerable.Empty(); - } - - return descriptors.Split(',').Where(descriptor => !string.IsNullOrEmpty(descriptor)).Select(descriptor => FromString(descriptor)); - } - - #region Equality and Compare - - #region Implement IEquatable to avoid boxing - public bool Equals(SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(SubjectType, subjectDescriptor.SubjectType) && - StringComparer.OrdinalIgnoreCase.Equals(Identifier, subjectDescriptor.Identifier); - } - #endregion - - public override bool Equals(object obj) - { - return obj is SubjectDescriptor && this == (SubjectDescriptor)obj; - } - - public override int GetHashCode() - { - if (this == default(SubjectDescriptor)) - { - return 0; - } - - int hashCode = 7443; // "large" prime to start the seed - - // Bitshifting and subtracting once is an efficient way to multiply by our second "large" prime, 0x7ffff = 524287 - hashCode = (hashCode << 19) - hashCode + StringComparer.OrdinalIgnoreCase.GetHashCode(SubjectType); - hashCode = (hashCode << 19) - hashCode + StringComparer.OrdinalIgnoreCase.GetHashCode(Identifier); - - return hashCode; - } - - public static bool operator ==(SubjectDescriptor left, SubjectDescriptor right) - { - return left.Equals(right); - } - - public static bool operator !=(SubjectDescriptor left, SubjectDescriptor right) - { - return !left.Equals(right); - } - - public static implicit operator string(SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.ToString(); - } - - internal static int Compare(SubjectDescriptor left, SubjectDescriptor right) - { - int retValue = StringComparer.OrdinalIgnoreCase.Compare(left.SubjectType, right.SubjectType); - - if (0 == retValue) - { - retValue = StringComparer.OrdinalIgnoreCase.Compare(left.Identifier, right.Identifier); - } - - return retValue; - } - - private static string NormalizeSubjectType(String subjectType) - { - // Look up the string in the static dictionary. If we get a hit, then - // we'll use that string for the subject type instead. This saves memory - // as well as improves compare/equals performance when comparing descriptors, - // since Object.ReferenceEquals will return true a lot more often - if (!Constants.SubjectTypeMap.TryGetValue(subjectType, out string normalizedSubjectType)) - { - normalizedSubjectType = subjectType; - } - - return normalizedSubjectType; - } - #endregion - - #region Validation - //Copied from TFCommonUtil.cs - private static void ValidateSubjectType(string subjectType) - { - if (string.IsNullOrEmpty(subjectType)) - { - throw new ArgumentNullException(nameof(subjectType)); - } - - if (subjectType.Length < Constants.SubjectDescriptorPolicies.MinSubjectTypeLength || subjectType.Length > Constants.SubjectDescriptorPolicies.MaxSubjectTypeLength) - { - throw new ArgumentOutOfRangeException(nameof(subjectType), subjectType, GraphResources.SubjectTypeLengthOutOfRange()); - } - } - - private static void ValidateIdentifier(string identifier) - { - if (string.IsNullOrEmpty(identifier)) - { - throw new ArgumentNullException(nameof(identifier)); - } - - if (identifier.Length > Constants.SubjectDescriptorPolicies.MaxIdentifierLength) - { - throw new ArgumentOutOfRangeException(nameof(identifier), identifier, GraphResources.IdentifierLengthOutOfRange()); - } - } - - #endregion - - #region XML Serialization - XmlSchema IXmlSerializable.GetSchema() { return null; } - - void IXmlSerializable.ReadXml(XmlReader reader) - { - ArgumentUtility.CheckForNull(reader, nameof(reader)); - - var isEmptyElement = reader.IsEmptyElement; - - reader.ReadStartElement(); - - if (isEmptyElement) - { - return; - } - - if (reader.NodeType == XmlNodeType.Text) - { - var sourceDescriptor = FromString(reader.ReadContentAsString()); - SubjectType = sourceDescriptor.SubjectType; - Identifier = sourceDescriptor.Identifier; - } - else - { - while (reader.IsStartElement()) - { - switch (reader.Name) - { - case nameof(SubjectType): - var subjectType = reader.ReadElementContentAsString(); - ValidateSubjectType(subjectType); - SubjectType = subjectType; - break; - case nameof(Identifier): - var identifier = reader.ReadElementContentAsString(); - ValidateIdentifier(identifier); - Identifier = identifier; - break; - default: - reader.ReadOuterXml(); - break; - } - } - } - - reader.ReadEndElement(); - } - - void IXmlSerializable.WriteXml(XmlWriter writer) - { - ArgumentUtility.CheckForNull(writer, nameof(writer)); - - if (Equals(default(SubjectDescriptor))) - { - return; - } - - writer.WriteElementString(nameof(SubjectType), SubjectType); - writer.WriteElementString(nameof(Identifier), Identifier); - } - #endregion - } - - public class SubjectDescriptorComparer : IComparer, IEqualityComparer - { - private SubjectDescriptorComparer() { } - - public int Compare(SubjectDescriptor left, SubjectDescriptor right) - { - return SubjectDescriptor.Compare(left, right); - } - - public bool Equals(SubjectDescriptor left, SubjectDescriptor right) - { - return left == right; - } - - public int GetHashCode(SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.GetHashCode(); - } - - public static SubjectDescriptorComparer Instance { get; } = new SubjectDescriptorComparer(); - } - - // Keep this in sync with the IdentityDescriptorExtensions to avoid extra casting/conversions - public static class SubjectDescriptorExtensions - { - internal static Guid GetMasterScopeId(this SubjectDescriptor subjectDescriptor) - { - if (!subjectDescriptor.IsGroupScopeType()) - { - throw new InvalidSubjectTypeException(subjectDescriptor.SubjectType); - } - - if (!Guid.TryParse(subjectDescriptor.Identifier, out Guid masterScopeId)) - { - throw new ArgumentException($"Parameter {nameof(subjectDescriptor)} does not have a valid master scope ID"); - } - - return masterScopeId; - } - - internal static Guid GetCuid(this SubjectDescriptor subjectDescriptor) - { - if (!subjectDescriptor.IsCuidBased()) - { - throw new InvalidSubjectTypeException(subjectDescriptor.SubjectType); - } - - if (!Guid.TryParse(subjectDescriptor.Identifier, out Guid cuid)) - { - throw new ArgumentException($"Parameter {nameof(subjectDescriptor)} does not have a valid CUID"); - } - - return cuid; - } - - public static bool IsWindowsType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.WindowsIdentity); - } - - public static bool IsGroupType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsAadGroupType() || subjectDescriptor.IsVstsGroupType(); - } - - public static bool IsAadGroupType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.AadGroup); - } - - public static bool IsVstsGroupType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.VstsGroup); - } - - public static bool IsClaimsUserType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsAadUserType() || subjectDescriptor.IsMsaUserType(); - } - - public static bool IsAadUserType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.AadUser); - } - - public static bool IsMsaUserType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.MsaUser); - } - - public static bool IsBindPendingUserType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.BindPendingUser); - } - - public static bool IsUnauthenticatedIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.UnauthenticatedIdentity); - } - - public static bool IsServiceIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.ServiceIdentity); - } - - public static bool IsAggregateIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.AggregateIdentity); - } - - public static bool IsImportedIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.ImportedIdentity); - } - - public static bool IsGroupScopeType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.GroupScopeType); - } - - public static bool IsServerTestIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.ServerTestIdentity); - } - - // ******* All types below this line are not backed by the graph or identity service ************************ - public static bool IsSystemServicePrincipalType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemServicePrincipal); - } - - public static bool IsSystemScopeType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemScope); - } - - public static bool IsSystemCspPartnerType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemCspPartner); - } - - public static bool IsSystemLicenseType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemLicense); - } - - public static bool IsSystemPublicAccessType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemPublicAccess); - } - - public static bool IsSystemAccessControlType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.SystemAccessControl); - } - - public static bool IsSystemType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsSystemServicePrincipalType() || - subjectDescriptor.IsSystemScopeType() || - subjectDescriptor.IsSystemLicenseType() || - subjectDescriptor.IsSystemCspPartnerType() || - subjectDescriptor.IsSystemPublicAccessType() || - subjectDescriptor.IsSystemAccessControlType(); - } - - public static bool IsSubjectStoreType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsSystemServicePrincipalType() || - subjectDescriptor.IsSystemScopeType() || - subjectDescriptor.IsSystemLicenseType() || - subjectDescriptor.IsSystemCspPartnerType(); - } - - public static bool IsCspPartnerIdentityType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.CspPartnerIdentity); - } - - public static bool IsUnknownSubjectType(this SubjectDescriptor subjectDescriptor) - { - return StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.Unknown) || - StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.UnknownGroup) || - StringComparer.OrdinalIgnoreCase.Equals(subjectDescriptor.SubjectType, Constants.SubjectType.UnknownUser); - } - - public static bool IsCuidBased(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsClaimsUserType() || subjectDescriptor.IsCspPartnerIdentityType(); - } - - public static bool IsUserType(this SubjectDescriptor subjectDescriptor) - { - return subjectDescriptor.IsClaimsUserType() || - subjectDescriptor.IsCspPartnerIdentityType() || - subjectDescriptor.IsBindPendingUserType() || - subjectDescriptor.IsServiceIdentityType(); - } - - public static bool IsPubliclyAvailableGraphSubjectType(this SubjectDescriptor subjectDescriptor) - { - return (subjectDescriptor == default(SubjectDescriptor)) || - subjectDescriptor.IsUserType() || - subjectDescriptor.IsGroupType() || - subjectDescriptor.IsGroupScopeType(); - } - } - - /// - /// Converter to support data contract serialization. - /// - /// - /// This class should only be used to convert a descriptor string from the client back into a string - /// tuple SubjectDescriptor type on the server. The client should be unaware that this tuple relationship exists - /// and this should not permit that relationship to leak to the client. - /// - /// Specifically, this is provided so that the MVC router can convert a string => SubjectDescriptor so - /// that we can use the [ClientParameterType(typeof(string))] SubjectDescriptor userDescriptor) convenience in each - /// controller method. - /// - public class SubjectDescriptorConverter : TypeConverter - { - public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType) - { - return sourceType == typeof(string) || base.CanConvertFrom(context, sourceType); - } - - public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) - { - return destinationType == typeof(string) || base.CanConvertTo(context, destinationType); - } - - public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value) - { - if (value is string) - { - return SubjectDescriptor.FromString((string)value); - } - - return base.ConvertFrom(context, culture, value); - } - - public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType) - { - if (destinationType == typeof(string) && value is SubjectDescriptor) - { - SubjectDescriptor subjectDescriptor = (SubjectDescriptor)value; - if (subjectDescriptor == default(SubjectDescriptor)) - { - // subjectDescriptor.ToString() returns null in the case of default(SubjectDescriptor) - // and null can not be deserialized when the object is a struct. - return string.Empty; - } - - return subjectDescriptor.ToString(); - } - - return base.ConvertTo(context, culture, value, destinationType); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AccessTokenResult.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AccessTokenResult.cs deleted file mode 100644 index 8e119b60e..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AccessTokenResult.cs +++ /dev/null @@ -1,32 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Jwt; - -namespace GitHub.Services.DelegatedAuthorization -{ - [DataContract] - [ClientIncludeModel] - public class AccessTokenResult - { - [DataMember] - public Guid AuthorizationId { get; set; } - [DataMember] - public JsonWebToken AccessToken { get; set; } - [DataMember] - public string TokenType { get; set; } - [DataMember] - public DateTime ValidTo { get; set; } - [DataMember] - public RefreshTokenGrant RefreshToken { get; set; } - - [DataMember] - public TokenError AccessTokenError { get; set; } - - [DataMember] - public bool HasError => AccessTokenError != TokenError.None; - - [DataMember] - public string ErrorDescription { get; set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrant.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrant.cs deleted file mode 100644 index e350e9064..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrant.cs +++ /dev/null @@ -1,26 +0,0 @@ -using Newtonsoft.Json; -using Newtonsoft.Json.Converters; -using System; -using System.Runtime.Serialization; - -namespace GitHub.Services.DelegatedAuthorization -{ - [KnownType(typeof(RefreshTokenGrant))] - [KnownType(typeof(JwtBearerAuthorizationGrant))] - [JsonConverter(typeof(AuthorizationGrantJsonConverter))] - public abstract class AuthorizationGrant - { - public AuthorizationGrant(GrantType grantType) - { - if (grantType == GrantType.None) - { - throw new ArgumentException("Grant type is required."); - } - - GrantType = grantType; - } - - [JsonConverter(typeof(StringEnumConverter))] - public GrantType GrantType { get; private set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrantJsonConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrantJsonConverter.cs deleted file mode 100644 index 967c27f23..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/AuthorizationGrantJsonConverter.cs +++ /dev/null @@ -1,50 +0,0 @@ -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Jwt; -using Newtonsoft.Json.Linq; -using System; - -namespace GitHub.Services.DelegatedAuthorization -{ - public class AuthorizationGrantJsonConverter : VssJsonCreationConverter - { - protected override AuthorizationGrant Create(Type objectType, JObject jsonObject) - { - var typeValue = jsonObject.GetValue(nameof(AuthorizationGrant.GrantType), StringComparison.OrdinalIgnoreCase); - if (typeValue == null) - { - throw new ArgumentException(WebApiResources.UnknownEntityType(typeValue)); - } - - GrantType grantType; - if (typeValue.Type == JTokenType.Integer) - { - grantType = (GrantType)(Int32)typeValue; - } - else if (typeValue.Type != JTokenType.String || !Enum.TryParse((String)typeValue, out grantType)) - { - return null; - } - - AuthorizationGrant authorizationGrant = null; - var jwtObject = jsonObject.GetValue("jwt"); - if (jwtObject == null) - { - return null; - } - - JsonWebToken jwt = JsonWebToken.Create(jwtObject.ToString()); - switch (grantType) - { - case GrantType.JwtBearer: - authorizationGrant = new JwtBearerAuthorizationGrant(jwt); - break; - - case GrantType.RefreshToken: - authorizationGrant = new RefreshTokenGrant(jwt); - break; - } - - return authorizationGrant; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/GrantType.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/GrantType.cs deleted file mode 100644 index 67634f660..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/GrantType.cs +++ /dev/null @@ -1,11 +0,0 @@ -namespace GitHub.Services.DelegatedAuthorization -{ - public enum GrantType - { - None = 0, - JwtBearer = 1, - RefreshToken = 2, - Implicit = 3, - ClientCredentials = 4, - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/JwtBearerAuthorizationGrant.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/JwtBearerAuthorizationGrant.cs deleted file mode 100644 index ccfc3c243..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/JwtBearerAuthorizationGrant.cs +++ /dev/null @@ -1,21 +0,0 @@ -using GitHub.Services.WebApi.Jwt; -using System.Runtime.Serialization; - -namespace GitHub.Services.DelegatedAuthorization -{ - public class JwtBearerAuthorizationGrant : AuthorizationGrant - { - public JwtBearerAuthorizationGrant(JsonWebToken jwt) - : base(GrantType.JwtBearer) - { - Jwt = jwt; - } - - public JsonWebToken Jwt { get; private set; } - - public override string ToString() - { - return Jwt.EncodedToken; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/RefreshTokenGrant.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/RefreshTokenGrant.cs deleted file mode 100644 index fb434ba27..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/RefreshTokenGrant.cs +++ /dev/null @@ -1,20 +0,0 @@ -using GitHub.Services.WebApi.Jwt; - -namespace GitHub.Services.DelegatedAuthorization -{ - public class RefreshTokenGrant : AuthorizationGrant - { - public RefreshTokenGrant(JsonWebToken jwt) - : base(GrantType.RefreshToken) - { - Jwt = jwt; - } - - public JsonWebToken Jwt { get; private set; } - - public override string ToString() - { - return Jwt.EncodedToken; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/TokenError.cs b/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/TokenError.cs deleted file mode 100644 index 4f44bfd03..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/DelegatedAuthorization/TokenError.cs +++ /dev/null @@ -1,39 +0,0 @@ -namespace GitHub.Services.DelegatedAuthorization -{ - public enum TokenError - { - None, - GrantTypeRequired, - AuthorizationGrantRequired, - ClientSecretRequired, - RedirectUriRequired, - InvalidAuthorizationGrant, - InvalidAuthorizationScopes, - InvalidRefreshToken, - AuthorizationNotFound, - AuthorizationGrantExpired, - AccessAlreadyIssued, - InvalidRedirectUri, - AccessTokenNotFound, - InvalidAccessToken, - AccessTokenAlreadyRefreshed, - InvalidClientSecret, - ClientSecretExpired, - ServerError, - AccessDenied, - AccessTokenKeyRequired, - InvalidAccessTokenKey, - FailedToGetAccessToken, - InvalidClientId, - InvalidClient, - InvalidValidTo, - InvalidUserId, - FailedToIssueAccessToken, - AuthorizationGrantScopeMissing, - InvalidPublicAccessTokenKey, - InvalidPublicAccessToken, - /* Deprecated */ - PublicFeatureFlagNotEnabled, - SSHPolicyDisabled - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDataType.cs b/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDataType.cs deleted file mode 100644 index c2afa9212..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDataType.cs +++ /dev/null @@ -1,47 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.Services.FormInput -{ - /// - /// Enumerates data types that are supported as subscription input values. - /// - [DataContract] - public enum InputDataType - { - /// - /// No data type is specified. - /// - [EnumMember] - None = 0, - - /// - /// Represents a textual value. - /// - [EnumMember] - String = 10, - - /// - /// Represents a numberic value. - /// - [EnumMember] - Number = 20, - - /// - /// Represents a value of true or false. - /// - [EnumMember] - Boolean = 30, - - /// - /// Represents a Guid. - /// - [EnumMember] - Guid = 40, - - /// - /// Represents a URI. - /// - [EnumMember] - Uri = 50 - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDescriptor.cs b/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDescriptor.cs deleted file mode 100644 index a2586816c..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputDescriptor.cs +++ /dev/null @@ -1,130 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.Services.FormInput -{ - /// - /// Describes an input for subscriptions. - /// - [DataContract] - public class InputDescriptor : ISecuredObject - { - /// - /// Identifier for the subscription input - /// - [DataMember] - public String Id { get; set; } - - /// - /// Localized name which can be shown as a label for the subscription input - /// - [DataMember] - public String Name { get; set; } - - /// - /// Description of what this input is used for - /// - [DataMember] - public String Description { get; set; } - - /// - /// Underlying data type for the input value. When this value is specified, - /// InputMode, Validation and Values are optional. - /// - [DataMember] - public string Type { get; set; } - - /// - /// List of scopes supported. Null indicates all scopes are supported. - /// - public List SupportedScopes { get; set; } - - /// - /// Custom properties for the input which can be used by the service provider - /// - [DataMember] - public IDictionary Properties { get; set; } - - /// - /// Mode in which the value of this input should be entered - /// - [DataMember] - public InputMode InputMode { get; set; } - - /// - /// Gets whether this input is confidential, such as for a password or application key - /// - [DataMember] - public Boolean IsConfidential { get; set; } - - /// - /// Gets whether this input is included in the default generated action description. - /// - /// - [DataMember] - public Boolean UseInDefaultDescription { get; set; } - - /// - /// The group localized name to which this input belongs and can be shown as a header - /// for the container that will include all the inputs in the group. - /// - [DataMember] - public String GroupName { get; set; } - - /// - /// A hint for input value. It can be used in the UI as the input placeholder. - /// - [DataMember] - public String ValueHint { get; set; } - - /// - /// Information to use to validate this input's value - /// - [DataMember(EmitDefaultValue = false)] - public InputValidation Validation { get; set; } - - /// - /// Information about possible values for this input - /// - [DataMember(EmitDefaultValue = false)] - public InputValues Values { get; set; } - - /// - /// The ids of all inputs that the value of this input is dependent on. - /// - [DataMember(EmitDefaultValue = false)] - public IList DependencyInputIds { get; set; } - - /// - /// If true, the value information for this input is dynamic and - /// should be fetched when the value of dependency inputs change. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean HasDynamicValueInformation { get; set; } - - public void SetSecuredObjectProperties(Guid namespaceId, Int32 requiredPermissions, String token) - { - this.m_namespaceId = namespaceId; - this.m_requiredPermissions = requiredPermissions; - this.m_token = token; - - this.Validation?.SetSecuredObjectProperties(namespaceId, requiredPermissions, token); - this.Values?.SetSecuredObjectProperties(namespaceId, requiredPermissions, token); - } - - public Guid NamespaceId => m_namespaceId; - - public Int32 RequiredPermissions => m_requiredPermissions; - - public String GetToken() - { - return m_token; - } - - private Guid m_namespaceId; - private Int32 m_requiredPermissions; - private String m_token; - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputMode.cs b/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputMode.cs deleted file mode 100644 index cd819ea9e..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputMode.cs +++ /dev/null @@ -1,53 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.Services.FormInput -{ - /// - /// Mode in which a subscription input should be entered (in a UI) - /// - [DataContract] - public enum InputMode - { - /// - /// This input should not be shown in the UI - /// - [EnumMember] - None = 0, - - /// - /// An input text box should be shown - /// - [EnumMember] - TextBox = 10, - - /// - /// An password input box should be shown - /// - [EnumMember] - PasswordBox = 20, - - /// - /// A select/combo control should be shown - /// - [EnumMember] - Combo = 30, - - /// - /// Radio buttons should be shown - /// - [EnumMember] - RadioButtons = 40, - - /// - /// Checkbox should be shown(for true/false values) - /// - [EnumMember] - CheckBox = 50, - - /// - /// A multi-line text area should be shown - /// - [EnumMember] - TextArea = 60 - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValidation.cs b/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValidation.cs deleted file mode 100644 index c57de3670..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValidation.cs +++ /dev/null @@ -1,81 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.Services.FormInput -{ - /// - /// Describes what values are valid for a subscription input - /// - [DataContract] - public class InputValidation : ISecuredObject - { - /// - /// Gets or sets the data data type to validate. - /// - [DataMember(EmitDefaultValue = false)] - public InputDataType DataType { get; set; } - - /// - /// Gets or sets if this is a required field. - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IsRequired { get; set; } - - /// - /// Gets or sets the pattern to validate. - /// - [DataMember(EmitDefaultValue = false)] - public String Pattern { get; set; } - - /// - /// Gets or sets the error on pattern mismatch. - /// - [DataMember(EmitDefaultValue = false)] - public String PatternMismatchErrorMessage { get; set; } - - /// - /// Gets or sets the minimum value for this descriptor. - /// - [DataMember(EmitDefaultValue = false)] - public Decimal? MinValue { get; set; } - - /// - /// Gets or sets the minimum value for this descriptor. - /// - [DataMember(EmitDefaultValue = false)] - public Decimal? MaxValue { get; set; } - - /// - /// Gets or sets the minimum length of this descriptor. - /// - [DataMember(EmitDefaultValue = false)] - public Int32? MinLength { get; set; } - - /// - /// Gets or sets the maximum length of this descriptor. - /// - [DataMember(EmitDefaultValue = false)] - public Int32? MaxLength { get; set; } - - public void SetSecuredObjectProperties(Guid namespaceId, int requiredPermissions, string token) - { - this.m_namespaceId = namespaceId; - this.m_requiredPermissions = requiredPermissions; - this.m_token = token; - } - - public Guid NamespaceId => m_namespaceId; - - public int RequiredPermissions => m_requiredPermissions; - - public string GetToken() - { - return m_token; - } - - private Guid m_namespaceId; - private int m_requiredPermissions; - private string m_token; - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValues.cs b/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValues.cs deleted file mode 100644 index 1ae8d80bc..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/FormInput/InputValues.cs +++ /dev/null @@ -1,166 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.Services.FormInput -{ - /// - /// Information about the possible/allowed values for a given subscription input - /// - [DataContract] - public class InputValues : ISecuredObject - { - /// - /// The id of the input - /// - [DataMember(EmitDefaultValue = false)] - public String InputId { get; set; } - - /// - /// The default value to use for this input - /// - [DataMember(EmitDefaultValue = false)] - public String DefaultValue { get; set; } - - /// - /// Possible values that this input can take - /// - [DataMember(EmitDefaultValue = false)] - public IList PossibleValues { get; set; } - - /// - /// Should the value be restricted to one of the values in the PossibleValues (True) - /// or are the values in PossibleValues just a suggestion (False) - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IsLimitedToPossibleValues { get; set; } - - /// - /// Should this input be disabled - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IsDisabled { get; set; } - - /// - /// Should this input be made read-only - /// - [DataMember(EmitDefaultValue = false)] - public Boolean IsReadOnly { get; set; } - - /// - /// Errors encountered while computing dynamic values. - /// - /// - [DataMember(EmitDefaultValue = false)] - public InputValuesError Error { get; set; } - - public void SetSecuredObjectProperties(Guid namespaceId, Int32 requiredPermissions, String token) - { - this.m_namespaceId = namespaceId; - this.m_requiredPermissions = requiredPermissions; - this.m_token = token; - - this.Error?.SetSecuredObjectProperties(namespaceId, requiredPermissions, token); - if (this.PossibleValues != null && this.PossibleValues.Any()) - { - foreach (var value in this.PossibleValues) - { - value.SetSecuredObjectProperties(namespaceId, requiredPermissions, token); - } - } - } - - public Guid NamespaceId => m_namespaceId; - - public Int32 RequiredPermissions => m_requiredPermissions; - - public String GetToken() - { - return m_token; - } - - private Guid m_namespaceId; - private Int32 m_requiredPermissions; - private String m_token; - } - - /// - /// Information about a single value for an input - /// - [DataContract] - public class InputValue : ISecuredObject - { - /// - /// The value to store for this input - /// - [DataMember] - public String Value { get; set; } - - /// - /// The text to show for the display of this value - /// - [DataMember(EmitDefaultValue = false)] - public String DisplayValue { get; set; } - - /// - /// Any other data about this input - /// - [DataMember(EmitDefaultValue = false)] - public IDictionary Data { get; set; } - - public void SetSecuredObjectProperties(Guid namespaceId, Int32 requiredPermissions, String token) - { - this.m_namespaceId = namespaceId; - this.m_requiredPermissions = requiredPermissions; - this.m_token = token; - } - - public Guid NamespaceId => m_namespaceId; - - public Int32 RequiredPermissions => m_requiredPermissions; - - public String GetToken() - { - return m_token; - } - - private Guid m_namespaceId; - private Int32 m_requiredPermissions; - private String m_token; - } - - /// - /// Error information related to a subscription input value. - /// - [DataContract] - public class InputValuesError : ISecuredObject - { - /// - /// The error message. - /// - [DataMember] - public String Message { get; set; } - - public void SetSecuredObjectProperties(Guid namespaceId, Int32 requiredPermissions, String token) - { - this.m_namespaceId = namespaceId; - this.m_requiredPermissions = requiredPermissions; - this.m_token = token; - } - - public Guid NamespaceId => m_namespaceId; - - public Int32 RequiredPermissions => m_requiredPermissions; - - public String GetToken() - { - return m_token; - } - - private Guid m_namespaceId; - private Int32 m_requiredPermissions; - private String m_token; - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroup.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroup.cs deleted file mode 100644 index e790bd5cf..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroup.cs +++ /dev/null @@ -1,171 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Graph group entity - /// - [DataContract] - public class GraphGroup : GraphMember - { - public override string SubjectKind => Constants.SubjectKind.Group; - - /// - /// A short phrase to help human readers disambiguate groups with similar names - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public string Description { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal string SpecialType { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeSpecialType() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal Guid ScopeId { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeScopeId() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal string ScopeType { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeScopeType() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal string ScopeName { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeScopeName() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal Guid LocalScopeId { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeLocalScopeId() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal Guid SecuringHostId { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeSecuringHostId() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal bool IsRestrictedVisible { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeIsRestrictedVisible() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal bool IsCrossProject { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeIsIsCrossProject() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal bool IsGlobalScope { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeIsGlobalScope() => ShoudSerializeInternals; - - [DataMember(IsRequired = false, EmitDefaultValue = false), EditorBrowsable(EditorBrowsableState.Never), ClientInternalUseOnly] - internal bool IsDeleted { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - internal GraphGroup( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url, - string domain, - string principalName, - string mailAddress, - string description, - string specialType, - Guid scopeId, - string scopeType, - string scopeName, - Guid localScopeId, - Guid securingHostId, - bool isRestrictedVisible, - bool isCrossProject, - bool isGlobalScope, - bool isDeleted) - : base(origin, originId, descriptor, legacyDescriptor, displayName, links, url, domain, principalName, mailAddress) - { - Description = description; - SpecialType = specialType; - ScopeId = scopeId; - ScopeType = scopeType; - ScopeName = scopeName; - LocalScopeId = localScopeId; - SecuringHostId = securingHostId; - IsRestrictedVisible = isRestrictedVisible; - IsCrossProject = isCrossProject; - IsGlobalScope = isGlobalScope; - IsDeleted = isDeleted; - } - - // this is how we replace/overwrite parameters and create a new object - // and keep our internal objects immutable - [EditorBrowsable(EditorBrowsableState.Never)] - internal GraphGroup( - GraphGroup group, - string origin = null, - string originId = null, - SubjectDescriptor? descriptor = null, - IdentityDescriptor legacyDescriptor = null, - string displayName = null, - ReferenceLinks links = null, - string url = null, - string domain = null, - string principalName = null, - string mailAddress = null, - string description = null, - string specialType = null, - Guid? scopeId = null, - string scopeType = null, - string scopeName = null, - Guid? localScopeId = null, - Guid? securingHostId = null, - bool? isRestrictedVisible = null, - bool? isCrossProject = null, - bool? isGlobalScope = null, - bool? isDeleted = null) - : this(origin ?? group?.Origin, - originId ?? group?.OriginId, - descriptor ?? group?.Descriptor ?? default(SubjectDescriptor), - legacyDescriptor ?? group?.LegacyDescriptor ?? default(IdentityDescriptor), - displayName ?? group?.DisplayName, - links ?? group?.Links, - url ?? group?.Url, - domain ?? group?.Domain, - principalName ?? group?.PrincipalName, - mailAddress ?? group?.MailAddress, - description ?? group?.Description, - specialType ?? group?.SpecialType, - scopeId ?? group?.ScopeId ?? default(Guid), - scopeType ?? group?.ScopeType, - scopeName ?? group?.ScopeName, - localScopeId ?? group?.LocalScopeId ?? default(Guid), - securingHostId ?? group?.SecuringHostId ?? default(Guid), - isRestrictedVisible ?? group?.IsRestrictedVisible ?? default(bool), - isCrossProject ?? group?.IsCrossProject ?? default(bool), - isGlobalScope ?? group?.IsGlobalScope ?? default(bool), - isDeleted ?? group?.IsDeleted ?? default(bool)) - { } - - // only for serialization - protected GraphGroup() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContext.cs deleted file mode 100644 index 515111d3a..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContext.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using Newtonsoft.Json; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Do not attempt to use this type to create a new group. This - /// type does not contain sufficient fields to create a new group. - /// - [DataContract] - [JsonConverter(typeof(GraphGroupCreationContextJsonConverter))] - public abstract class GraphGroupCreationContext - { - /// - /// Optional: If provided, we will use this identifier for the storage key of the created group - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Guid StorageKey { get; set; } - } - - /// - /// Use this type to create a new group using the OriginID as a reference to an existing group from an external - /// AD or AAD backed provider. This is the subset of GraphGroup fields required for creation of - /// a group for the AD and AAD use case. - /// - [DataContract] - public class GraphGroupOriginIdCreationContext : GraphGroupCreationContext - { - /// - /// This should be the object id or sid of the group from the source AD or AAD provider. - /// Example: d47d025a-ce2f-4a79-8618-e8862ade30dd - /// Team Services will communicate with the source provider to fill all other fields on creation. - /// - [DataMember(IsRequired = true)] - public string OriginId { get; set; } - } - - /// - /// Use this type to create a new group using the mail address as a reference to an existing group from an external - /// AD or AAD backed provider. This is the subset of GraphGroup fields required for creation of - /// a group for the AAD and AD use case. - /// - [DataContract] - public class GraphGroupMailAddressCreationContext : GraphGroupCreationContext - { - /// - /// This should be the mail address or the group in the source AD or AAD provider. - /// Example: jamal@contoso.com - /// Team Services will communicate with the source provider to fill all other fields on creation. - /// - [DataMember(IsRequired = true)] - public string MailAddress { get; set; } - } - - /// - /// Use this type to create a new Vsts group that is not backed by an external provider. - /// - [DataContract] - public class GraphGroupVstsCreationContext : GraphGroupCreationContext - { - /// - /// Used by VSTS groups; if set this will be the group DisplayName, otherwise ignored - /// - [DataMember(IsRequired = true)] - public string DisplayName { get; set; } - - /// - /// Used by VSTS groups; if set this will be the group description, otherwise ignored - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public string Description { get; set; } - - /// - /// Internal use only. An optional sid to use for group creation. - /// - public SubjectDescriptor Descriptor { get; set; } - - - [DataMember(Name = "Descriptor", IsRequired = false, EmitDefaultValue = false)] - private string DescriptorString - { - get { return Descriptor.ToString(); } - set { Descriptor = SubjectDescriptor.FromString(value); } - } - /// - /// For internal use only in back compat scenarios. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public bool CrossProject { get; set; } - - /// - /// For internal use only in back compat scenarios. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public bool RestrictedVisibility { get; set; } - - /// - /// For internal use only in back compat scenarios. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public string SpecialGroupType { get; set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContextJsonConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContextJsonConverter.cs deleted file mode 100644 index a605270d0..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphGroupCreationContextJsonConverter.cs +++ /dev/null @@ -1,46 +0,0 @@ -using System; -using System.Linq; -using Newtonsoft.Json.Linq; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Graph.Client -{ - public class GraphGroupCreationContextJsonConverter : VssJsonCreationConverter - { - protected override GraphGroupCreationContext Create(Type objectType, JObject jsonObject) - { - // enforce origin id or principalname or displayName - var hasOriginId = jsonObject["originId"] != null; - var hasMailAddress = jsonObject["mailAddress"] != null; - var hasDisplayName = jsonObject["displayName"] != null; - var requiredFields = new bool[] - { - hasOriginId, - hasDisplayName, - hasMailAddress - }; - - if (requiredFields.Count(b => b) > 1) - { - throw new ArgumentNullException(WebApiResources.GraphGroupMissingRequiredFields()); - } - - if (hasOriginId) - { - return new GraphGroupOriginIdCreationContext(); - } - - if (hasMailAddress) - { - return new GraphGroupMailAddressCreationContext(); - } - - if (hasDisplayName) - { - return new GraphGroupVstsCreationContext(); - } - - throw new ArgumentException(WebApiResources.GraphGroupMissingRequiredFields()); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphMember.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphMember.cs deleted file mode 100644 index 4e150be7d..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphMember.cs +++ /dev/null @@ -1,58 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - [DataContract] - public abstract class GraphMember : GraphSubject - { - /// - /// This represents the name of the container of origin for a graph member. - /// (For MSA this is "Windows Live ID", for AD the name of the domain, for AAD the - /// tenantID of the directory, for VSTS groups the ScopeId, etc) - /// - [DataMember(IsRequired = false, EmitDefaultValue = true)] - public string Domain { get; private set; } - - /// - /// This is the PrincipalName of this graph member from the source provider. The source - /// provider may change this field over time and it is not guaranteed to be immutable - /// for the life of the graph member by VSTS. - /// - [DataMember] - public string PrincipalName { get; private set; } - - /// - /// The email address of record for a given graph member. This may be different - /// than the principal name. - /// - [DataMember(IsRequired = false, EmitDefaultValue = true)] - public string MailAddress { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - protected GraphMember( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url, - string domain, - string principalName, - string mailAddress) - : base(origin, originId, descriptor, legacyDescriptor, displayName, links, url) - { - Domain = domain; - PrincipalName = principalName; - MailAddress = mailAddress; - } - - // only for serialization - protected GraphMember() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphScope.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphScope.cs deleted file mode 100644 index 362d29597..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphScope.cs +++ /dev/null @@ -1,138 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using GroupScopeType = GitHub.Services.Identity.GroupScopeType; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Container where a graph entity is defined (organization, project, team) - /// - [DataContract] - public class GraphScope : GraphSubject - { - public override string SubjectKind => Constants.SubjectKind.Scope; - - /// - /// The subject descriptor that references the administrators group for this scope. Only - /// members of this group can change the contents of this scope or assign other users - /// permissions to access this scope. - /// - public SubjectDescriptor AdministratorDescriptor { get; private set; } - - /// - /// The subject descriptor that references the administrators group for this scope. Only - /// members of this group can change the contents of this scope or assign other users - /// permissions to access this scope. - /// - [DataMember(Name = "AdministratorDescriptor", IsRequired = false, EmitDefaultValue = false)] - private string AdministratorString - { - get { return AdministratorDescriptor.ToString(); } - set { AdministratorDescriptor = SubjectDescriptor.FromString(value); } - } - - /// - /// When true, this scope is also a securing host for one or more scopes. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public bool IsGlobal { get; private set; } - - /// - /// The subject descriptor of the parent scope. - /// - public SubjectDescriptor ParentDescriptor { get; private set; } - - /// - /// The subject descriptor for the closest account or organization in the - /// ancestor tree of this scope. - /// - [DataMember(Name = "ParentDescriptor", IsRequired = false, EmitDefaultValue = false)] - private string ParentDescriptorString - { - get { return ParentDescriptor.ToString(); } - set { ParentDescriptor = SubjectDescriptor.FromString(value); } - } - - /// - /// The subject descriptor for the containing organization in the ancestor tree - /// of this scope. - /// - public SubjectDescriptor SecuringHostDescriptor { get; private set; } - - /// - /// The subject descriptor for the containing organization in the ancestor tree - /// of this scope. - /// - [DataMember(Name = "SecuringHostDescriptor", IsRequired = false, EmitDefaultValue = false)] - private string SecuringHostDescriptorString - { - get { return SecuringHostDescriptor.ToString(); } - set { SecuringHostDescriptor = SubjectDescriptor.FromString(value); } - } - - /// - /// The type of this scope. Typically ServiceHost or TeamProject. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public GroupScopeType ScopeType { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - internal GraphScope( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url, - SubjectDescriptor administratorDescriptor, - bool isGlobal, - SubjectDescriptor parentDescriptor, - SubjectDescriptor securingHostDescriptor, - GroupScopeType scopeType = GroupScopeType.Generic) - : base(origin, originId, descriptor, legacyDescriptor, displayName, links, url) - { - AdministratorDescriptor = administratorDescriptor; - IsGlobal = isGlobal; - ParentDescriptor = parentDescriptor; - SecuringHostDescriptor = securingHostDescriptor; - ScopeType = scopeType; - } - - // this is how we replace/overwrite parameters and create a new object - // and keep our internal objects immutable - internal GraphScope( - GraphScope scope, - string origin = null, - string originId = null, - SubjectDescriptor? descriptor = null, - IdentityDescriptor legacyDescriptor = null, - string displayName = null, - ReferenceLinks links = null, - string url = null, - SubjectDescriptor? administrator = null, - bool? isGlobal = null, - SubjectDescriptor? parentDescriptor = null, - SubjectDescriptor? securingHostDescriptor = null, - GroupScopeType? scopeType = GroupScopeType.Generic) - : this(origin ?? scope?.Origin, - originId ?? scope?.OriginId, - descriptor ?? scope?.Descriptor ?? default(SubjectDescriptor), - legacyDescriptor ?? scope?.LegacyDescriptor ?? default(IdentityDescriptor), - displayName ?? scope?.DisplayName, - links ?? scope?.Links, - url ?? scope?.Url, - administrator ?? scope?.AdministratorDescriptor ?? default(SubjectDescriptor), - isGlobal ?? scope?.IsGlobal ?? default(bool), - parentDescriptor ?? scope?.ParentDescriptor ?? default(SubjectDescriptor), - securingHostDescriptor ?? scope?.SecuringHostDescriptor ?? default(SubjectDescriptor), - scopeType ?? scope?.ScopeType ?? default(GroupScopeType)) - { } - - // only for serialization - protected GraphScope() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubject.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubject.cs deleted file mode 100644 index fc48a5bd9..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubject.cs +++ /dev/null @@ -1,78 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using Newtonsoft.Json; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Top-level graph entity - /// - [DataContract] - [JsonConverter(typeof(GraphSubjectJsonConverter))] - public abstract class GraphSubject : GraphSubjectBase - { - /// - /// This field identifies the type of the graph subject (ex: Group, Scope, User). - /// - [DataMember] - public abstract string SubjectKind { get; } - - /// - /// The type of source provider for the origin identifier (ex:AD, AAD, MSA) - /// - [DataMember] - public string Origin { get; private set; } - - /// - /// The unique identifier from the system of origin. Typically a sid, object id or Guid. Linking - /// and unlinking operations can cause this value to change for a user because the user is not - /// backed by a different provider and has a different unique id in the new provider. - /// - [DataMember] - public string OriginId { get; private set; } - - /// - /// [Internal Use Only] The legacy descriptor is here in case you need to access old version IMS using identity descriptor. - /// - [ClientInternalUseOnly] - internal IdentityDescriptor LegacyDescriptor { get; private set; } - - /// - /// [Internal Use Only] The legacy descriptor is here in case you need to access old version IMS using identity descriptor. - /// - [DataMember(Name = "LegacyDescriptor", IsRequired = false, EmitDefaultValue = false)] - private string LegacyDescriptorString - { - get { return LegacyDescriptor?.ToString(); } - set { LegacyDescriptor = IdentityDescriptor.FromString(value); } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeLegacyDescriptorString() => ShoudSerializeInternals; - - [ClientInternalUseOnly] - internal bool ShoudSerializeInternals; - - // only for serialization - protected GraphSubject() { } - - [EditorBrowsable(EditorBrowsableState.Never)] - protected GraphSubject( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url) : base(descriptor, displayName, links, url) - { - Origin = origin; - OriginId = originId; - LegacyDescriptor = legacyDescriptor; - ShoudSerializeInternals = false; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectBase.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectBase.cs deleted file mode 100644 index 71d1cd095..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectBase.cs +++ /dev/null @@ -1,80 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; -using System.Xml; -using System.Xml.Schema; -using System.Xml.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Xml; -using Newtonsoft.Json; - -namespace GitHub.Services.Graph.Client -{ - [JsonObject(MemberSerialization = MemberSerialization.OptIn)] - [XmlSerializableDataContract] - public abstract class GraphSubjectBase : IXmlSerializable - { - /// The descriptor is the primary way to reference the graph subject while the system is running. This field - /// will uniquely identify the same graph subject across both Accounts and Organizations. - /// - public SubjectDescriptor Descriptor { get; protected set; } - - /// - /// The descriptor is the primary way to reference the graph subject while the system is running. This field - /// will uniquely identify the same graph subject across both Accounts and Organizations. - /// - [DataMember(Name = "Descriptor", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "Descriptor", DefaultValueHandling = DefaultValueHandling.Ignore)] - private string DescriptorString - { - get { return Descriptor.ToString(); } - set { Descriptor = SubjectDescriptor.FromString(value); } - } - - /// - /// This is the non-unique display name of the graph subject. To change this field, you must alter its value in the - /// source provider. - /// - [DataMember] - [JsonProperty] - public string DisplayName { get; protected set; } - - /// - /// This field contains zero or more interesting links about the graph subject. These links may be invoked to obtain additional - /// relationships or more detailed information about this graph subject. - /// - [DataMember(Name = "_links", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "_links", DefaultValueHandling = DefaultValueHandling.Ignore)] - [XmlIgnore] // ReferenceLinks type does not currently support XML serialization (#1164908 for tracking) - public ReferenceLinks Links { get; protected set; } - - /// - /// This url is the full route to the source resource of this graph subject. - /// - [DataMember(EmitDefaultValue = false)] - [JsonProperty(DefaultValueHandling = DefaultValueHandling.Ignore)] - public string Url { get; protected set; } - - // only for serialization - protected GraphSubjectBase() { } - - [EditorBrowsable(EditorBrowsableState.Never)] - protected GraphSubjectBase( - SubjectDescriptor descriptor, - string displayName, - ReferenceLinks links, - string url) - { - Descriptor = descriptor; - DisplayName = displayName; - Links = links; - Url = url; - } - - XmlSchema IXmlSerializable.GetSchema() { return null; } - - void IXmlSerializable.ReadXml(XmlReader reader) => reader.ReadDataMemberXml(this); - - void IXmlSerializable.WriteXml(XmlWriter writer) => writer.WriteDataMemberXml(this); - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectJsonConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectJsonConverter.cs deleted file mode 100644 index 0953b7186..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSubjectJsonConverter.cs +++ /dev/null @@ -1,42 +0,0 @@ -using System; -using System.Linq; -using System.Reflection; -using GitHub.Services.WebApi; -using Newtonsoft.Json.Linq; - -namespace GitHub.Services.Graph.Client -{ - public class GraphSubjectJsonConverter : VssJsonCreationConverter - { - protected override GraphSubject Create(Type objectType, JObject jsonObject) - { - var subjectKindObject = jsonObject.GetValue(nameof(GraphSubject.SubjectKind), StringComparison.OrdinalIgnoreCase); - if (subjectKindObject == null) - { - throw new ArgumentException(WebApiResources.UnknownEntityType(subjectKindObject)); - } - var typeName = subjectKindObject.ToString(); - switch (typeName) - { - case Constants.SubjectKind.Group: - var groupInfo = typeof(GraphGroup).GetTypeInfo(); - var graphGroupConstructor = groupInfo.DeclaredConstructors.First(x => x.GetParameters().Length == 0); - return (GraphGroup)graphGroupConstructor.Invoke(null); - case Constants.SubjectKind.Scope: - var scopeInfo = typeof(GraphScope).GetTypeInfo(); - var graphScopeConstructor = scopeInfo.DeclaredConstructors.First(x => x.GetParameters().Length == 0); - return (GraphScope)graphScopeConstructor.Invoke(null); - case Constants.SubjectKind.User: - var userInfo = typeof(GraphUser).GetTypeInfo(); - var graphUserConstructor = userInfo.DeclaredConstructors.First(x => x.GetParameters().Length == 0); - return (GraphUser)graphUserConstructor.Invoke(null); - case Constants.SubjectKind.SystemSubject: - var systemSubjectInfo = typeof(GraphSystemSubject).GetTypeInfo(); - var graphSystemSubjectConstructor = systemSubjectInfo.DeclaredConstructors.First(x => x.GetParameters().Length == 0); - return (GraphSystemSubject)graphSystemSubjectConstructor.Invoke(null); - default: - throw new ArgumentException(WebApiResources.UnknownEntityType(typeName)); - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSystemSubject.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSystemSubject.cs deleted file mode 100644 index 7a26f2e37..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphSystemSubject.cs +++ /dev/null @@ -1,30 +0,0 @@ -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - [DataContract] - public class GraphSystemSubject : GraphSubject - { - public override string SubjectKind => Constants.SubjectKind.SystemSubject; - - [EditorBrowsable(EditorBrowsableState.Never)] - internal GraphSystemSubject( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url) - : base(origin, originId, descriptor, legacyDescriptor, displayName, links, url) - { - } - - // only for serialization - protected GraphSystemSubject() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUser.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUser.cs deleted file mode 100644 index 5dd2cc866..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUser.cs +++ /dev/null @@ -1,107 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using IdentityDescriptor = GitHub.Services.Identity.IdentityDescriptor; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Graph user entity - /// - [DataContract] - public class GraphUser : GraphMember - { - public override string SubjectKind => Constants.SubjectKind.User; - - /// - /// The meta type of the user in the origin, such as "member", "guest", etc. - /// See for the set of possible values. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public string MetaType { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false), ClientInternalUseOnly] - internal DateTime MetadataUpdateDate { get; private set; } - - /// - /// The short, generally unique name for the user in the backing directory. - /// For AAD users, this corresponds to the mail nickname, which is often but not necessarily similar - /// to the part of the user's mail address before the @ sign. - /// For GitHub users, this corresponds to the GitHub user handle. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public string DirectoryAlias { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public virtual bool ShouldSerializeMetadataUpdateDate() => ShoudSerializeInternals; - - /// - /// When true, the group has been deleted in the identity provider - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public bool IsDeletedInOrigin { get; private set; } - - [EditorBrowsable(EditorBrowsableState.Never)] - internal GraphUser( - string origin, - string originId, - SubjectDescriptor descriptor, - IdentityDescriptor legacyDescriptor, - string displayName, - ReferenceLinks links, - string url, - string domain, - string principalName, - string mailAddress, - string metaType, - DateTime metadataUpdateDate, - bool isDeletedInOrigin, - string directoryAlias) - : base(origin, originId, descriptor, legacyDescriptor, displayName, links, url, domain, principalName, mailAddress) - { - MetaType = metaType; - MetadataUpdateDate = metadataUpdateDate; - IsDeletedInOrigin = isDeletedInOrigin; - DirectoryAlias = directoryAlias; - } - - // this is how we replace/overwrite parameters and create a new object - // and keep our internal objects immutable - internal GraphUser( - GraphUser user, - string origin = null, - string originId = null, - SubjectDescriptor? descriptor = null, - IdentityDescriptor legacyDescriptor = null, - string displayName = null, - ReferenceLinks links = null, - string url = null, - string domain = null, - string principalName = null, - string mailAddress = null, - string metaType = null, - DateTime? metadataUpdateDate = null, - bool? isDeletedInOrigin = false, - string directoryAlias = null) - : this(origin ?? user?.Origin, - originId ?? user?.OriginId, - descriptor ?? user?.Descriptor ?? default(SubjectDescriptor), - legacyDescriptor ?? user?.LegacyDescriptor ?? default(IdentityDescriptor), - displayName ?? user?.DisplayName, - links ?? user?.Links, - url ?? user?.Url, - domain ?? user?.Domain, - principalName ?? user?.PrincipalName, - mailAddress ?? user?.MailAddress, - metaType ?? user?.MetaType, - metadataUpdateDate ?? user?.MetadataUpdateDate ?? DateTime.MinValue, - isDeletedInOrigin ?? user?.IsDeletedInOrigin ?? default, - directoryAlias ?? user?.DirectoryAlias) - { } - - // only for serialization - protected GraphUser() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserCreationContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserCreationContext.cs deleted file mode 100644 index 2350e8c08..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserCreationContext.cs +++ /dev/null @@ -1,81 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Do not attempt to use this type to create a new user. Use - /// one of the subclasses instead. This type does not contain - /// sufficient fields to create a new user. - /// - [DataContract] - [JsonConverter(typeof(GraphUserCreationContextJsonConverter))] - public abstract class GraphUserCreationContext - { - /// - /// Optional: If provided, we will use this identifier for the storage key of the created user - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Guid StorageKey { get; set; } - } - - /// - /// Use this type to create a new user using the OriginID as a reference to an existing user from an external - /// AD or AAD backed provider. This is the subset of GraphUser fields required for creation of - /// a GraphUser for the AD and AAD use case when looking up the user by its unique ID in the backing provider. - /// - [DataContract] - public class GraphUserOriginIdCreationContext : GraphUserCreationContext - { - /// - /// This should be the object id or sid of the user from the source AD or AAD provider. - /// Example: d47d025a-ce2f-4a79-8618-e8862ade30dd - /// Team Services will communicate with the source provider to fill all other fields on creation. - /// - [DataMember(IsRequired = true)] - public string OriginId { get; set; } - - - /// - /// This should be the name of the origin provider. - /// Example: github.com - /// - [DataMember(IsRequired = false)] - public string Origin { get; set; } - } - - /// - /// Use this type to create a new user using the principal name as a reference to an existing user from an external - /// AD or AAD backed provider. This is the subset of GraphUser fields required for creation of - /// a GraphUser for the AD and AAD use case when looking up the user by its principal name in the backing provider. - /// - [DataContract] - public class GraphUserPrincipalNameCreationContext : GraphUserCreationContext - { - /// - /// This should be the principal name or upn of the user in the source AD or AAD provider. - /// Example: jamal@contoso.com - /// Team Services will communicate with the source provider to fill all other fields on creation. - /// - [DataMember(IsRequired = true)] - public string PrincipalName { get; set; } - } - - /// - /// Use this type to create a new user using the mail address as a reference to an existing user from an external - /// AD or AAD backed provider. This is the subset of GraphUser fields required for creation of - /// a GraphUser for the AD and AAD use case when looking up the user by its mail address in the backing provider. - /// - [DataContract] - public class GraphUserMailAddressCreationContext : GraphUserCreationContext - { - /// - /// This should be the mail address of the user in the source AD or AAD provider. - /// Example: Jamal.Hartnett@contoso.com - /// Team Services will communicate with the source provider to fill all other fields on creation. - /// - { - protected override GraphUserCreationContext Create(Type objectType, JObject jsonObject) - { - // enforce origin id or principalname or displayName - var hasOriginId = jsonObject["originId"] != null; - var hasPrincipalName = jsonObject["principalName"] != null; - var hasMailAddress = jsonObject["mailAddress"] != null; - var requiredFields = new bool[] - { - hasOriginId, - hasPrincipalName, - hasMailAddress, - }; - - if (requiredFields.Count(b => b) != 1) - { - throw new ArgumentException(WebApiResources.GraphUserMissingRequiredFields()); - } - - if (hasOriginId) - { - return new GraphUserOriginIdCreationContext(); - } - - if (hasPrincipalName) - { - return new GraphUserPrincipalNameCreationContext(); - } - - if (hasMailAddress) - { - return new GraphUserMailAddressCreationContext(); - } - - throw new ArgumentException(WebApiResources.GraphUserMissingRequiredFields()); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContext.cs deleted file mode 100644 index 9a50f3aaf..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContext.cs +++ /dev/null @@ -1,45 +0,0 @@ -using System; -using System.Runtime.Serialization; -using Newtonsoft.Json; -using System.ComponentModel; - -namespace GitHub.Services.Graph.Client -{ - /// - /// Do not attempt to use this type to update user. Use - /// one of the subclasses instead. This type does not contain - /// sufficient fields to create a new user. - /// - [DataContract] - [JsonConverter(typeof(GraphUserUpdateContextJsonConverter))] - public abstract class GraphUserUpdateContext - { - /// - /// Storage key should not be specified in case of updating user - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - [EditorBrowsable(EditorBrowsableState.Never), Obsolete()] - public Guid StorageKey { get; set; } - - //Currently there's a bug on the client generator that if a class doesn't have data member, it wouldn't get generated - //We're adding a temporary data member here in order to get passed that issue - //BUG 1466336 has been created to track this issue. Once the bug is fixed, we'll remove this data member. - //Marking it as obsolete and never use for now to ensure no one can access - } - /// - /// Use this type to update an existing user using the OriginID as a reference to an existing user from an external - /// AD or AAD backed provider. This is the subset of GraphUser fields required for creation of - /// a GraphUser for the AD and AAD use case when looking up the user by its unique ID in the backing provider. - /// - [DataContract] - public class GraphUserOriginIdUpdateContext : GraphUserUpdateContext - { - /// - /// This should be the object id or sid of the user from the source AD or AAD provider. - /// Example: d47d025a-ce2f-4a79-8618-e8862ade30dd - /// Azure Devops will communicate with the source provider to fill all other fields on creation. - /// - [DataMember(IsRequired = true)] - public string OriginId { get; set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContextJsonConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContextJsonConverter.cs deleted file mode 100644 index 859004236..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Client/GraphUserUpdateContextJsonConverter.cs +++ /dev/null @@ -1,33 +0,0 @@ -using System; -using System.Linq; -using Newtonsoft.Json.Linq; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Graph.Client -{ - public class GraphUserUpdateContextJsonConverter : VssJsonCreationConverter - { - protected override GraphUserUpdateContext Create(Type objectType, JObject jsonObject) - { - // enforce origin id or principalname or displayName - var hasOriginId = jsonObject["originId"] != null; - - var requiredFields = new bool[] - { - hasOriginId - }; - - if (requiredFields.Count(b => b) != 1) - { - throw new ArgumentException(WebApiResources.GraphUserMissingRequiredFields()); - } - - if (hasOriginId) - { - return new GraphUserOriginIdUpdateContext(); - } - - throw new ArgumentException(WebApiResources.GraphUserMissingRequiredFields()); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Graph/Constants.cs b/src/Sdk/WebApi/WebApi/Contracts/Graph/Constants.cs index 5245b4426..45f20ecbd 100644 --- a/src/Sdk/WebApi/WebApi/Contracts/Graph/Constants.cs +++ b/src/Sdk/WebApi/WebApi/Contracts/Graph/Constants.cs @@ -103,56 +103,6 @@ namespace GitHub.Services.Graph public static readonly IReadOnlyDictionary SocialTypeMap; - public static class ScopeUpdateFields - { - public const string Name = "name"; - } - - public static class GroupUpdateFields - { - public const string DisplayName = "displayName"; - public const string Description = "description"; - } - - public static class Links - { - public const string Self = "self"; - public const string Memberships = "memberships"; - public const string MembershipState = "membershipState"; - public const string StorageKey = "storageKey"; - public const string Groups = "groups"; - public const string Descriptor = "descriptor"; - public const string Subject = "subject"; - public const string Member = "member"; - public const string Conainer = "container"; - public const string Avatar = "avatar"; - } - - [GenerateSpecificConstants] - public static class OriginName - { - public const string ActiveDirectory = "ad"; - [GenerateConstant] - public const string AzureActiveDirectory = "aad"; - [GenerateConstant] - public const string MicrosoftAccount = "msa"; - [GenerateConstant] - public const string VisualStudioTeamServices = "vsts"; - [GenerateConstant] - public const string GitHubDirectory = "ghb"; - } - - public static class FederatedProviderName - { - public const string GitHub = "github.com"; - } - - public static class TraversalDepth - { - public const int Direct = 1; - public const int Expanded = -1; - } - [GenerateSpecificConstants] public static class UserMetaType { @@ -179,15 +129,6 @@ namespace GitHub.Services.Graph internal const int MaxIdentifierLength = SubjectDescriptorPolicies.MaxIdentifierLength; } - internal static class Version - { - internal const int Unspecified = -1; - } - - public const int MaximumRestResultSize = 500; - public const string JsonPatchMediaType = "application/json-patch+json"; - public const string JsonPatchOperationPathPrefix = "/"; - public const char SubjectListSeparator = ','; public const char SubjectDescriptorPartsSeparator = '.'; // Social descriptor constants diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/ChangedIdentities.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/ChangedIdentities.cs deleted file mode 100644 index 23cf16f5d..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/ChangedIdentities.cs +++ /dev/null @@ -1,119 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using Newtonsoft.Json; - -namespace GitHub.Services.Identity -{ - /// - /// Container class for changed identities - /// - [DataContract] - public class ChangedIdentities - { - [JsonConstructor] - private ChangedIdentities() - { - } - - public ChangedIdentities( - IList identities, - ChangedIdentitiesContext sequenceContext) : - this(identities, sequenceContext, false) - { - } - - public ChangedIdentities( - IList identities, - ChangedIdentitiesContext sequenceContext, - bool moreData) - { - Identities = identities; - SequenceContext = sequenceContext; - MoreData = moreData; - } - - /// - /// Changed Identities - /// - [DataMember] - public IList Identities { get; private set; } - - /// - /// Last Identity SequenceId - /// - [DataMember] - public ChangedIdentitiesContext SequenceContext { get; private set; } - - /// - /// More data available, set to true if pagesize is specified. - /// - [DataMember] - public bool MoreData { get; private set; } - } - - /// - /// Context class for changed identities - /// - [DataContract] - public class ChangedIdentitiesContext - { - [JsonConstructor] - private ChangedIdentitiesContext() - { - } - - public ChangedIdentitiesContext( - Int32 identitySequenceId, - Int32 groupSequenceId) : - this(identitySequenceId, groupSequenceId, ChangedIdentitiesContext.UnspecifiedSequenceId) - { - } - - public ChangedIdentitiesContext( - Int32 identitySequenceId, - Int32 groupSequenceId, - Int32 organizationIdentitySequenceId) : - this(identitySequenceId, groupSequenceId, organizationIdentitySequenceId, 0) - { - } - - public ChangedIdentitiesContext( - Int32 identitySequenceId, - Int32 groupSequenceId, - Int32 organizationIdentitySequenceId, - Int32 pageSize) - { - IdentitySequenceId = identitySequenceId; - GroupSequenceId = groupSequenceId; - OrganizationIdentitySequenceId = organizationIdentitySequenceId; - PageSize = pageSize; - } - - /// - /// Last Identity SequenceId - /// - [DataMember] - public Int32 IdentitySequenceId { get; private set; } - - /// - /// Last Group SequenceId - /// - [DataMember] - public Int32 GroupSequenceId { get; private set; } - - /// - /// Last Group OrganizationIdentitySequenceId - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Int32 OrganizationIdentitySequenceId { get; private set; } - - /// - /// Page size - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Int32 PageSize { get; private set; } - - private static int UnspecifiedSequenceId = -1; - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateGroupsInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateGroupsInfo.cs deleted file mode 100644 index 36b8649f3..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateGroupsInfo.cs +++ /dev/null @@ -1,26 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class CreateGroupsInfo - { - public CreateGroupsInfo() - { - } - - public CreateGroupsInfo(Guid scopeId, IList groups) - { - this.ScopeId = scopeId; - this.Groups = new List(groups); - } - - [DataMember] - public Guid ScopeId { get; private set; } - - [DataMember] - public List Groups { get; private set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateScopeInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateScopeInfo.cs deleted file mode 100644 index ff8b27875..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/CreateScopeInfo.cs +++ /dev/null @@ -1,51 +0,0 @@ -using GitHub.Services.Common; -using System; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - //Technically speaking, this is poor REST - //a PUT or POST to a service to create an entity should - //contain that entity, in this case an IdentityScope - //however this contains extra fields not in an IdentityScope - [DataContract] - public class CreateScopeInfo - { - public CreateScopeInfo() - { - } - - internal CreateScopeInfo(Guid parentScopeId, GroupScopeType scopeType, String scopeName, String adminGroupName, String adminGroupDescription, Guid creatorId) - { - ArgumentUtility.CheckStringForNullOrEmpty(scopeName, "scopeName"); - ArgumentUtility.CheckStringForNullOrEmpty(adminGroupName, "adminGroupName"); - ArgumentUtility.CheckStringForNullOrEmpty(adminGroupDescription, "admingGroupDescription"); - - ParentScopeId = parentScopeId; - ScopeType = scopeType; - ScopeName = scopeName; - AdminGroupName = adminGroupName; - AdminGroupDescription = adminGroupDescription; - CreatorId = creatorId; - } - - [DataMember] - public Guid ParentScopeId { get; private set; } - - [DataMember] - public GroupScopeType ScopeType { get; private set; } - - [DataMember] - public String ScopeName { get; private set; } - - [DataMember] - public String AdminGroupName { get; private set; } - - [DataMember] - public String AdminGroupDescription { get; private set; } - - [DataMember(IsRequired=false, EmitDefaultValue=false)] - public Guid CreatorId { get; private set; } - - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityInfo.cs deleted file mode 100644 index b40e904c1..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityInfo.cs +++ /dev/null @@ -1,20 +0,0 @@ -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class FrameworkIdentityInfo - { - [DataMember] - public FrameworkIdentityType IdentityType { get; set; } - - [DataMember] - public string Role { get; set; } - - [DataMember] - public string Identifier { get; set; } - - [DataMember] - public string DisplayName { get; set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityType.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityType.cs deleted file mode 100644 index 6e939ae6c..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/FrameworkIdentityType.cs +++ /dev/null @@ -1,10 +0,0 @@ -namespace GitHub.Services.Identity -{ - public enum FrameworkIdentityType - { - None = 0, - ServiceIdentity = 1, - AggregateIdentity = 2, - ImportedIdentity = 3, - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/GroupMembership.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/GroupMembership.cs deleted file mode 100644 index 311da6f16..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/GroupMembership.cs +++ /dev/null @@ -1,93 +0,0 @@ -// Copyright (c) Microsoft Corporation. All rights reserved. -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Diagnostics; -using System.Globalization; -using System.Runtime.Serialization; -using System.Xml; - -namespace GitHub.Services.Identity -{ - /// - /// - /// - [DataContract] - public sealed class GroupMembership - { - public GroupMembership(Guid queriedId, Guid id, IdentityDescriptor descriptor) - { - QueriedId = queriedId; - Id = id; - Descriptor = descriptor; - Active = true; - } - - [DataMember] - public Guid QueriedId - { - get; - set; - } - - [DataMember] - public Guid Id - { - get - { - return m_id; - } - - set - { - m_id = value; - } - } - - [DataMember] - public IdentityDescriptor Descriptor - { - get; - set; - } - - [DataMember] - public Boolean Active - { - get; - set; - } - - - private Guid m_id; - - public GroupMembership Clone() - { - return new GroupMembership( - queriedId: QueriedId, - id: Id, - descriptor: Descriptor == null ? null : new IdentityDescriptor(Descriptor)) - { - Active = this.Active - }; - } - - public override string ToString() - { - return string.Format("[Id = {0}, Descriptor = {1}, Active = {2}, QueriedId = {3}]", Id, Descriptor, Active, QueriedId); - } - } - - [CollectionDataContract(Name = "GroupMemberships", ItemName = "GroupMembership")] - public class GroupMembershipCollection : List - { - public GroupMembershipCollection() - { - } - - public GroupMembershipCollection(IList source) - : base(source) - { - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/Identity.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/Identity.cs index 874022c0b..eb9b896ad 100644 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/Identity.cs +++ b/src/Sdk/WebApi/WebApi/Contracts/Identity/Identity.cs @@ -35,8 +35,6 @@ namespace GitHub.Services.Identity { Id = Id, Descriptor = new IdentityDescriptor(Descriptor), - SubjectDescriptor = SubjectDescriptor, - SocialDescriptor = SocialDescriptor, ProviderDisplayName = ProviderDisplayName, CustomDisplayName = CustomDisplayName, IsActive = IsActive, @@ -212,23 +210,6 @@ namespace GitHub.Services.Identity set; } - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public SubjectDescriptor SubjectDescriptor - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public SocialDescriptor SocialDescriptor - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } //***************************************************************************************************************** /// /// The display name for the identity as specified by the source identity provider. diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityBatchInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityBatchInfo.cs deleted file mode 100644 index 99727ca8f..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityBatchInfo.cs +++ /dev/null @@ -1,76 +0,0 @@ -using GitHub.Services.Common; -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class IdentityBatchInfo - { - private IdentityBatchInfo() - { - } - - public IdentityBatchInfo(IList subjectDescriptors, QueryMembership queryMembership = QueryMembership.None, IEnumerable propertyNames = null, bool includeRestrictedVisibility = false) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(subjectDescriptors, nameof(subjectDescriptors)); - - this.SubjectDescriptors = new List(subjectDescriptors); - this.QueryMembership = queryMembership; - this.PropertyNames = propertyNames; - this.IncludeRestrictedVisibility = includeRestrictedVisibility; - } - - public IdentityBatchInfo(IList descriptors, QueryMembership queryMembership = QueryMembership.None, IEnumerable propertyNames = null, bool includeRestrictedVisibility = false) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(descriptors, nameof(descriptors)); - - this.Descriptors = new List(descriptors); - this.QueryMembership = queryMembership; - this.PropertyNames = propertyNames; - this.IncludeRestrictedVisibility = includeRestrictedVisibility; - } - - public IdentityBatchInfo(IList identityIds, QueryMembership queryMembership = QueryMembership.None, IEnumerable propertyNames = null, bool includeRestrictedVisibility = false) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(identityIds, nameof(identityIds)); - - this.IdentityIds = new List(identityIds); - this.QueryMembership = queryMembership; - this.PropertyNames = propertyNames; - this.IncludeRestrictedVisibility = includeRestrictedVisibility; - } - - public IdentityBatchInfo(IList socialDescriptors, QueryMembership queryMembership = QueryMembership.None, IEnumerable propertyNames = null, bool includeRestrictedVisibility = false) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(socialDescriptors, nameof(socialDescriptors)); - - this.SocialDescriptors = new List(socialDescriptors); - this.QueryMembership = queryMembership; - this.PropertyNames = propertyNames; - this.IncludeRestrictedVisibility = includeRestrictedVisibility; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public List Descriptors { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public List SubjectDescriptors { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public List IdentityIds { get; private set; } - - [DataMember] - public QueryMembership QueryMembership { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public IEnumerable PropertyNames { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public bool IncludeRestrictedVisibility { get; private set; } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public List SocialDescriptors { get; private set; } - } -} \ No newline at end of file diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityCollections.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityCollections.cs deleted file mode 100644 index 5bc30bcc8..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityCollections.cs +++ /dev/null @@ -1,45 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [CollectionDataContract(Name = "Identities", ItemName = "Identity")] - public class IdentitiesCollection : List - { - public IdentitiesCollection() - { - } - - public IdentitiesCollection(IList source) - : base(source) - { - } - } - - [CollectionDataContract(Name = "Descriptors", ItemName = "Descriptor")] - public class IdentityDescriptorCollection : List - { - public IdentityDescriptorCollection() - { - } - - public IdentityDescriptorCollection(IList source) - : base(source) - { - } - } - - [CollectionDataContract(Name = "IdentityIds", ItemName = "IdentityId")] - public class IdentityIdCollection : List - { - public IdentityIdCollection() - { - } - - public IdentityIdCollection(IList source) - : base(source) - { - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityEnumerations.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityEnumerations.cs index 5947e4ba5..fdcf8e78c 100644 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityEnumerations.cs +++ b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityEnumerations.cs @@ -17,180 +17,4 @@ namespace GitHub.Services.Identity [EnumMember, XmlEnum("2")] TeamProject = 2 } - - - // This is the *same* as IdentitySearchFactor in TFCommon - // Changed the name to avoid conflicts - [DataContract] - public enum IdentitySearchFilter - { - /// - /// NT account name (domain\alias) - /// - [EnumMember] - AccountName = 0, - - /// - /// Display name - /// - [EnumMember] - DisplayName = 1, - - /// - /// Find project admin group - /// - [EnumMember] - AdministratorsGroup = 2, - - /// - /// Find the identity using the identifier - /// - [EnumMember] - Identifier = 3, - - /// - /// Email address - /// - [EnumMember] - MailAddress = 4, - - /// - /// A general search for an identity. - /// - /// - /// This is the default search factor for shorter overloads of ReadIdentity, and typically the correct choice for user input. - /// - /// Use the general search factor to find one or more identities by one of the following properties: - /// * Display name - /// * account name - /// * UniqueName - /// - /// UniqueName may be easier to type than display name. It can also be used to indicate a single identity when two or more identities share the same display name (e.g. "John Smith") - /// - [EnumMember] - General = 5, - - /// - /// Alternate login username - /// - [EnumMember] - Alias = 6, - - /// - /// Find identity using Domain/TenantId - /// - [EnumMember] - [Obsolete("Use read identities to get member of collection valid users group instead.")] - Domain = 7, - - /// - /// Find identity using DirectoryAlias - /// - [EnumMember] - DirectoryAlias = 8, - - /// - /// Find a team group by its name - /// - [Obsolete("Deprecating TeamGroupName, use LocalGroupName instead and filter out non teams groups from the result")] - [EnumMember] - TeamGroupName = 9, - - /// - /// Find a local group (i.e. VSTS or TFS rather than AAD or AD group) by its name - /// - [EnumMember] - LocalGroupName = 10, - } - - // This enum is as an index for IMS identity caches. - // This is the *same* as MembershipQuery in TFCommon - // Changed the name to avoid conflicts - [DataContract] - public enum QueryMembership - { - // These enumeration values should run from zero to N, with no gaps. - // IdentityHostCache uses these values as indexes. - - /// - /// Query will not return any membership data - /// - [EnumMember] - None = 0, - - /// - /// Query will return only direct membership data - /// - [EnumMember] - Direct = 1, - - /// - /// Query will return expanded membership data - /// - [EnumMember] - Expanded = 2, - - /// - /// Query will return expanded up membership data (parents only) - /// - [EnumMember] - ExpandedUp = 3, - - /// - /// Query will return expanded down membership data (children only) - /// - [EnumMember] - ExpandedDown = 4 - - // Dev10 had the public value "Last = 3", as an indicator of the end of the enumeration. - // Dev14 supports public enum value "ExpandedDown = 4" , as an indicator of the end of the enumeration. - } - - // Designates "special" VSS groups. - [DataContract] - public enum SpecialGroupType - { - [EnumMember] - Generic = 0, - - [EnumMember] - AdministrativeApplicationGroup, - - [EnumMember] - ServiceApplicationGroup, - - [EnumMember] - EveryoneApplicationGroup, - - [EnumMember] - LicenseesApplicationGroup, - - [EnumMember] - AzureActiveDirectoryApplicationGroup, - - [EnumMember] - AzureActiveDirectoryRole, - } - - [Flags] - public enum ReadIdentitiesOptions - { - None = 0, - FilterIllegalMemberships = 1 - } - - public enum RestoreProjectOptions - { - /// - /// Brings back all memberships whose members are not owned by the scope - /// - All = 0, - - /// - /// Brings back some memberships whose members are not owned by the scope. - /// The membership will be a subset of All with the additional requirement - /// that the members have visibilty into the project collection scope. - /// - Visible = 1, - } } diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityScope.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityScope.cs deleted file mode 100644 index 2f9db5f93..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityScope.cs +++ /dev/null @@ -1,146 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; -using GitHub.Services.Common; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class IdentityScope - { - internal IdentityScope() - { - } - - //Copy-Constructor - internal IdentityScope(IdentityScope other) - : this(other.Id, other.Name) - { - Administrators = other.Administrators == null ? null : new IdentityDescriptor(other.Administrators); - IsActive = other.IsActive; - IsGlobal = other.IsGlobal; - LocalScopeId = other.LocalScopeId; - ParentId = other.ParentId; - ScopeType = other.ScopeType; - SecuringHostId = other.SecuringHostId; - } - - //Constructor used for the rename operation - internal IdentityScope(Guid id, String name) - { - ArgumentUtility.CheckForEmptyGuid(id, "id"); - ArgumentUtility.CheckStringForNullOrEmpty(name, "name"); - this.Id = id; - this.Name = name; - } - - [DataMember(IsRequired=true)] - public Guid Id - { - get; - - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - internal Guid LocalScopeId - { - get; - - set; - } - - [DataMember(IsRequired=false, EmitDefaultValue=false)] - public Guid ParentId - { - get; - - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public GroupScopeType ScopeType - { - get; - - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public IdentityDescriptor Administrators - { - get; - - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Boolean IsGlobal - { - get; - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Guid SecuringHostId - { - get; - - internal set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Boolean IsActive - { - get; - - internal set; - } - - public IdentityScope Clone() - { - return new IdentityScope(this); - } - - public override string ToString() - { - return $"[Id={Id}, Name={Name}, LocalScopeId={LocalScopeId}, ParentId={ParentId}, ScopeType={ScopeType}, SecuringHostId={SecuringHostId}, Administrators={Administrators}, IsActive={IsActive}, IsGlobal={IsGlobal}]"; - } - - private SubjectDescriptor subjectDescriptor; - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public SubjectDescriptor SubjectDescriptor - { - get - { - if (subjectDescriptor == default(SubjectDescriptor)) - { - subjectDescriptor = new SubjectDescriptor(Graph.Constants.SubjectType.GroupScopeType, Id.ToString()); - } - - return subjectDescriptor; - } - } - } - - [CollectionDataContract(Name = "Scopes", ItemName = "Scope")] - public class IdentityScopeCollection : List - { - public IdentityScopeCollection() - { - } - - public IdentityScopeCollection(IList source) - : base(source) - { - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySelf.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySelf.cs deleted file mode 100644 index 9c8c9df2e..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySelf.cs +++ /dev/null @@ -1,105 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Diagnostics; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - /// - /// Identity information. - /// - [DebuggerDisplay("{DisplayName}")] - [DataContract] - public class IdentitySelf - { - /// - /// This is the VSID of the home tenant profile. If the profile is signed into the home tenant or if the profile - /// has no tenants then this Id is the same as the Id returned by the profile/profiles/me endpoint. Going forward - /// it is recommended that you use the combined values of Origin, OriginId and Domain to uniquely identify a user - /// rather than this Id. - /// - [DataMember] - public Guid Id - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// The display name. For AAD accounts with multiple tenants this is the display name of the profile in the home tenant. - /// - [DataMember] - public String DisplayName - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// The UserPrincipalName (UPN) of the account. This value comes from the source provider. - /// - [DataMember] - public string AccountName - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// The type of source provider for the origin identifier. - /// For MSA accounts this is "msa". For AAD accounts this is "aad". - /// - [DataMember] - public string Origin - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// The unique identifier from the system of origin. If there are multiple tenants this is the - /// unique identifier of the account in the home tenant. - /// (For MSA this is the PUID in hex notation, for AAD this is the object id.) - /// - [DataMember] - public string OriginId - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// This represents the name of the container of origin. - /// For AAD accounts this is the tenantID of the home tenant. - /// For MSA accounts this is the string "Windows Live ID". - /// - [DataMember] - public string Domain - { - get; - - [EditorBrowsable(EditorBrowsableState.Never)] - set; - } - - /// - /// For AAD accounts this is all of the tenants that this account is a member of. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public IEnumerable Tenants - { - get; set; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySnapshot.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySnapshot.cs deleted file mode 100644 index 939541935..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentitySnapshot.cs +++ /dev/null @@ -1,81 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class IdentitySnapshot - { - public IdentitySnapshot() - { - } - - public IdentitySnapshot(Guid scopeId) - { - ScopeId = scopeId; - Scopes = new List(); - Groups = new List(); - Memberships = new List(); - IdentityIds = new List(); - } - - [DataMember] - public Guid ScopeId - { - get; - set; - } - - [DataMember] - public List Scopes - { - get; - set; - } - - [DataMember] - public List Groups - { - get; - set; - } - - [DataMember] - public List Memberships - { - get; - set; - } - - [DataMember] - public List IdentityIds - { - get; - set; - } - - public IdentitySnapshot Clone() - { - return new IdentitySnapshot() - { - ScopeId = this.ScopeId, - Scopes = this.Scopes?.Where(x => x != null).Select(x => x.Clone()).ToList(), - Groups = this.Groups?.Where(x => x != null).Select(x => x.Clone()).ToList(), - Memberships = this.Memberships?.Where(x => x != null).Select(x => x.Clone()).ToList(), - IdentityIds = this.IdentityIds.ToList(), - }; - } - - public override string ToString() - { - return string.Format("[ScopeId = {0}, Scopes={1}, Groups={2}, Memberships={3}, Identities={4}]", - ScopeId, - Scopes?.Count, - Groups?.Count, - Memberships?.Count, - IdentityIds?.Count); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityUpdateData.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityUpdateData.cs deleted file mode 100644 index e0084a566..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/IdentityUpdateData.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class IdentityUpdateData - { - [DataMember] - public Int32 Index { get; set; } - - [DataMember] - public Guid Id { get; set; } - - [DataMember] - public Boolean Updated { get; set; } - } -} \ No newline at end of file diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/RequestHeadersContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/RequestHeadersContext.cs deleted file mode 100644 index e473bfe12..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/RequestHeadersContext.cs +++ /dev/null @@ -1,64 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Net.Http.Headers; - -namespace GitHub.Services.Identity -{ - public class RequestHeadersContext - { - internal SequenceContext SequenceContext { get; set; } - - internal bool IgnoreCache { get; set; } - - public RequestHeadersContext(SequenceContext sequenceContext) : - this(sequenceContext, false) - { - } - - public RequestHeadersContext(SequenceContext sequenceContext, bool ignoreCache) - { - SequenceContext = sequenceContext; - IgnoreCache = ignoreCache; - } - - private static bool ParseOrGetDefault(string s) - { - if (!string.IsNullOrWhiteSpace(s) && bool.TryParse(s, out var value)) - { - return value; - } - return false; - } - - internal class HeadersUtils - { - public static KeyValuePair[] PopulateRequestHeaders(RequestHeadersContext requestHeaderContext) - { - if (requestHeaderContext == null) - { - return new KeyValuePair[0]; - } - - KeyValuePair[] sequenceContextHeaders = SequenceContext.HeadersUtils.PopulateRequestHeaders(requestHeaderContext.SequenceContext); - KeyValuePair[] resultHeaderPairs = new KeyValuePair[sequenceContextHeaders.Length + 1]; - sequenceContextHeaders.CopyTo(resultHeaderPairs, 0); - resultHeaderPairs[sequenceContextHeaders.Length] = new KeyValuePair(c_ignoreCacheHeader, requestHeaderContext.IgnoreCache.ToString()); - return resultHeaderPairs; - } - - public static bool TryExtractRequestHeaderContext(HttpRequestHeaders httpRequestHeaders, out RequestHeadersContext requestHeadersContext) - { - requestHeadersContext = null; - bool hasIgnoreCacheHeader = httpRequestHeaders.TryGetValues(c_ignoreCacheHeader, out IEnumerable ignoreCacheValue) && ignoreCacheValue != null; - bool hasSequenceContextHeader = SequenceContext.HeadersUtils.TryExtractSequenceContext(httpRequestHeaders, out SequenceContext sequenceContext); - bool ignoreCache = ParseOrGetDefault(ignoreCacheValue?.FirstOrDefault()); - requestHeadersContext = new RequestHeadersContext(sequenceContext, ignoreCache); - return hasIgnoreCacheHeader || hasSequenceContextHeader; - } - - private const string c_ignoreCacheHeader = "X-VSSF-IMS-IgnoreCache"; - } - - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/SequenceContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/SequenceContext.cs deleted file mode 100644 index da935a228..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/SequenceContext.cs +++ /dev/null @@ -1,102 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Net.Http.Headers; - -namespace GitHub.Services.Identity -{ - public class SequenceContext - { - public SequenceContext(long identitySequenceId, long groupSequenceId) : - this(identitySequenceId, groupSequenceId, SequenceContext.UnspecifiedSequenceId) - { - } - - public SequenceContext(long identitySequenceId, long groupSequenceId, long organizationIdentitySequenceId) : - this(identitySequenceId, groupSequenceId, organizationIdentitySequenceId, 0) - { - } - - public SequenceContext(long identitySequenceId, long groupSequenceId, long organizationIdentitySequenceId, long pageSize) - { - IdentitySequenceId = identitySequenceId; - GroupSequenceId = groupSequenceId; - OrganizationIdentitySequenceId = organizationIdentitySequenceId; - PageSize = pageSize; - } - - internal long IdentitySequenceId { get; } - - internal long GroupSequenceId { get; } - - internal long OrganizationIdentitySequenceId { get; } - - internal long PageSize { get; } - - internal SequenceContext Clone() - { - return new SequenceContext(IdentitySequenceId, GroupSequenceId, OrganizationIdentitySequenceId); - } - - public override string ToString() => $"[{nameof(IdentitySequenceId)}:{IdentitySequenceId}, {nameof(GroupSequenceId)}:{GroupSequenceId}, {nameof(OrganizationIdentitySequenceId)}:{OrganizationIdentitySequenceId}]"; - - internal const long UnspecifiedSequenceId = -1; - - internal static SequenceContext MaxSequenceContext = new SequenceContext(long.MaxValue, long.MaxValue, long.MaxValue, 0); - internal static SequenceContext InitSequenceContext = new SequenceContext(UnspecifiedSequenceId, UnspecifiedSequenceId, UnspecifiedSequenceId, 0); - - internal class HeadersUtils - { - internal const string MinIdentitySequenceId = "X-VSSF-MinIdentitySequenceId"; - internal const string MinGroupSequenceId = "X-VSSF-MinGroupSequenceId"; - internal const string MinOrgIdentitySequenceId = "X-VSSF-MinOrgIdentitySequenceId"; - internal const string PageSize = "X-VSSF-PagingSize"; - - internal static bool TryExtractSequenceContext(HttpRequestHeaders httpRequestHeaders, out SequenceContext sequenceContext) - { - sequenceContext = null; - bool hasMinIdentitySequenceHeader = httpRequestHeaders.TryGetValues(MinIdentitySequenceId, out var minIdentitySequenceIdValues) && minIdentitySequenceIdValues != null; - bool hasMinGroupSequenceHeader = httpRequestHeaders.TryGetValues(MinGroupSequenceId, out var minGroupSequenceIdValues) && minGroupSequenceIdValues != null; - bool hasMinOrgIdentitySequenceHeader = httpRequestHeaders.TryGetValues(MinOrgIdentitySequenceId, out var minOrgIdentitySequenceIdValues) && minOrgIdentitySequenceIdValues != null; - bool hasPageSizeHeader = httpRequestHeaders.TryGetValues(PageSize, out var pageSizeValues) && pageSizeValues != null; - - if (!hasMinGroupSequenceHeader && !hasMinIdentitySequenceHeader && !hasMinOrgIdentitySequenceHeader) - { - return false; - } - - long minIdentitySequenceId = ParseOrGetDefault(minIdentitySequenceIdValues?.FirstOrDefault()); - long minGroupSequenceId = ParseOrGetDefault(minGroupSequenceIdValues?.FirstOrDefault()); - long minOrgIdentitySequenceId = ParseOrGetDefault(minOrgIdentitySequenceIdValues?.FirstOrDefault()); - long pageSize = ParseOrGetDefault(pageSizeValues?.FirstOrDefault()); - sequenceContext = new SequenceContext(minIdentitySequenceId, minGroupSequenceId, minOrgIdentitySequenceId, pageSize); - return true; - } - - internal static KeyValuePair[] PopulateRequestHeaders(SequenceContext sequenceContext) - { - if (sequenceContext == null) - { - return new KeyValuePair[0]; - } - - return new[] - { - new KeyValuePair(MinIdentitySequenceId, sequenceContext.IdentitySequenceId.ToString()), - new KeyValuePair(MinGroupSequenceId, sequenceContext.GroupSequenceId.ToString()), - new KeyValuePair(MinOrgIdentitySequenceId, sequenceContext.OrganizationIdentitySequenceId.ToString()), - new KeyValuePair(PageSize, sequenceContext.PageSize.ToString()) - }; - } - - private static long ParseOrGetDefault(string s) - { - if (!string.IsNullOrWhiteSpace(s) && long.TryParse(s, out long value)) - { - return value; - } - return UnspecifiedSequenceId; - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/SwapIdentityInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/SwapIdentityInfo.cs deleted file mode 100644 index 25b7652cb..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/SwapIdentityInfo.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DataContract] - public class SwapIdentityInfo - { - public SwapIdentityInfo() - { - } - - public SwapIdentityInfo(Guid id1, Guid id2) - { - this.Id1 = id1; - this.Id2 = id2; - } - - [DataMember] - public Guid Id1 { get; private set; } - - [DataMember] - public Guid Id2 { get; private set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Identity/TenantInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Identity/TenantInfo.cs deleted file mode 100644 index 482d12254..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Identity/TenantInfo.cs +++ /dev/null @@ -1,24 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Runtime.Serialization; - -namespace GitHub.Services.Identity -{ - [DebuggerDisplay("{TenantName}")] - [DataContract] - public class TenantInfo - { - [DataMember] - public Guid TenantId { get; set; } - - [DataMember] - public string TenantName { get; set; } - - [DataMember] - public bool HomeTenant { get; set; } - - [DataMember] - public IEnumerable VerifiedDomains { get; set; } - } -} \ No newline at end of file diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/AccountLicense.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/AccountLicense.cs deleted file mode 100644 index 7a113cbc6..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/AccountLicense.cs +++ /dev/null @@ -1,134 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace GitHub.Services.Licensing -{ - /// - /// Represents an Account license - /// - public sealed class AccountLicense : License, IComparable - { - /// - /// An Early Adopter License - /// - public static readonly AccountLicense EarlyAdopter = new AccountLicense(AccountLicenseType.EarlyAdopter); - - /// - /// A Stakeholder License - /// - public static readonly AccountLicense Stakeholder = new AccountLicense(AccountLicenseType.Stakeholder); - - /// - /// An Express License - /// - public static readonly AccountLicense Express = new AccountLicense(AccountLicenseType.Express); - - /// - /// A Professional License - /// - public static readonly AccountLicense Professional = new AccountLicense(AccountLicenseType.Professional); - - /// - /// An Advanced License - /// - public static readonly AccountLicense Advanced = new AccountLicense(AccountLicenseType.Advanced); - - /// - /// Initializes an instance of the class - /// - /// The type of license - private AccountLicense(AccountLicenseType license) - : base(LicensingSource.Account, typeof(AccountLicenseType), (int)license) - { - } - - /// - /// Gets the license type for the license - /// - public AccountLicenseType License - { - get { return (AccountLicenseType)this.GetLicenseAsInt32(); } - } - - /// - /// Compares the current object with another object of the same type. - /// - /// A value that indicates the relative order of the objects being compared. The return value has the following meanings: Value Meaning Less than zero This object is less than the parameter.Zero This object is equal to . Greater than zero This object is greater than . - /// An object to compare with this object. - public int CompareTo(AccountLicense other) - { - return Compare(this, other); - } - - /// - /// Compares two objects of the same type. - /// - /// A value that indicates the relative order of the objects being compared. - /// The left-hand operand to compare - /// The right-hand operand to compare - public static int Compare(AccountLicense left, AccountLicense right) - { - if (object.ReferenceEquals(left, null)) - { - if (object.ReferenceEquals(right, null)) - { - return 0; - } - return -1; - } - else if (object.ReferenceEquals(right, null)) - { - return +1; - } - - return LicenseComparer.Instance.Compare(left, right); - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is greater than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator >(AccountLicense left, AccountLicense right) - { - return Compare(left, right) > 0; - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is less than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator <(AccountLicense left, AccountLicense right) - { - return Compare(left, right) < 0; - } - - /// - /// Gets a instance for the provided license type - /// - /// The type of license - /// A license for the provided license type - /// license was not in the list of allowed values - public static License GetLicense(AccountLicenseType license) - { - switch (license) - { - case AccountLicenseType.None: return None; - case AccountLicenseType.EarlyAdopter: return EarlyAdopter; - case AccountLicenseType.Stakeholder: return Stakeholder; - case AccountLicenseType.Express: return Express; - case AccountLicenseType.Professional: return Professional; - case AccountLicenseType.Advanced: return Advanced; - default: - throw new InvalidEnumArgumentException("license", (int)license, typeof(AccountLicenseType)); - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/Definitions.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/Definitions.cs deleted file mode 100644 index ac75c659c..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/Definitions.cs +++ /dev/null @@ -1,96 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Licensing -{ - [DataContract] - public enum AssignmentSource - { - None = 0, - Unknown = 1, - GroupRule = 2 - } - - [DataContract] - public enum LicensingOrigin - { - None = 0, - OnDemandPrivateProject = 1, - OnDemandPublicProject = 2, - UserHubInvitation = 3, - PrivateProjectInvitation = 4, - PublicProjectInvitation = 5, - } - - [DataContract] - public enum LicensingSource - { - None = 0, - Account = 1, - Msdn = 2, - Profile = 3, - Auto = 4, - Trial = 5 - } - - [DataContract] - [ClientIncludeModel] - public enum MsdnLicenseType - { - None = 0, - Eligible = 1, - Professional = 2, - Platforms = 3, - TestProfessional = 4, - Premium = 5, - Ultimate = 6, - Enterprise = 7, - } - - [DataContract] - [ClientIncludeModel] - public enum AccountLicenseType - { - None = 0, - EarlyAdopter = 1, - Express = 2, - Professional = 3, - Advanced = 4, - Stakeholder = 5, - } - - [DataContract] - public enum VisualStudioOnlineServiceLevel - { - /// - /// No service rights. The user cannot access the account - /// - [EnumMember] - None = 0, - - /// - /// Default or minimum service level - /// - [EnumMember] - Express = 1, - - /// - /// Premium service level - either by purchasing on the Azure portal or by purchasing the appropriate MSDN subscription - /// - [EnumMember] - Advanced = 2, - - /// - /// Only available to a specific set of MSDN Subscribers - /// - [EnumMember] - AdvancedPlus = 3, - - /// - /// Stakeholder service level - /// - [EnumMember] - Stakeholder = 4, - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/License.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/License.cs deleted file mode 100644 index fc0e0987f..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/License.cs +++ /dev/null @@ -1,403 +0,0 @@ -using System; -using System.ComponentModel; -using System.Diagnostics; -using System.Text; -using Newtonsoft.Json; - -namespace GitHub.Services.Licensing -{ - /// - /// The base class for a specific license source and license - /// - [JsonConverter(typeof(LicenseJsonConverter))] - [TypeConverter(typeof(LicenseTypeConverter))] - [JsonObject] - [DebuggerDisplay("{ToString(), nq}")] - public abstract class License : IEquatable - { - /// - /// Represents a non-existent license - /// - public static readonly License None = new NoLicense(); - - /// - /// Represents a license that is auto assigned at user sign-in (e.g. from msdn licenses) - /// - public static readonly License Auto = new AutoLicense(); - - private Type licenseEnumType; - private int license; - - /// - /// Initializes a new instance of the License type - /// - /// The source of the license - /// The type for the license enum - /// The value for the license - internal License(LicensingSource source, Type licenseEnumType, int license) - { - this.licenseEnumType = licenseEnumType; - this.license = license; - this.Source = source; - } - - /// - /// Gets the source of the license - /// - public LicensingSource Source { get; private set; } - - /// - /// Gets the internal value for the license - /// - internal int GetLicenseAsInt32() - { - return this.license; - } - - /// - /// Serves as a hash function for a particular type. - /// - /// A hash code for the current . - public override int GetHashCode() - { - return this.Source.GetHashCode() - ^ this.license.GetHashCode(); - } - - /// - /// Determines whether the specified System.Object is equal to the current . - /// - /// The object to compare with the current object. - /// true if the specified object is equal to the current object; otherwise, false. - public override bool Equals(object obj) - { - return this.Equals(obj as License); - } - - /// - /// Determines whether the specified is equal to the current . - /// - /// The object to compare with the current object. - /// true if the specified object is equal to the current object; otherwise, false. - public bool Equals(License obj) - { - return obj != null - && this.Source == obj.Source - && this.license == obj.license; - } - - /// - /// Returns a string that represents the current object. - /// - /// A string that represents the current object. - public override string ToString() - { - var sb = new StringBuilder(); - sb.Append(this.Source.ToString()); - sb.Append('-'); - sb.Append(Enum.GetName(this.licenseEnumType, this.license)); - return sb.ToString(); - } - - /// - /// Parses the provided text into a - /// - /// The text to parse - /// The parsed - /// The text was in the wrong format - public static License Parse(string text) - { - return Parse(text, ignoreCase: false); - } - - /// - /// Parses the provided text into a - /// - /// The text to parse - /// A value indicating whether to ignore the case of the text - /// The parsed - /// The text was in the wrong format - public static License Parse(string text, bool ignoreCase) - { - License license; - if (!TryParse(text, ignoreCase, out license)) - { - throw new FormatException(); - } - - return license; - } - - /// - /// Tries to parse the provided text into a - /// - /// The text to parse - /// The parsed - /// True if the could be parsed; otherwise, false - public static bool TryParse(string text, out License license) - { - return TryParse(text, false, out license); - } - - /// - /// Tries to parse the provided text into a - /// - /// The text to parse - /// A value indicating whether to ignore the case of the text - /// The parsed - /// True if the could be parsed; otherwise, false - public static bool TryParse(string text, bool ignoreCase, out License license) - { - license = None; - if (string.IsNullOrWhiteSpace(text)) - { - return false; - } - - var parts = text.Split('-'); - - LicensingSource source; - if (!Enum.TryParse(parts[0], ignoreCase, out source)) - { - return false; - } - - if (parts.Length == 1 && source == LicensingSource.None) - { - return true; - } - - if (parts.Length == 1 && source == LicensingSource.Auto) - { - license = Auto; - return true; - } - - if (parts.Length > 2) - { - return false; - } - - switch (source) - { - case LicensingSource.Msdn: - MsdnLicenseType msdnLicense; - if (Enum.TryParse(parts[1], ignoreCase, out msdnLicense) && msdnLicense != MsdnLicenseType.None) - { - license = MsdnLicense.GetLicense(msdnLicense); - return true; - } - - break; - - case LicensingSource.Account: - AccountLicenseType accountLicense; - if (Enum.TryParse(parts[1], ignoreCase, out accountLicense) && accountLicense != AccountLicenseType.None) - { - license = AccountLicense.GetLicense(accountLicense); - return true; - } - - break; - - case LicensingSource.Auto: - LicensingSource licenseSource; - if (Enum.TryParse(parts[1], ignoreCase, out licenseSource)) - { - license = AutoLicense.GetLicense(licenseSource); - return true; - } - - break; - } - - return false; - } - - /// - /// Gets a value indicating whether the two provided values are equivalent - /// - /// The first value - /// The second value - /// True if both values are equivalent; otherwise, false - public static bool Equals(License left, License right) - { - if (object.ReferenceEquals(left, null)) - { - return object.ReferenceEquals(right, null); - } - else if (object.ReferenceEquals(right, null)) - { - return false; - } - - return left.Equals(right); - } - - /// - /// Gets a value indicating whether the license is null or - /// - /// The license - /// true if the license is either null or ; otherwise, false - public static bool IsNullOrNone(License license) - { - return license == null || license.Source == LicensingSource.None; - } - - /// - /// Gets the license for the provided source and license type - /// - /// The source - /// The license type - /// The license - internal static License GetLicense(LicensingSource source, int license) - { - switch (source) - { - case LicensingSource.None: - return None; - - case LicensingSource.Account: - return AccountLicense.GetLicense((AccountLicenseType)license); - - case LicensingSource.Msdn: - return MsdnLicense.GetLicense((MsdnLicenseType)license); - - case LicensingSource.Profile: - throw new NotSupportedException(); - - case LicensingSource.Auto: - return Auto; - - default: - throw new InvalidEnumArgumentException("source", (int)source, typeof(LicensingSource)); - } - } - - /// - /// Gets a value indicating whether the two provided values are equivalent - /// - /// The first operand - /// The second operand - /// True if both values are equivalent; otherwise, false - public static bool operator ==(License left, License right) - { - return Equals(left, right); - } - - /// - /// Gets a value indicating whether the two provided values are not equivalent - /// - /// The first operand - /// The second operand - /// True if values are not equivalent; otherwise, false - public static bool operator !=(License left, License right) - { - return !Equals(left, right); - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is greater than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator >(License left, License right) - { - return LicenseComparer.Instance.Compare(left, right) > 0; - } - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is greater than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator >=(License left, License right) - { - return LicenseComparer.Instance.Compare(left, right) >= 0; - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is less than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator <(License left, License right) - { - return LicenseComparer.Instance.Compare(left, right) < 0; - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is less than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator <=(License left, License right) - { - return LicenseComparer.Instance.Compare(left, right) <= 0; - } - - /// - /// A concrete that represents no license - /// - private sealed class NoLicense : License - { - /// - /// Initializes a new instance of the class - /// - internal NoLicense() - : base(LicensingSource.None, null, 0) - { - } - - /// - /// Returns a string that represents the current object. - /// - /// A string that represents the current object. - public override string ToString() - { - return "None"; - } - } - - internal sealed class AutoLicense : License - { - /// - /// Represents an Auto license where the source provider is MSDN - /// - internal static readonly License Msdn = GetLicense(LicensingSource.Msdn); - - /// - /// Initializes a new instance of the class - /// - internal AutoLicense() - : base(LicensingSource.Auto, null, 0) - { - } - - private AutoLicense(LicensingSource licenseSource) - : base(LicensingSource.Auto, typeof(LicensingSource), (int) licenseSource) - { - } - - /// - /// Gets a instance for the provided licensing source - /// - internal static AutoLicense GetLicense(LicensingSource source) - { - return new AutoLicense(source); - } - - /// - /// Returns a string that represents the current object. - /// - /// A string that represents the current object. - public override string ToString() - { - return this.GetLicenseAsInt32() == 0 ? "Auto" : base.ToString(); - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseComparer.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseComparer.cs deleted file mode 100644 index 48c39f2dd..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseComparer.cs +++ /dev/null @@ -1,98 +0,0 @@ -using System.Collections.Generic; - -namespace GitHub.Services.Licensing -{ - public class LicenseComparer : IComparer - { - public int Compare(License x, License y) - { - if (x == null && y == null) - { - return 0; - } - - if (x == null) - { - return -1; - } - - if (y == null) - { - return 1; - } - - // both licenses have to have a source of Account or Msdn to compare weights - if((x.Source == LicensingSource.Account || x.Source == LicensingSource.Msdn) - && (y.Source == LicensingSource.Account || y.Source == LicensingSource.Msdn)) - { - var thisLicenseWeight = GetWeight(x); - var otherLicenseWeight = GetWeight(y); - - return thisLicenseWeight.CompareTo(otherLicenseWeight); - } - - // Not a known source. Just do a license value compare. - return x.GetLicenseAsInt32().CompareTo(y.GetLicenseAsInt32()); - } - - public int GetWeight(License license) - { - if (license == License.None) - { - return 0; - } - else if (license == AccountLicense.Stakeholder) - { - return 1; - } - else if (license == AccountLicense.Express) - { - return 2; - } - else if (license == AccountLicense.Professional) - { - return 3; - } - else if (license == MsdnLicense.Eligible) - { - return 4; - } - else if (license == MsdnLicense.Professional) - { - return 5; - } - else if (license == AccountLicense.Advanced) - { - return 6; - } - else if (license == MsdnLicense.TestProfessional) - { - return 7; - } - else if (license == MsdnLicense.Platforms) - { - return 8; - } - else if (license == MsdnLicense.Premium) - { - return 9; - } - else if (license == MsdnLicense.Ultimate) - { - return 10; - } - else if (license == MsdnLicense.Enterprise) - { - return 11; - } - else if (license == AccountLicense.EarlyAdopter) - { - return 12; - } - - return 0; // Unexpected license - } - - public static LicenseComparer Instance { get; } = new LicenseComparer(); - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseJsonConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseJsonConverter.cs deleted file mode 100644 index f7baceb7c..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseJsonConverter.cs +++ /dev/null @@ -1,66 +0,0 @@ -using System; -using System.Reflection; -using GitHub.Services.WebApi; -using Newtonsoft.Json; - -namespace GitHub.Services.Licensing -{ - /// - /// Converts between a and a JSON-serialized license string - /// - internal sealed class LicenseJsonConverter : VssSecureJsonConverter - { - /// - /// Determines whether this instance can convert the specified object type. - /// - /// Type of the object - /// true if this instance can convert the specified object type; otherwise, false. - public override bool CanConvert(Type objectType) - { - return typeof(License).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - - /// - /// Reads the JSON representation of the object. - /// - /// The Newtonsoft.Json.JsonReader to read from. - /// Type of the object. - /// The existing value of object being read. - /// The calling serializer. - /// The object value. - public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) - { - if (reader.TokenType == JsonToken.String) - { - return License.Parse(reader.Value.ToString(), ignoreCase: true); - } - - if (reader.TokenType == JsonToken.Null) - { - return null; - } - - throw new JsonSerializationException(); - } - - /// - /// Writes the JSON representation of the object. - /// - /// The Newtonsoft.Json.JsonWriter to write to. - /// The value. - /// The calling serializer. - public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) - { - base.WriteJson(writer, value, serializer); - - if (value == null) - { - writer.WriteNull(); - return; - } - - var license = (License)value; - writer.WriteValue(license.ToString()); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseTypeConverter.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseTypeConverter.cs deleted file mode 100644 index adedb23c2..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/LicenseTypeConverter.cs +++ /dev/null @@ -1,85 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace GitHub.Services.Licensing -{ - /// - /// Performs type conversion for a License - /// - internal sealed class LicenseTypeConverter : TypeConverter - { - /// Returns whether this converter can convert an object of the given type to the type of this converter, using the specified context. - /// true if this converter can perform the conversion; otherwise, false. - /// An that provides a format context. - /// A that represents the type you want to convert from. - public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType) - { - return sourceType == typeof(string) || base.CanConvertFrom(context, sourceType); - } - - /// Returns whether this converter can convert the object to the specified type, using the specified context. - /// true if this converter can perform the conversion; otherwise, false. - /// An that provides a format context. - /// A that represents the type you want to convert to. - public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType) - { - return destinationType == typeof(string) || base.CanConvertTo(context, destinationType); - } - - /// Converts the given object to the type of this converter, using the specified context and culture information. - /// An that represents the converted value. - /// An that provides a format context. - /// The to use as the current culture. - /// The to convert. - /// The conversion cannot be performed. - public override object ConvertFrom(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value) - { - var text = value as string; - if (text != null) - { - return License.Parse(text); - } - - return base.ConvertFrom(context, culture, value); - } - - /// Converts the given value object to the specified type, using the specified context and culture information. - /// An that represents the converted value. - /// An that provides a format context. - /// A . If null is passed, the current culture is assumed. - /// The to convert. - /// The to convert the parameter to. - /// The parameter is null. - /// The conversion cannot be performed. - public override object ConvertTo(ITypeDescriptorContext context, System.Globalization.CultureInfo culture, object value, Type destinationType) - { - var license = value as License; - if (license != null && destinationType == typeof(string)) - { - return license.ToString(); - } - - return base.ConvertTo(context, culture, value, destinationType); - } - - /// Returns whether the given value object is valid for this type and for the specified context. - /// true if the specified value is valid for this object; otherwise, false. - /// An that provides a format context. - /// The to test for validity. - public override bool IsValid(ITypeDescriptorContext context, object value) - { - var text = value as string; - if (text != null) - { - License license; - return License.TryParse(text, out license); - } - - return base.IsValid(context, value); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Licensing/MsdnLicense.cs b/src/Sdk/WebApi/WebApi/Contracts/Licensing/MsdnLicense.cs deleted file mode 100644 index 8aefe17da..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Licensing/MsdnLicense.cs +++ /dev/null @@ -1,143 +0,0 @@ -using System; -using System.Collections.Generic; -using System.ComponentModel; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace GitHub.Services.Licensing -{ - /// - /// Represents an Msdn license - /// - public sealed class MsdnLicense : License, IComparable - { - /// - /// The account user is MSDN Eligible - /// - public static readonly MsdnLicense Eligible = new MsdnLicense(MsdnLicenseType.Eligible); - - /// - /// The account user has an MSDN Professional license - /// - public static readonly MsdnLicense Professional = new MsdnLicense(MsdnLicenseType.Professional); - - /// - /// The account user has an MSDN Platforms license - /// - public static readonly MsdnLicense Platforms = new MsdnLicense(MsdnLicenseType.Platforms); - - /// - /// The account user has an MSDN TestProfessional license - /// - public static readonly MsdnLicense TestProfessional = new MsdnLicense(MsdnLicenseType.TestProfessional); - - /// - /// The account user has an MSDN Premium license - /// - public static readonly MsdnLicense Premium = new MsdnLicense(MsdnLicenseType.Premium); - - /// - /// The account user has an MSDN Ultimate license - /// - public static readonly MsdnLicense Ultimate = new MsdnLicense(MsdnLicenseType.Ultimate); - - /// - /// The account user has an MSDN Enterprise license - /// - public static readonly MsdnLicense Enterprise = new MsdnLicense(MsdnLicenseType.Enterprise); - - /// - /// Initializes an instance of the class - /// - /// The type of license - private MsdnLicense(MsdnLicenseType license) - : base(LicensingSource.Msdn, typeof(MsdnLicenseType), (int)license) - { - } - - /// - /// Gets the license type for the license - /// - public MsdnLicenseType License - { - get { return (MsdnLicenseType)this.GetLicenseAsInt32(); } - } - - /// - /// Compares the current object with another object of the same type. - /// - /// A value that indicates the relative order of the objects being compared. The return value has the following meanings: Value Meaning Less than zero This object is less than the parameter.Zero This object is equal to . Greater than zero This object is greater than . - /// An object to compare with this object. - public int CompareTo(MsdnLicense other) - { - return Compare(this, other); - } - - /// - /// Compares two objects of the same type. - /// - /// A value that indicates the relative order of the objects being compared. - /// The left-hand operand to compare - /// The right-hand operand to compare - public static int Compare(MsdnLicense left, MsdnLicense right) - { - if (object.ReferenceEquals(left, null)) - { - if (object.ReferenceEquals(right, null)) return 0; - return -1; - } - else if (object.ReferenceEquals(right, null)) - { - return +1; - } - - return LicenseComparer.Instance.Compare(left, right); - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is greater than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator >(MsdnLicense left, MsdnLicense right) - { - return Compare(left, right) > 0; - } - - /// - /// Compares two objects of the same type. - /// - /// True if the left-hand value is less than the right-hand value; otherwise, false - /// The left-hand operand to compare - /// The right-hand operand to compare - public static bool operator <(MsdnLicense left, MsdnLicense right) - { - return Compare(left, right) < 0; - } - - /// - /// Gets a instance for the provided license type - /// - /// The type of license - /// A license for the provided license type - /// license was not in the list of allowed values - public static License GetLicense(MsdnLicenseType license) - { - switch (license) - { - case MsdnLicenseType.None: return None; - case MsdnLicenseType.Eligible: return Eligible; - case MsdnLicenseType.Professional: return Professional; - case MsdnLicenseType.Platforms: return Platforms; - case MsdnLicenseType.TestProfessional: return TestProfessional; - case MsdnLicenseType.Premium: return Premium; - case MsdnLicenseType.Ultimate: return Ultimate; - case MsdnLicenseType.Enterprise: return Enterprise; - default: - throw new InvalidEnumArgumentException("license", (int)license, typeof(MsdnLicenseType)); - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Location/Constants.cs b/src/Sdk/WebApi/WebApi/Contracts/Location/Constants.cs index 83f5b4c07..d825e0665 100644 --- a/src/Sdk/WebApi/WebApi/Contracts/Location/Constants.cs +++ b/src/Sdk/WebApi/WebApi/Contracts/Location/Constants.cs @@ -87,21 +87,5 @@ namespace GitHub.Services.Location public static class AccessMappingConstants { public static readonly string PublicAccessMappingMoniker = "PublicAccessMapping"; - public static readonly string ServerAccessMappingMoniker = "ServerAccessMapping"; - public static readonly string ClientAccessMappingMoniker = "ClientAccessMapping"; - public static readonly string HostGuidAccessMappingMoniker = "HostGuidAccessMapping"; - public static readonly string RootDomainMappingMoniker = "RootDomainMapping"; - public static readonly string AzureInstanceMappingMoniker = "AzureInstanceMapping"; - public static readonly string ServicePathMappingMoniker = "ServicePathMapping"; - public static readonly string ServiceDomainMappingMoniker = "ServiceDomainMapping"; - public static readonly string LegacyPublicAccessMappingMoniker = "LegacyPublicAccessMapping"; - public static readonly string MessageQueueAccessMappingMoniker = "MessageQueueAccessMapping"; - public static readonly string LegacyAppDotAccessMappingMoniker = "LegacyAppDotDomain"; - public static readonly string AffinitizedMultiInstanceAccessMappingMoniker = "AffinitizedMultiInstanceAccessMapping"; - - public static readonly string VstsAccessMapping = "VstsAccessMapping"; - public static readonly string DevOpsAccessMapping = "CodexAccessMapping"; - - [Obsolete][EditorBrowsable(EditorBrowsableState.Never)] public static readonly string ServiceAccessMappingMoniker = "ServiceAccessMappingMoniker"; } } diff --git a/src/Sdk/WebApi/WebApi/Contracts/Location/ResourceAreaInfo.cs b/src/Sdk/WebApi/WebApi/Contracts/Location/ResourceAreaInfo.cs deleted file mode 100644 index b784e3b20..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Location/ResourceAreaInfo.cs +++ /dev/null @@ -1,31 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.Services.Location -{ - [DataContract] - public class ResourceAreaInfo - { - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public Guid Id - { - get; - set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Name - { - get; - set; - } - - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String LocationUrl - { - get; - set; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/PagedList.cs b/src/Sdk/WebApi/WebApi/Contracts/PagedList.cs deleted file mode 100644 index 93e8097ad..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/PagedList.cs +++ /dev/null @@ -1,25 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace GitHub.Services.WebApi -{ - public interface IPagedList : IList - { - string ContinuationToken { get; } - } - - public class PagedList : List, IPagedList - { - public PagedList(IEnumerable list, String continuationToken) - : base(list) - { - this.ContinuationToken = continuationToken; - } - - public String ContinuationToken - { - get; - private set; - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Patch/Json/JsonPatchDocument.cs b/src/Sdk/WebApi/WebApi/Contracts/Patch/Json/JsonPatchDocument.cs deleted file mode 100644 index 02166afac..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Patch/Json/JsonPatchDocument.cs +++ /dev/null @@ -1,13 +0,0 @@ -using System.Collections.Generic; -using System.Runtime.Serialization; - -namespace GitHub.Services.WebApi.Patch.Json -{ - /// - /// The JSON model for JSON Patch Operations - /// - [ClientIncludeModel] - public class JsonPatchDocument : List - { - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Profile/ProfileQueryContext.cs b/src/Sdk/WebApi/WebApi/Contracts/Profile/ProfileQueryContext.cs index 69daf560f..7d29e478f 100644 --- a/src/Sdk/WebApi/WebApi/Contracts/Profile/ProfileQueryContext.cs +++ b/src/Sdk/WebApi/WebApi/Contracts/Profile/ProfileQueryContext.cs @@ -3,41 +3,6 @@ using System.Runtime.Serialization; namespace GitHub.Services.Profile { - public class ProfileQueryContext - { - public ProfileQueryContext(AttributesScope scope, string containerName = null) - : this(scope, CoreProfileAttributes.All, containerName) - { - } - - public ProfileQueryContext(AttributesScope scope, CoreProfileAttributes coreAttributes, string containerName = null) - { - ContainerScope = scope; - CoreAttributes = coreAttributes; - switch (scope) - { - case AttributesScope.Core: - ContainerName = null; - break; - case AttributesScope.Core | AttributesScope.Application: - ProfileArgumentValidation.ValidateApplicationContainerName(containerName); - ContainerName = containerName; - break; - default: - throw new ArgumentException(string.Format("The scope '{0}' is not supported for this operation.", scope)); - } - } - - [DataMember(IsRequired = true)] - public AttributesScope ContainerScope { get; private set; } - - [DataMember] - public string ContainerName { get; private set; } - - [DataMember] - public CoreProfileAttributes CoreAttributes { get; private set; } - } - [Flags] public enum CoreProfileAttributes { diff --git a/src/Sdk/WebApi/WebApi/Contracts/Users/UpdateUserParameters.cs b/src/Sdk/WebApi/WebApi/Contracts/Users/UpdateUserParameters.cs deleted file mode 100644 index e74dfdd8a..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Users/UpdateUserParameters.cs +++ /dev/null @@ -1,181 +0,0 @@ -using GitHub.Services.Common; -using GitHub.Services.WebApi; -using System; -using System.Runtime.Serialization; -using System.Linq; -using System.Globalization; - -namespace GitHub.Services.Users -{ - /// - /// Used for updating a user's data. - /// - [DataContract] - public class UpdateUserParameters - { - /// - /// Creates a new instance of an UpdateUserParameters object. - /// - public UpdateUserParameters() - { - this.Properties = new PropertiesCollection(); - } - - public UpdateUserParameters(UpdateUserParameters copy) - { - Descriptor = copy.Descriptor; - Properties = new PropertiesCollection(copy.Properties); - LastModified = copy.LastModified; - Revision = copy.Revision; - } - - /// - /// The user's unique identifier, and the primary means by which the user is referenced. - /// - [IgnoreDataMember] - public SubjectDescriptor Descriptor { get; set; } - - /// - /// The collection of properties to set. See "User" for valid fields. - /// - [DataMember(IsRequired = true, EmitDefaultValue = false)] - public PropertiesCollection Properties - { - get; private set; - } - - /// - /// The user's name, as displayed throughout the product. - /// - [IgnoreDataMember] - public String DisplayName - { - set { this.Properties[nameof(DisplayName)] = value; } - get { return this.Properties.GetValue(nameof(DisplayName), defaultValue: null); } - } - - /// - /// The user's preferred email address. - /// - [IgnoreDataMember] - public String Mail - { - set { this.Properties[nameof(Mail)] = value; } - get { return this.Properties.GetValue(nameof(Mail), defaultValue: null); } - } - - /// - /// The user's preferred email address which has not yet been confirmed. - /// - [IgnoreDataMember] - public String UnconfirmedMail - { - set { this.Properties[nameof(UnconfirmedMail)] = value; } - get { return this.Properties.GetValue(nameof(UnconfirmedMail), defaultValue: null); } - } - - /// - /// The user's country of residence or association. - /// - [IgnoreDataMember] - public String Country - { - set { this.Properties[nameof(Country)] = value; } - get { return this.Properties.GetValue(nameof(Country), defaultValue: null); } - } - - /// - /// The region in which the user resides or is associated. - /// - [IgnoreDataMember] - public String Region - { - set { this.Properties[nameof(Region)] = value; } - get { return this.Properties.GetValue(nameof(Region), defaultValue: null); } - } - - /// - /// A short blurb of "about me"-style text. - /// - [IgnoreDataMember] - public String Bio - { - set { this.Properties[nameof(Bio)] = value; } - get { return this.Properties.GetValue(nameof(Bio), defaultValue: null); } - } - - /// - /// A link to an external blog. - /// - [IgnoreDataMember] - public String Blog - { - set { this.Properties[nameof(Blog)] = value; } - get { return this.Properties.GetValue(nameof(Blog), defaultValue: null); } - } - - /// - /// The company at which the user is employed. - /// - [IgnoreDataMember] - public String Company - { - set { this.Properties[nameof(Company)] = value; } - get { return this.Properties.GetValue(nameof(Company), defaultValue: null); } - } - - /// - /// The date/time at which the user data was last modified. - /// - [IgnoreDataMember] - internal DateTimeOffset LastModified { get; set; } - - /// - /// The user data revision, for change tracking. - /// - [IgnoreDataMember] - internal Int32 Revision { get; set; } - - internal UpdateUserParameters Clone() - { - UpdateUserParameters clone = new UpdateUserParameters(); - - clone.Descriptor = this.Descriptor; - clone.Properties = new PropertiesCollection(this.Properties); - clone.Revision = this.Revision; - - return clone; - } - - internal virtual User ToUser() - { - User user = new User - { - Descriptor = this.Descriptor, - LastModified = this.LastModified, - Revision = this.Revision, - }; - - user.UpdateWith(this); - - return user; - } - - public override string ToString() - { - return String.Format( - CultureInfo.InvariantCulture, - @"UpdateUserParameters -[ -Descriptor: {0} -Revision: {1} -LastModified: {2} -{3} -]", - this.Descriptor, - this.Revision, - this.LastModified, - String.Join("\r\n", Properties.Select(kvp => $"{kvp.Key}:{kvp.Value}"))); - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Contracts/Users/User.cs b/src/Sdk/WebApi/WebApi/Contracts/Users/User.cs deleted file mode 100644 index 0c529d456..000000000 --- a/src/Sdk/WebApi/WebApi/Contracts/Users/User.cs +++ /dev/null @@ -1,187 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Users -{ - [DataContract] - public class User - { - public User() - { - } - - public User(User copy) - { - Descriptor = copy.Descriptor; - UserName = copy.UserName; - DisplayName = copy.DisplayName; - Mail = copy.Mail; - UnconfirmedMail = copy.UnconfirmedMail; - Bio = copy.Bio; - Blog = copy.Blog; - Company = copy.Company; - Country = copy.Country; - DateCreated = copy.DateCreated; - Links = copy.Links; - LastModified = copy.LastModified; - Revision = copy.Revision; - State = copy.State; - } - - /// - /// The user's unique identifier, and the primary means by which the user is referenced. - /// - [DataMember(IsRequired = true)] - public SubjectDescriptor Descriptor { get; set; } - - /// - /// The unique name of the user. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String UserName { get; set; } - - /// - /// The user's name, as displayed throughout the product. - /// - [DataMember(IsRequired = false)] - public String DisplayName { get; set; } - - /// - /// The user's preferred email address. - /// - [DataMember(IsRequired = false)] - public String Mail { get; set; } - - /// - /// The user's preferred email address which has not yet been confirmed. - /// Do not use this as an email destination, instead prefer the - /// confirmed email address - /// - [DataMember(IsRequired = false)] - public String UnconfirmedMail { get; set; } - - /// - /// A short blurb of "about me"-style text. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Bio { get; set; } - - /// - /// A link to an external blog. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Blog { get; set; } - - /// - /// The company at which the user is employed. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public String Company { get; set; } - - /// - /// The user's country of residence or association. - /// - [DataMember(IsRequired = false)] - public String Country { get; set; } - - /// - /// The date the user was created in the system - /// - [DataMember(IsRequired = false)] - public DateTimeOffset DateCreated { get; set; } - - /// - /// A set of readonly links for obtaining more info about the user. - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public ReferenceLinks Links { get; internal set; } - - /// - /// The date/time at which the user data was last modified. - /// - [DataMember(IsRequired = false)] - public DateTimeOffset LastModified { get; internal set; } - - /// - /// The attribute's revision, for change tracking. - /// - [DataMember(IsRequired = false)] - public Int32 Revision { get; internal set; } - - /// - /// The status of the user - /// - [DataMember(IsRequired = false, EmitDefaultValue = false)] - public UserState State { get; internal set; } - - /// - /// Enumeration for the user status - /// - [DataContract] - public enum UserState - { - Wellformed=0, - PendingProfileCreation, - Deleted, - } - - public static implicit operator UpdateUserParameters(User user) - { - return new UpdateUserParameters - { - Descriptor = user.Descriptor, - DisplayName = user.DisplayName, - Mail = user.Mail, - UnconfirmedMail = user.UnconfirmedMail, - Country = user.Country, - Bio = user.Bio, - Blog = user.Blog, - Company = user.Company, - LastModified = user.LastModified, - Revision = user.Revision, - }; - } - - internal virtual void UpdateWith(UpdateUserParameters userParameters) - { - ArgumentUtility.CheckForNull(userParameters, nameof(userParameters)); - - foreach (String propertyName in userParameters.Properties.Keys) - { - String value = userParameters.Properties[propertyName] as String; - switch (propertyName) - { - case (nameof(DisplayName)): - DisplayName = value; - break; - - case (nameof(Mail)): - Mail = value; - break; - - case (nameof(UnconfirmedMail)): - UnconfirmedMail = value; - break; - - case (nameof(Country)): - Country = value; - break; - - case (nameof(Bio)): - Bio = value; - break; - - case (nameof(Blog)): - Blog = value; - break; - - case (nameof(Company)): - Company = value; - break; - } - } - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Exceptions/CommonRestExceptions.cs b/src/Sdk/WebApi/WebApi/Exceptions/CommonRestExceptions.cs deleted file mode 100644 index 351e9be7f..000000000 --- a/src/Sdk/WebApi/WebApi/Exceptions/CommonRestExceptions.cs +++ /dev/null @@ -1,76 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.Common; - -namespace GitHub.Services.WebApi.Exceptions -{ - [Serializable] - [ExceptionMapping("0.0", "3.0", "MissingRequiredParameterException", "GitHub.Services.WebApi.Exceptions.MissingRequiredParameterException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class MissingRequiredParameterException : VssServiceException - { - public MissingRequiredParameterException() - { - } - - public MissingRequiredParameterException(string message) - : base(message) - { - } - - public MissingRequiredParameterException(string message, Exception innerException) - : base(message, innerException) - { - } - - public MissingRequiredParameterException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class MissingRequiredHeaderException : VssServiceException - { - public MissingRequiredHeaderException() - { - } - - public MissingRequiredHeaderException(string message) - : base(message) - { - } - - public MissingRequiredHeaderException(string message, Exception innerException) - : base(message, innerException) - { - } - - public MissingRequiredHeaderException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class MultipleHeaderValuesException : VssServiceException - { - public MultipleHeaderValuesException() - { - } - - public MultipleHeaderValuesException(string message) - : base(message) - { - } - - public MultipleHeaderValuesException(string message, Exception innerException) - : base(message, innerException) - { - } - - public MultipleHeaderValuesException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } -} diff --git a/src/Sdk/WebApi/WebApi/Exceptions/GraphExceptions.cs b/src/Sdk/WebApi/WebApi/Exceptions/GraphExceptions.cs deleted file mode 100644 index a606584aa..000000000 --- a/src/Sdk/WebApi/WebApi/Exceptions/GraphExceptions.cs +++ /dev/null @@ -1,469 +0,0 @@ -using System; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.Identity; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Graph -{ - [Serializable] - public class GraphException : VssServiceException - { - public GraphException() - { } - - public GraphException(string message) - : base(message) - { } - - public GraphException(string message, Exception innerException) - : base(message, innerException) - { } - - protected GraphException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } - - #region Common Exceptions - - [Serializable] - public class GraphBadRequestException : GraphException - { - protected GraphBadRequestException() - { - } - - public GraphBadRequestException(string message) - : base(message) - { - } - - public GraphBadRequestException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphBadRequestException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class InvalidGraphMemberIdException : GraphException - { - protected InvalidGraphMemberIdException() - { - } - - public InvalidGraphMemberIdException(string message) - : base(message) - { - } - - public InvalidGraphMemberIdException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected InvalidGraphMemberIdException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class GraphSubjectNotFoundException : GraphException - { - protected GraphSubjectNotFoundException() - { - } - - public GraphSubjectNotFoundException(string message) - : base(message) - { - } - - public GraphSubjectNotFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphSubjectNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public GraphSubjectNotFoundException(SubjectDescriptor subjectDescriptor) - : base(GraphResources.GraphSubjectNotFound(subjectDescriptor.ToString())) - { - } - - public GraphSubjectNotFoundException(Guid id) - : base(IdentityResources.IdentityNotFoundWithTfid(id)) - { - } - } - - [Serializable] - public class GraphMemberNotFoundException : GraphException - { - protected GraphMemberNotFoundException() - { - } - - public GraphMemberNotFoundException(string message) - : base(message) - { - } - - public GraphMemberNotFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphMemberNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public GraphMemberNotFoundException(SubjectDescriptor subjectDescriptor, SubjectDescriptor containerDescriptor) - : base(GraphResources.GraphMembershipNotFound(subjectDescriptor.ToString(), containerDescriptor.ToString())) - { - } - } - - [Serializable] - public class GraphMembershipNotFoundException : GraphException - { - protected GraphMembershipNotFoundException() - { - } - - public GraphMembershipNotFoundException(string message) - : base(message) - { - } - - public GraphMembershipNotFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphMembershipNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public GraphMembershipNotFoundException(SubjectDescriptor subjectDescriptor, SubjectDescriptor containerDescriptor) - : base(GraphResources.GraphMembershipNotFound(subjectDescriptor.ToString(), containerDescriptor.ToString())) - { - } - } - - [Serializable] - public class GraphApiUnavailableException : GraphException - { - protected GraphApiUnavailableException() - { - } - - public GraphApiUnavailableException(string message) - : base(message) - { - } - - public GraphApiUnavailableException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphApiUnavailableException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public GraphApiUnavailableException(SubjectDescriptor subjectDescriptor) - : base(IdentityResources.IdentityNotFoundWithDescriptor(subjectDescriptor.SubjectType, subjectDescriptor.Identifier)) - { - } - - public GraphApiUnavailableException(Guid id) - : base(IdentityResources.IdentityNotFoundWithTfid(id)) - { - } - } - - #endregion - - [Serializable] - public class GraphProviderInfoApiUnavailableException : GraphException - { - protected GraphProviderInfoApiUnavailableException() - { - } - - public GraphProviderInfoApiUnavailableException(string message) - : base(message) - { - } - - public GraphProviderInfoApiUnavailableException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected GraphProviderInfoApiUnavailableException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public GraphProviderInfoApiUnavailableException(SubjectDescriptor subjectDescriptor) - : base(IdentityResources.IdentityNotFoundWithDescriptor(subjectDescriptor.SubjectType, subjectDescriptor.Identifier)) - { - } - - public GraphProviderInfoApiUnavailableException(Guid id) - : base(IdentityResources.IdentityNotFoundWithTfid(id)) - { - } - } - - [Serializable] - public class SubjectDescriptorNotFoundException : GraphException - { - public SubjectDescriptorNotFoundException() - { } - - public SubjectDescriptorNotFoundException(string message) - : base(message) - { } - - public SubjectDescriptorNotFoundException(string message, Exception innerException) - : base(message, innerException) - { } - - protected SubjectDescriptorNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public SubjectDescriptorNotFoundException(Guid storageKey) - : base(GraphResources.SubjectDescriptorNotFoundWithStorageKey(storageKey)) - { - } - - public SubjectDescriptorNotFoundException(IdentityDescriptor identityDescriptor) - : base(GraphResources.SubjectDescriptorNotFoundWithIdentityDescriptor(identityDescriptor)) - { - } - } - - [Serializable] - public class StorageKeyNotFoundException : GraphException - { - public StorageKeyNotFoundException() - { } - - public StorageKeyNotFoundException(string message) - : base(message) - { } - - public StorageKeyNotFoundException(string message, Exception innerException) - : base(message, innerException) - { } - - protected StorageKeyNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public StorageKeyNotFoundException(SubjectDescriptor descriptor) - : base(GraphResources.StorageKeyNotFound(descriptor)) - { - } - } - - [Serializable] - public class InvalidGetDescriptorRequestException : GraphException - { - public InvalidGetDescriptorRequestException() - { } - - public InvalidGetDescriptorRequestException(string message) - : base(message) - { } - - public InvalidGetDescriptorRequestException(string message, Exception innerException) - : base(message, innerException) - { } - - protected InvalidGetDescriptorRequestException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public InvalidGetDescriptorRequestException(Guid id) - : base(IdentityResources.InvalidGetDescriptorRequestWithLocalId(id)) - { - } - } - - [Serializable] - public class TooManyRequestedItemsException : GraphException - { - /// - /// Gets the count of the requested items. - /// Note: the value can be null based on whether the message disclose the limit. - /// - [DataMember] - public int? RequestedCount { get; set; } - - /// - /// Gets max limit for the requested items. - /// Note: the value can be null based on whether the message disclose the limit. - /// - [DataMember] - public int? MaxLimit { get; set; } - - public TooManyRequestedItemsException() - : base(IdentityResources.TooManyRequestedItemsError()) - { } - - public TooManyRequestedItemsException(string message) - : base(message) - { } - - public TooManyRequestedItemsException(string message, Exception innerException) - : base(message, innerException) - { } - - protected TooManyRequestedItemsException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public TooManyRequestedItemsException(int providedCount, int maxCount) - : base(IdentityResources.TooManyRequestedItemsErrorWithCount(providedCount, maxCount)) - { - this.RequestedCount = providedCount; - this.MaxLimit = maxCount; - } - } - - [Serializable] - public class InvalidGraphRequestException : GraphException - { - public InvalidGraphRequestException() - { } - - public InvalidGraphRequestException(string message) - : base(message) - { } - - public InvalidGraphRequestException(string message, Exception innerException) - : base(message, innerException) - { } - - protected InvalidGraphRequestException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } - - [Serializable] - public class CannotEditChildrenOfNonGroupException : GraphException - { - public CannotEditChildrenOfNonGroupException() - { } - - public CannotEditChildrenOfNonGroupException(string message) - : base(message) - { } - - public CannotEditChildrenOfNonGroupException(string message, Exception innerException) - : base(message, innerException) - { } - - protected CannotEditChildrenOfNonGroupException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public CannotEditChildrenOfNonGroupException(SubjectDescriptor subjectDescriptor) - : base(GraphResources.CannotEditChildrenOfNonGroup(subjectDescriptor.ToString())) - { - } - } - - [Serializable] - public class InvalidSubjectTypeException : GraphException - { - public InvalidSubjectTypeException() - { } - - public InvalidSubjectTypeException(string message) - : base(message) - { } - - public InvalidSubjectTypeException(string message, Exception innerException) - : base(message, innerException) - { } - - protected InvalidSubjectTypeException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } - - [Serializable] - public class GraphAccountNameCollisionRepairUnsafeException : GraphException - { - public GraphAccountNameCollisionRepairUnsafeException() - { } - - public GraphAccountNameCollisionRepairUnsafeException(string message) - : base(message) - { } - - public GraphAccountNameCollisionRepairUnsafeException(string message, Exception innerException) - : base(message, innerException) - { } - - protected GraphAccountNameCollisionRepairUnsafeException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } - - [Serializable] - public class GraphAccountNameCollisionRepairFailedException : GraphException - { - public GraphAccountNameCollisionRepairFailedException() - { } - - public GraphAccountNameCollisionRepairFailedException(string message) - : base(message) - { } - - public GraphAccountNameCollisionRepairFailedException(string message, Exception innerException) - : base(message, innerException) - { } - - protected GraphAccountNameCollisionRepairFailedException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } - - [Serializable] - public class CannotUpdateWellKnownGraphGroupException : GraphException - { - public CannotUpdateWellKnownGraphGroupException() - { } - - public CannotUpdateWellKnownGraphGroupException(string message) - : base(message) - { } - - public CannotUpdateWellKnownGraphGroupException(string message, Exception innerException) - : base(message, innerException) - { } - - protected CannotUpdateWellKnownGraphGroupException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Exceptions/IdentityExceptions.cs b/src/Sdk/WebApi/WebApi/Exceptions/IdentityExceptions.cs deleted file mode 100644 index 12db542e7..000000000 --- a/src/Sdk/WebApi/WebApi/Exceptions/IdentityExceptions.cs +++ /dev/null @@ -1,1533 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Diagnostics; -using System.Diagnostics.CodeAnalysis; -using System.Globalization; -using System.Runtime.Serialization; -using System.Text; -using GitHub.Services.Common; -using GitHub.Services.WebApi; - -namespace GitHub.Services.Identity -{ - [Serializable] - [ExceptionMapping("0.0", "3.0", "IdentityServiceException", "GitHub.Services.Identity.IdentityServiceException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityServiceException : VssServiceException - { - public IdentityServiceException() - { - EventId = VssEventId.VssIdentityServiceException; - } - - public IdentityServiceException(string message) - : base(message) - { - EventId = VssEventId.VssIdentityServiceException; - } - - public IdentityServiceException(string message, Exception innerException) - : base(message, innerException) - { - EventId = VssEventId.VssIdentityServiceException; - } - - protected IdentityServiceException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - EventId = VssEventId.VssIdentityServiceException; - } - } - /// - /// The group you are creating already exists, thrown by the data tier - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "GroupCreationException", "GitHub.Services.Identity.GroupCreationException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class GroupCreationException : IdentityServiceException - { - public GroupCreationException(string displayName, string projectName) - : base(IdentityResources.GROUPCREATIONERROR(displayName, projectName)) - { - } - - public GroupCreationException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// IMS domain is incorrect for operation - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityDomainMismatchException", "GitHub.Services.Identity.IdentityDomainMismatchException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityDomainMismatchException : IdentityServiceException - { - public IdentityDomainMismatchException(string incorrectHost, string correctHost) - : base(IdentityResources.IDENTITYDOMAINMISMATCHERROR(incorrectHost, correctHost)) - { - } - - public IdentityDomainMismatchException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected IdentityDomainMismatchException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// You are trying to add a group that is a parent group of the current group, throw - /// by the data tier - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "AddMemberCyclicMembershipException", "GitHub.Services.Identity.AddMemberCyclicMembershipException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddMemberCyclicMembershipException : IdentityServiceException - { - public AddMemberCyclicMembershipException() - { - } - - public AddMemberCyclicMembershipException(string groupName, string memberName) - : base(IdentityResources.ADDMEMBERCYCLICMEMBERSHIPERROR(groupName, memberName)) - { - } - - public AddMemberCyclicMembershipException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected AddMemberCyclicMembershipException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// You are trying to create a group scope that already exists - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "GroupScopeCreationException", "GitHub.Services.Identity.GroupScopeCreationException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class GroupScopeCreationException : IdentityServiceException - { - public GroupScopeCreationException() - { - } - - public GroupScopeCreationException(String message, Exception innerException) - : base(message, innerException) - { - } - - public GroupScopeCreationException(string scopeId) - : base(IdentityResources.GROUPSCOPECREATIONERROR(scopeId)) - { - } - - protected GroupScopeCreationException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Group cannot be created in the requested scope since the requested scope is not within the root scope. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - public class IncompatibleScopeException : IdentityServiceException - { - public IncompatibleScopeException() - { - } - - public IncompatibleScopeException(String message): base(message) - { - } - public IncompatibleScopeException(String message, Exception innerException) - : base(message, innerException) - { - } - - public IncompatibleScopeException(string rootScopeId, string scopeIdToCheck) - : base(IdentityResources.IncompatibleScopeError(rootScopeId, scopeIdToCheck)) - { - } - - protected IncompatibleScopeException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Trying to add a member to a group that is already a member of the group, thrown by the data tier. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "AddMemberIdentityAlreadyMemberException", "GitHub.Services.Identity.AddMemberIdentityAlreadyMemberException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddMemberIdentityAlreadyMemberException : IdentityServiceException - { - public AddMemberIdentityAlreadyMemberException(string groupName, string memberName) - : base(IdentityResources.ADDMEMBERIDENTITYALREADYMEMBERERROR(groupName, memberName)) - { - } - - public AddMemberIdentityAlreadyMemberException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected AddMemberIdentityAlreadyMemberException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveAccountOwnerFromAdminGroupException", "GitHub.Services.Identity.RemoveAccountOwnerFromAdminGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveAccountOwnerFromAdminGroupException : IdentityServiceException - { - public RemoveAccountOwnerFromAdminGroupException() - : base(IdentityResources.AccountOwnerCannotBeRemovedFromGroup(IdentityResources.ProjectCollectionAdministrators())) { } - - public RemoveAccountOwnerFromAdminGroupException(string message) : base(message){ } - - public RemoveAccountOwnerFromAdminGroupException(string message, Exception innerException) : base(message, innerException) { } - } - - /// - /// You can't remove yourself from the global namespace admins group and lock yourself out of your collection/hosting account. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveSelfFromAdminGroupException", "GitHub.Services.Identity.RemoveSelfFromAdminGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveSelfFromAdminGroupException : IdentityServiceException - { - public RemoveSelfFromAdminGroupException() - : base(IdentityResources.RemoveSelfFromAdminGroupError(BlockRemovingSelfFromAdminGroup)) - { - } - - public RemoveSelfFromAdminGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - - private const String BlockRemovingSelfFromAdminGroup = @"/Service/Integration/Settings/BlockRemovingSelfFromAdminGroup"; - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveOrganizationAdminFromAdminGroupException", "GitHub.Services.Identity.RemoveOrganizationAdminFromAdminGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - class RemoveOrganizationAdminFromAdminGroupException : IdentityServiceException - { - public RemoveOrganizationAdminFromAdminGroupException(string message) : base(message) { } - - public RemoveOrganizationAdminFromAdminGroupException(String message, Exception innerException) : base(message, innerException) { } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveServiceAccountsFromAdminGroupException", "GitHub.Services.Identity.RemoveServiceAccountsFromAdminGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - class RemoveServiceAccountsFromAdminGroupException : IdentityServiceException - { - public RemoveServiceAccountsFromAdminGroupException(string message) : base(message) { } - public RemoveServiceAccountsFromAdminGroupException(String message, Exception innerException) : base(message, innerException) { } - } - - /// - /// Group member you are trying to delete was not a member of the group. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveGroupMemberNotMemberException", "GitHub.Services.Identity.RemoveGroupMemberNotMemberException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveGroupMemberNotMemberException : IdentityServiceException - { - public RemoveGroupMemberNotMemberException(string sid) - : base(IdentityResources.REMOVEGROUPMEMBERNOTMEMBERERROR(sid)) - { - } - - public RemoveGroupMemberNotMemberException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// Thrown when an AddMemberToGroup call is made to put an identity X into group Y, but the action - /// is not legal for some reason related to identity X - /// - [Serializable] - [ExceptionMapping("0.0", "3.0", "AddGroupMemberIllegalMemberException", "GitHub.Services.Identity.AddGroupMemberIllegalMemberException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddGroupMemberIllegalMemberException : IdentityServiceException - { - public AddGroupMemberIllegalMemberException() - { - } - - public AddGroupMemberIllegalMemberException(String message) - : base(message) - { - } - - public AddGroupMemberIllegalMemberException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected AddGroupMemberIllegalMemberException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Cannot add windows identity to hosted deployment - /// - [Serializable] - [ExceptionMapping("0.0", "3.0", "AddGroupMemberIllegalWindowsIdentityException", "GitHub.Services.Identity.AddGroupMemberIllegalWindowsIdentityException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddGroupMemberIllegalWindowsIdentityException : IdentityServiceException - { - public AddGroupMemberIllegalWindowsIdentityException(Identity member) - : base(IdentityResources.ADDGROUPMEMBERILLEGALWINDOWSIDENTITY(member.DisplayName)) - { - } - - public AddGroupMemberIllegalWindowsIdentityException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// Cannot add internet identity to on premise deployment - /// - [Serializable] - [ExceptionMapping("0.0", "3.0", "AddGroupMemberIllegalInternetIdentityException", "GitHub.Services.Identity.AddGroupMemberIllegalInternetIdentityException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddGroupMemberIllegalInternetIdentityException : IdentityServiceException - { - public AddGroupMemberIllegalInternetIdentityException(Identity member) - : base(IdentityResources.ADDGROUPMEMBERILLEGALINTERNETIDENTITY(member.DisplayName)) - { - } - - public AddGroupMemberIllegalInternetIdentityException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// Trying to remove a group that doesn't exist, thrown by the data tier - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveNonexistentGroupException", "GitHub.Services.Identity.RemoveNonexistentGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveNonexistentGroupException : IdentityServiceException - { - public RemoveNonexistentGroupException(string sid) - : base(IdentityResources.REMOVENONEXISTENTGROUPERROR(sid)) - { - } - - public RemoveNonexistentGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// You can't remove any of the special groups: the global administrators group, the - /// service users group, the team foundation valid users group, or a project administration - /// group. Thrown by the data tier. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveSpecialGroupException", "GitHub.Services.Identity.RemoveSpecialGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveSpecialGroupException : IdentityServiceException - { - public RemoveSpecialGroupException(string sid, SpecialGroupType specialType) - : base(BuildMessage(sid, specialType)) - { - } - - public RemoveSpecialGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected static string BuildMessage(string sid, SpecialGroupType specialType) - { - switch (specialType) - { - case SpecialGroupType.AdministrativeApplicationGroup: - return IdentityResources.REMOVEADMINGROUPERROR(); - - case SpecialGroupType.EveryoneApplicationGroup: - return IdentityResources.REMOVEEVERYONEGROUPERROR(); - - case SpecialGroupType.ServiceApplicationGroup: - return IdentityResources.REMOVESERVICEGROUPERROR(); - - default: - return IdentityResources.REMOVESPECIALGROUPERROR(); - } - } - } - - /// - /// Group you were looking up does not exist, thrown by the data tier - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "FindGroupSidDoesNotExistException", "GitHub.Services.Identity.FindGroupSidDoesNotExistException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class FindGroupSidDoesNotExistException : IdentityServiceException - { - public FindGroupSidDoesNotExistException(string sid) - : base(IdentityResources.FINDGROUPSIDDOESNOTEXISTERROR(sid)) - { - } - - public FindGroupSidDoesNotExistException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected FindGroupSidDoesNotExistException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Group rename error, new name already in use - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "GroupRenameException", "GitHub.Services.Identity.GroupRenameException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class GroupRenameException : IdentityServiceException - { - public GroupRenameException(string displayName) - : base(IdentityResources.GROUPRENAMEERROR(displayName)) - { - } - - public GroupRenameException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// You cannot add a project group to a project group in a different project - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "AddProjectGroupProjectMismatchException", "GitHub.Services.Identity.AddProjectGroupProjectMismatchException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddProjectGroupProjectMismatchException : IdentityServiceException - { - public AddProjectGroupProjectMismatchException() - { - } - - public AddProjectGroupProjectMismatchException(string groupName, string memberName) - : base(IdentityResources.ADDPROJECTGROUPTPROJECTMISMATCHERROR(groupName, memberName)) - { - } - - public AddProjectGroupProjectMismatchException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected AddProjectGroupProjectMismatchException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "AddProjectGroupToGlobalGroupException", "GitHub.Services.Identity.AddProjectGroupToGlobalGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AddProjectGroupToGlobalGroupException : IdentityServiceException - { - public AddProjectGroupToGlobalGroupException() - { - } - - public AddProjectGroupToGlobalGroupException(string globalGroupName, string projectGroupName) - : base(IdentityResources.ADDPROJECTGROUPTOGLOBALGROUPERROR(projectGroupName, globalGroupName)) - { - } - - public AddProjectGroupToGlobalGroupException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected AddProjectGroupToGlobalGroupException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Unable to locate project for the project uri passed in - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "GroupScopeDoesNotExistException", "GitHub.Services.Identity.GroupScopeDoesNotExistException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class GroupScopeDoesNotExistException : IdentityServiceException - { - [SuppressMessage("Microsoft.Design", "CA1054:UriParametersShouldNotBeStrings", MessageId = "0#")] - public GroupScopeDoesNotExistException(string projectUri) - : base(IdentityResources.GROUPSCOPEDOESNOTEXISTERROR(projectUri)) - { - } - - public GroupScopeDoesNotExistException(Guid scopeId) - : base(IdentityResources.GROUPSCOPEDOESNOTEXISTERROR(scopeId)) - { - } - - public GroupScopeDoesNotExistException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected GroupScopeDoesNotExistException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// This exception is thrown when a user tries to add a group that is - /// not an application group. We do not modify the memberships of Windows groups. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "NotApplicationGroupException", "GitHub.Services.Identity.NotApplicationGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class NotApplicationGroupException : IdentityServiceException - { - public NotApplicationGroupException() - : base(IdentityResources.NOT_APPLICATION_GROUP()) - { - } - - public NotApplicationGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// You must specify a group when removing members from a group, thrown by the app tier - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "ModifyEveryoneGroupException", "GitHub.Services.Identity.ModifyEveryoneGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class ModifyEveryoneGroupException : IdentityServiceException - { - public ModifyEveryoneGroupException() - : base(IdentityResources.MODIFYEVERYONEGROUPEXCEPTION()) - { - } - - public ModifyEveryoneGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// ReadIdentityFromSource returned null and we need an identity to continue the operation - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityNotFoundException", "GitHub.Services.Identity.IdentityNotFoundException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityNotFoundException : IdentityServiceException - { - public IdentityNotFoundException() - : base(IdentityResources.IdentityNotFoundSimpleMessage()) - { - } - - public IdentityNotFoundException(String message) - : base(message) - { - } - - public IdentityNotFoundException(String message, Exception innerException) - : base(message, innerException) - { - } - - public IdentityNotFoundException(IdentityDescriptor descriptor) - : base(IdentityResources.IdentityNotFoundMessage(descriptor.IdentityType)) - { - } - - public IdentityNotFoundException(SubjectDescriptor subjectDescriptor) - : base(IdentityResources.IdentityNotFoundMessage(subjectDescriptor.SubjectType)) - { - } - - public IdentityNotFoundException(Guid tfid) - : base(IdentityResources.IdentityNotFoundWithTfid(tfid)) - { - } - } - - /// - /// Identity is not part of calling identity's directory - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - public class IdentityNotFoundInCurrentDirectoryException : IdentityServiceException - { - public IdentityNotFoundInCurrentDirectoryException() - : base(IdentityResources.IdentityNotFoundInCurrentDirectory()) - { - } - - public IdentityNotFoundInCurrentDirectoryException(String message) - : base(message) - { - } - - public IdentityNotFoundInCurrentDirectoryException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// The identity is not a service identity - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityNotServiceIdentityException", "GitHub.Services.Identity.IdentityNotServiceIdentityException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityNotServiceIdentityException : IdentityServiceException - { - public IdentityNotServiceIdentityException(String message) - : base(message) - { - } - - public IdentityNotServiceIdentityException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidServiceIdentityNameException", "GitHub.Services.Identity.InvalidServiceIdentityNameException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidServiceIdentityNameException : IdentityServiceException - { - public InvalidServiceIdentityNameException(String identityName) - : base(IdentityResources.InvalidServiceIdentityName(identityName)) - { - } - - public InvalidServiceIdentityNameException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// The identity already exists - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityAlreadyExistsException", "GitHub.Services.Identity.IdentityAlreadyExistsException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityAlreadyExistsException : IdentityServiceException - { - public IdentityAlreadyExistsException(String message) - : base(message) - { - } - - public IdentityAlreadyExistsException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - /// - /// This exception is thrown when a user tries to add a distribution list - /// to a group. We only allow security groups to used. - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "NotASecurityGroupException", "GitHub.Services.Identity.NotASecurityGroupException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class NotASecurityGroupException : IdentityServiceException - { - public NotASecurityGroupException(String displayName) - : base(IdentityResources.NOT_A_SECURITY_GROUP(displayName)) - { - } - - public NotASecurityGroupException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RemoveMemberServiceAccountException", "GitHub.Services.Identity.RemoveMemberServiceAccountException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RemoveMemberServiceAccountException : IdentityServiceException - { - public RemoveMemberServiceAccountException() - : base(IdentityResources.CANNOT_REMOVE_SERVICE_ACCOUNT()) - { - } - - public RemoveMemberServiceAccountException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IllegalAliasException", "GitHub.Services.Identity.IllegalAliasException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IllegalAliasException : IdentityServiceException - { - public IllegalAliasException(string name) : - base(name) - { - } - - public IllegalAliasException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IllegalIdentityException", "GitHub.Services.Identity.IllegalIdentityException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IllegalIdentityException : IdentityServiceException - { - public IllegalIdentityException(string name) : - base(IdentityResources.IllegalIdentityException(name)) - { - } - - public IllegalIdentityException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentitySyncException", "GitHub.Services.Identity.IdentitySyncException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentitySyncException : IdentityServiceException - { - public IdentitySyncException(string message, Exception innerException) : - base(IdentityResources.IDENTITY_SYNC_ERROR(message)) - { - } - } - - /// - /// Identity provider not available - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityProviderUnavailableException", "GitHub.Services.Identity.IdentityProviderUnavailableException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityProviderUnavailableException : IdentityServiceException - { - public IdentityProviderUnavailableException(IdentityDescriptor descriptor) - : base(IdentityResources.IdentityProviderUnavailable(descriptor.IdentityType, descriptor.Identifier)) - { - } - - public IdentityProviderUnavailableException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityPropertyRequiredException", "GitHub.Services.Identity.IdentityPropertyRequiredException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityPropertyRequiredException : IdentityServiceException - { - public IdentityPropertyRequiredException(String message) - : base(message) - { - } - - public IdentityPropertyRequiredException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityAccountNameAlreadyInUseException", "GitHub.Services.Identity.IdentityAccountNameAlreadyInUseException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityAccountNameAlreadyInUseException : IdentityServiceException - { - public IdentityAccountNameAlreadyInUseException(String oneAccountName, Int32 collisionCount) - : base(BuildExceptionMessage(oneAccountName, collisionCount)) - { - } - - public IdentityAccountNameAlreadyInUseException(String message, Exception innerException) - : base(message, innerException) - { - } - - private static String BuildExceptionMessage(String oneAccountName, Int32 collisionCount) - { - Debug.Assert(collisionCount > 0, "identity account name exception fired, but no collisions were found"); - - if (collisionCount == 1) - { - return IdentityResources.IdentityAccountNameAlreadyInUseError(oneAccountName); - } - else - { - return IdentityResources.IdentityAccountNamesAlreadyInUseError(collisionCount, oneAccountName); - } - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityAccountNameCollisionRepairFailedException", "GitHub.Services.Identity.IdentityAccountNameCollisionRepairFailedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityAccountNameCollisionRepairFailedException : IdentityServiceException - { - public IdentityAccountNameCollisionRepairFailedException(String accountName) - : base(IdentityResources.IdentityAccountNameCollisionRepairFailedError(accountName)) - { - } - - public IdentityAccountNameCollisionRepairFailedException(String accountName, Exception innerException) - : base(IdentityResources.IdentityAccountNameCollisionRepairFailedError(accountName), innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityAccountNameCollisionRepairUnsafeException", "GitHub.Services.Identity.IdentityAccountNameCollisionRepairUnsafeException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityAccountNameCollisionRepairUnsafeException : IdentityServiceException - { - public IdentityAccountNameCollisionRepairUnsafeException(String accountName) - : base(IdentityResources.IdentityAccountNameCollisionRepairUnsafeError(accountName)) - { - } - - public IdentityAccountNameCollisionRepairUnsafeException(String accountName, Exception innerException) - : base(IdentityResources.IdentityAccountNameCollisionRepairUnsafeError(accountName), innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityAliasAlreadyInUseException", "GitHub.Services.Identity.IdentityAliasAlreadyInUseException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityAliasAlreadyInUseException : IdentityServiceException - { - public IdentityAliasAlreadyInUseException(String conflictingAlias) - : base(IdentityResources.IdentityAliasAlreadyInUseError(conflictingAlias)) - { - } - - public IdentityAliasAlreadyInUseException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "DynamicIdentityTypeCreationNotSupportedException", "GitHub.Services.Identity.DynamicIdentityTypeCreationNotSupportedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class DynamicIdentityTypeCreationNotSupportedException : IdentityServiceException - { - public DynamicIdentityTypeCreationNotSupportedException() - : base(IdentityResources.DynamicIdentityTypeCreationNotSupported()) - { - } - - public DynamicIdentityTypeCreationNotSupportedException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "TooManyIdentitiesReturnedException", "GitHub.Services.Identity.TooManyIdentitiesReturnedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class TooManyIdentitiesReturnedException : IdentityServiceException - { - public TooManyIdentitiesReturnedException() - : base(IdentityResources.TooManyResultsError()) - { - } - - public TooManyIdentitiesReturnedException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "MultipleIdentitiesFoundException", "GitHub.Services.Identity.MultipleIdentitiesFoundException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class MultipleIdentitiesFoundException : IdentityServiceException - { - public MultipleIdentitiesFoundException(string identityName, IEnumerable matchingIdentities) - : base(BuildExceptionMessage(identityName, matchingIdentities)) - { - - } - - public MultipleIdentitiesFoundException(string identityName, IEnumerable matchingIdentities) - : base(BuildExceptionMessage(identityName, matchingIdentities)) - { - - } - - public MultipleIdentitiesFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - - private static string BuildExceptionMessage(string identityName, IEnumerable matchingIdentities) - { - StringBuilder builder = new StringBuilder(); - - foreach (var identity in matchingIdentities) - { - builder.AppendFormat(CultureInfo.CurrentUICulture, "- {0} ({1})", identity.ProviderDisplayName, identity.CustomDisplayName); - } - - return IdentityResources.MultipleIdentitiesFoundError(identityName, builder.ToString()); - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "HistoricalIdentityNotFoundException", "GitHub.Services.Identity.HistoricalIdentityNotFoundException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class HistoricalIdentityNotFoundException : IdentityServiceException - { - public HistoricalIdentityNotFoundException() - : base(IdentityResources.TooManyResultsError()) - { - } - - public HistoricalIdentityNotFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidIdentityIdTranslationException", "GitHub.Services.Identity.InvalidIdentityIdTranslationException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidIdentityIdTranslationException : IdentityServiceException - { - public InvalidIdentityIdTranslationException() - : base(IdentityResources.InvalidIdentityIdTranslations()) - { - } - - public InvalidIdentityIdTranslationException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdTranslationsAreMigratedException", "GitHub.Services.Identity.IdTranslationsAreMigratedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdTranslationsAreMigratedException : IdentityServiceException - { - public IdTranslationsAreMigratedException() - : base(IdentityResources.IdentityIdTranslationsAreMigrated()) - { - } - - public IdTranslationsAreMigratedException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidIdentityStorageKeyTranslationException", "GitHub.Services.Identity.InvalidIdentityStorageKeyTranslationException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidIdentityStorageKeyTranslationException : IdentityServiceException - { - public InvalidIdentityStorageKeyTranslationException() - : base(IdentityResources.InvalidIdentityKeyMaps()) - { - } - - public InvalidIdentityStorageKeyTranslationException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidIdentityKeyMapsException", "GitHub.Services.Identity.InvalidIdentityKeyMapsException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidIdentityKeyMapException : IdentityServiceException - { - public InvalidIdentityKeyMapException() - : base(IdentityResources.InvalidIdentityKeyMaps()) - { - } - - public InvalidIdentityKeyMapException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidTypeIdForIdentityStorageKeyException", "GitHub.Services.Identity.InvalidTypeIdForIdentityStorageKeyException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidTypeIdForIdentityKeyMapException : IdentityServiceException - { - public InvalidTypeIdForIdentityKeyMapException() - : base(IdentityResources.InvalidIdentityKeyMaps()) - { - } - - public InvalidTypeIdForIdentityKeyMapException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "DuplicateIdentitiesFoundException", "GitHub.Services.Identity.DuplicateIdentitiesFoundException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class DuplicateIdentitiesFoundException : IdentityServiceException - { - public DuplicateIdentitiesFoundException() - : base(IdentityResources.InvalidIdentityIdTranslations()) - { - } - - public DuplicateIdentitiesFoundException(String message) - : base(message) - { - } - - public DuplicateIdentitiesFoundException(string message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityExpressionException", "GitHub.Services.Identity.IdentityExpressionException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityExpressionException : IdentityServiceException - { - public IdentityExpressionException(String message) - : base(message) - { - } - - public IdentityExpressionException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidDisplayNameException", "GitHub.Services.Identity.InvalidDisplayNameException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidDisplayNameException : IdentityServiceException - { - public InvalidDisplayNameException(String message) - : base(message) - { - } - - public InvalidDisplayNameException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [ExceptionMapping("0.0", "3.0", "GroupNameNotRecognizedException", "GitHub.Services.Identity.GroupNameNotRecognizedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class GroupNameNotRecognizedException : IdentityServiceException - { - public GroupNameNotRecognizedException() - { - } - - public GroupNameNotRecognizedException(string message, Exception innerException) - : base(message, innerException) - { - } - - public GroupNameNotRecognizedException(string groupName) - : this(IdentityResources.InvalidNameNotRecognized(groupName), null) - { - } - - protected GroupNameNotRecognizedException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "AccountPreferencesAlreadyExistException", "GitHub.Services.Identity.AccountPreferencesAlreadyExistException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class AccountPreferencesAlreadyExistException : IdentityServiceException - { - public AccountPreferencesAlreadyExistException() - : base(IdentityResources.AccountPreferencesAlreadyExist()) - { - } - - public AccountPreferencesAlreadyExistException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [ExceptionMapping("0.0", "3.0", "IdentityMapReadOnlyException", "GitHub.Services.Identity.IdentityMapReadOnlyException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityMapReadOnlyException : IdentityServiceException - { - public IdentityMapReadOnlyException() - : this((Exception)null) - { - } - - public IdentityMapReadOnlyException(Exception innerException) - : base(IdentityResources.IdentityMapReadOnlyException(), innerException) - { - } - - public IdentityMapReadOnlyException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected IdentityMapReadOnlyException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - [ExceptionMapping("0.0", "3.0", "IdentityStoreNotAvailableException", "GitHub.Services.Identity.IdentityStoreNotAvailableException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityStoreNotAvailableException : IdentityServiceException - { - public IdentityStoreNotAvailableException() : base() { } - public IdentityStoreNotAvailableException(string errorMessage) : base(errorMessage) { } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidDisplayNameException", "GitHub.Services.Identity.InvalidChangedIdentityException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidChangedIdentityException : IdentityServiceException - { - public InvalidChangedIdentityException(String message) - : base(message) - { - } - - public InvalidChangedIdentityException(String message, Exception innerException) - : base(message, innerException) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdenittyInvalidTypeIdException", "GitHub.Services.Identity.IdenittyInvalidTypeIdException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - [Obsolete("This exception has been renamed to IdentityInvalidTypeIdException")] - public class IdenittyInvalidTypeIdException : IdentityServiceException - { - public IdenittyInvalidTypeIdException(string message) : - base(message) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "IdentityInvalidTypeIdException", "GitHub.Services.Identity.IdentityInvalidTypeIdException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] -#pragma warning disable 618 - public class IdentityInvalidTypeIdException : IdenittyInvalidTypeIdException -#pragma warning restore 618 - { - public IdentityInvalidTypeIdException(string message) : - base(message) - { - } - } - - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "InvalidIdentityKeyException", "GitHub.Services.Identity.InvalidIdentityKeyException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class InvalidIdentityKeyException : IdentityServiceException - { - public InvalidIdentityKeyException() : base() { } - - public InvalidIdentityKeyException(string message) : - base(message) - { - } - } - - [Serializable] - [ExceptionMapping("0.0", "3.0", "IdentityMaterializationFailedException", "GitHub.Services.Identity.IdentityMaterializationFailedException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class IdentityMaterializationFailedException : IdentityServiceException - { - public IdentityMaterializationFailedException() - { - } - - public IdentityMaterializationFailedException(string message, Exception innerException) - : base(message, innerException) - { - } - - public IdentityMaterializationFailedException(string principalName) - : this(IdentityResources.IdentityMaterializationFailedMessage(principalName), null) - { - } - - protected IdentityMaterializationFailedException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class IdentityDescriptorNotFoundException : IdentityServiceException - { - public IdentityDescriptorNotFoundException() - { } - - public IdentityDescriptorNotFoundException(string message) - : base(message) - { } - - public IdentityDescriptorNotFoundException(string message, Exception innerException) - : base(message, innerException) - { } - - protected IdentityDescriptorNotFoundException(SerializationInfo info, StreamingContext context) - : base(info, context) - { } - - public IdentityDescriptorNotFoundException(Guid id, bool isMasterId) - : base(isMasterId ? - IdentityResources.IdentityDescriptorNotFoundWithMasterId(id) : - IdentityResources.IdentityDescriptorNotFoundWithLocalId(id)) - { - } - } - - [Serializable] - public abstract class TenantSwitchException : IdentityServiceException - { - public TenantSwitchException() - { - } - - public TenantSwitchException(string message) : base(message) - { - } - - public TenantSwitchException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected TenantSwitchException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class InvitationPendingException : TenantSwitchException - { - public string AccountName { get; } - public string OrganizationName { get; } - - public InvitationPendingException() - { - } - - public InvitationPendingException(string message) - : base(message) - { - } - - public InvitationPendingException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected InvitationPendingException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public InvitationPendingException(string accountName, string organizationName) - : base(IdentityResources.InvitationPendingMessage(accountName, organizationName)) - { - AccountName = accountName; - OrganizationName = organizationName; - } - } - - [Serializable] - public class WrongWorkOrPersonalException : TenantSwitchException - { - public string AccountName { get; } - public bool ShouldBePersonal { get; } - public bool ShouldCreatePersonal { get; } - - public WrongWorkOrPersonalException() - { - } - - public WrongWorkOrPersonalException(string message) - : base(message) - { - } - - public WrongWorkOrPersonalException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected WrongWorkOrPersonalException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - - public WrongWorkOrPersonalException(string accountName, bool shouldBePersonal, bool shouldCreatePersonal) - : base(GetMessage(shouldBePersonal, shouldCreatePersonal)) - { - AccountName = accountName; - ShouldBePersonal = shouldBePersonal; - ShouldCreatePersonal = shouldCreatePersonal; - } - - private static string GetMessage(bool shouldBePersonal, bool shouldCreatePersonal) - { - if (shouldBePersonal) - { - if (shouldCreatePersonal) - { - return IdentityResources.ShouldCreatePersonalAccountMessage(); - } - else - { - return IdentityResources.ShouldBePersonalAccountMessage(); - } - } - else - { - return IdentityResources.ShouldBeWorkAccountMessage(); - } - } - } - - [Serializable] - public class InvalidTransferIdentityRightsRequestException : IdentityServiceException - { - public InvalidTransferIdentityRightsRequestException() - { - } - - public InvalidTransferIdentityRightsRequestException(string message) - : base(message) - { - } - - public InvalidTransferIdentityRightsRequestException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected InvalidTransferIdentityRightsRequestException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class FailedTransferIdentityRightsException : IdentityServiceException - { - public FailedTransferIdentityRightsException() - { - } - - public FailedTransferIdentityRightsException(string message) - : base(message) - { - } - - public FailedTransferIdentityRightsException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected FailedTransferIdentityRightsException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class CollectionShardingException : IdentityServiceException - { - public CollectionShardingException() - { - } - - public CollectionShardingException(string message) - : base(message) - { - } - - public CollectionShardingException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected CollectionShardingException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - [Serializable] - public class ScopeBadRequestException: IdentityServiceException - { - protected ScopeBadRequestException() - { - } - - public ScopeBadRequestException(string message) - : base(message) - { - } - - public ScopeBadRequestException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected ScopeBadRequestException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Indicates that a caller action triggered an attempt to read or update identity information at the deployment level - /// directly from (or using data from) a sharded host after dual writes had been disabled, meaning that the fallback is not allowed. - /// - [Serializable] - public class FallbackIdentityOperationNotAllowedException : IdentityServiceException - { - public FallbackIdentityOperationNotAllowedException() - { - } - - public FallbackIdentityOperationNotAllowedException(string message) - : base(message) - { - } - - public FallbackIdentityOperationNotAllowedException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected FallbackIdentityOperationNotAllowedException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Thrown when we were trying to create a client to talk to the legacy SPS identity store (e.g. SPS SU1), - /// but were not able to do so due to an unexpected response. - /// - [Serializable] - public class CannotFindLegacySpsIdentityStoreException : IdentityServiceException - { - public CannotFindLegacySpsIdentityStoreException() - { - } - - public CannotFindLegacySpsIdentityStoreException(string message) - : base(message) - { - } - - public CannotFindLegacySpsIdentityStoreException(string message, Exception innerException) - : base(message, innerException) - { - } - - protected CannotFindLegacySpsIdentityStoreException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } - - /// - /// Unable to restore group scope - /// - [Serializable] - [SuppressMessage("Microsoft.Design", "CA1032:ImplementStandardExceptionConstructors")] - [ExceptionMapping("0.0", "3.0", "RestoreGroupScopeValidationException", "GitHub.Services.Identity.RestoreGroupScopeValidationException, GitHub.Services.WebApi, Version=14.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a")] - public class RestoreGroupScopeValidationException : IdentityServiceException - { - [SuppressMessage("Microsoft.Design", "CA1054:UriParametersShouldNotBeStrings", MessageId = "0#")] - public RestoreGroupScopeValidationException(string validationError) - : base(IdentityResources.RestoreGroupScopeValidationError(validationError)) - { - } - - public RestoreGroupScopeValidationException(String message, Exception innerException) - : base(message, innerException) - { - } - - protected RestoreGroupScopeValidationException(SerializationInfo info, StreamingContext context) - : base(info, context) - { - } - } -} diff --git a/src/Sdk/WebApi/WebApi/HttpClients/Constants.cs b/src/Sdk/WebApi/WebApi/HttpClients/Constants.cs index c93c64057..f0c8361a3 100644 --- a/src/Sdk/WebApi/WebApi/HttpClients/Constants.cs +++ b/src/Sdk/WebApi/WebApi/HttpClients/Constants.cs @@ -5,119 +5,11 @@ namespace GitHub.Services { internal static class QueryParameters { - //Common query parameters - internal const String Properties = "properties"; - - //Account query parameters - internal const String CreatorId = "creatorId"; - internal const String OwnerId = "ownerId"; - internal const String IncludeDisabledAccounts = "includeDisabledAccounts"; - internal const String IncludeOwner = "includeOwner"; - internal const String StatusReason = "statusReason"; - internal const String IncludeDeletedUsers = "includeDeletedUsers"; - internal const String AccountId = "accountId"; - internal const String UsePrecreated = "usePrecreated"; - internal const string UserType = "userType"; - - //Identity query parameters - internal const String SubjectDescriptors = "subjectDescriptors"; - internal const String SocialDescriptors = "socialDescriptors"; - internal const String Descriptors = "descriptors"; - internal const String IdentityIds = "identityIds"; - internal const String SearchFilter = "searchFilter"; - internal const String FilterValue = "filterValue"; - internal const String QueryMembership = "queryMembership"; - internal const String IdentitySequenceId = "identitySequenceId"; - internal const String GroupSequenceId = "groupSequenceId"; - internal const String OrgIdentitySequenceId = "organizationIdentitySequenceId"; - internal const String PageSize = "pageSize"; - internal const String ScopeId = "scopeId"; - internal const String ScopeIds = "scopeIds"; - internal const String Recurse = "recurse"; - internal const String Deleted = "deleted"; - internal const String ScopeName = "scopeName"; - internal const String MemberId = "memberId"; - internal const String IncludeRestrictedVisibility = "includeRestrictedVisibility"; - internal const String ReadAllIdentities = "readAllIdentities"; - internal const String ReadIdentitiesOptions = "options"; - internal const String DomainId = "domainId"; - - //DelegatedAuthorization query parameters - internal const String UserId = "userId"; - internal const String DisplayName = "displayName"; - internal const String ValidTo = "validTo"; - internal const String Scope = "scope"; - internal const String AccessTokenKey = "key"; - internal const String TokenType = "tokenType"; - - //Security query parameters - internal const String AlwaysAllowAdministrators = "alwaysAllowAdministrators"; - internal const String Descriptor = "descriptor"; - internal const String IncludeExtendedInfo = "includeExtendedInfo"; - internal const String LocalOnly = "localonly"; - internal const String Token = "token"; - internal const String Tokens = "tokens"; - internal const String Delimiter = "delimiter"; - - // Security backing store query parameters - internal const String OldSequenceId = "oldSequenceId"; - internal const String InheritFlag = "inheritFlag"; - internal const String UseVsidSubjects = "useVsidSubjects"; - - //Profile query parameters - internal const String Size = "size"; - internal const String ModifiedSince = "modifiedsince"; - internal const String ModifiedAfterRevision = "modifiedafterrevision"; - internal const String Partition = "partition"; - internal const String Details = "details"; - internal const String WithCoreAttributes = "withcoreattributes"; - internal const String CoreAttributes = "coreattributes"; - internal const String ProfilePageType = "profilePageType"; - internal const String IpAddress = "ipaddress"; - - //ClinetNotification query parameters - internal const String ClientId = "clientId"; - //File container query parameters internal const String ArtifactUris = "artifactUris"; internal const String ScopeIdentifier = "scope"; internal const String ItemPath = "itemPath"; internal const String includeDownloadTickets = "includeDownloadTickets"; internal const String isShallow = "isShallow"; - - //Telemetry query parameters for Licensing - internal const String TelemetryPrefix = "t-"; - - } - - public static class IdentityMruRestApiConstants - { - public const String Add = "add"; - public const String Remove = "remove"; - public const String Update = "update"; - public const String Me = "me"; - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class ProfileRestApiConstants - { - public const String Me = "me"; - public const String Value = "value"; - } - - public static class UserRestApiConstants - { - public const String Me = "me"; - public const string JsonMergePatchMediaType = "application/merge-patch+json"; - } - - public static class CustomHttpResponseHeaders - { - public const string ActivityId = "ActivityId"; - } - - public static class ExtensionManagementConstants - { - public const string Me = "me"; } } diff --git a/src/Sdk/WebApi/WebApi/HttpClients/FileContainerHttpClient.cs b/src/Sdk/WebApi/WebApi/HttpClients/FileContainerHttpClient.cs index 57202de4e..531b928a0 100644 --- a/src/Sdk/WebApi/WebApi/HttpClients/FileContainerHttpClient.cs +++ b/src/Sdk/WebApi/WebApi/HttpClients/FileContainerHttpClient.cs @@ -66,18 +66,6 @@ namespace GitHub.Services.FileContainer.Client { } - /// - /// Queries for file containers - /// - /// List of artifact uris associated with containers. If empty or null will return all containers. - /// - /// - public Task> QueryContainersAsync(List artifactUris, Guid scopeIdentifier, Object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - List> query = AppendContainerQueryString(artifactUris, scopeIdentifier); - return SendAsync>(HttpMethod.Get, FileContainerResourceIds.FileContainer, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken); - } - /// /// Queries for container items in a container. /// @@ -434,48 +422,6 @@ namespace GitHub.Services.FileContainer.Client return response; } - [EditorBrowsable(EditorBrowsableState.Never)] - public async Task> CreateItemsAsync( - Int64 containerId, - List items, - Guid scopeIdentifier, - CancellationToken cancellationToken = default(CancellationToken), - Object userState = null) - { - List updatedItems = items.Select(x => { x.ContainerId = containerId; x.Status = ContainerItemStatus.PendingUpload; return x; }).ToList(); - - try - { - return await PostAsync, List>( - updatedItems, - FileContainerResourceIds.FileContainer, - routeValues: new { containerId = containerId, scopeIdentifier = scopeIdentifier }, - version: s_currentApiVersion, - userState: userState, - cancellationToken: cancellationToken); - } - catch (Exception) - { - //eat until versioning works in options request - return updatedItems; - } - } - - // for back compat with internal use - [EditorBrowsable(EditorBrowsableState.Never)] - public Task UploadFileToTfsAsync( - Int64 containerId, - String itemPath, - Stream fileStream, - Guid scopeIdentifier, - CancellationToken cancellationToken, - int chunkSize = c_defaultChunkSize, - bool uploadFirstChunk = false, - Object userState = null) - { - return UploadFileAsync(containerId, itemPath, fileStream, scopeIdentifier, cancellationToken, chunkSize, uploadFirstChunk, userState); - } - /// /// Download a file from the specified container. /// @@ -494,55 +440,6 @@ namespace GitHub.Services.FileContainer.Client return DownloadAsync(containerId, itemPath, "application/octet-stream", cancellationToken, scopeIdentifier, userState); } - /// - /// Download a file or folder as a zip file. - /// - /// - /// - /// - /// - /// A stream of the zip file. - public Task DownloadItemAsZipAsync( - Int64 containerId, - String itemPath, - CancellationToken cancellationToken, - Guid scopeIdentifier, - Object userState = null) - { - return DownloadAsync(containerId, itemPath, "application/zip", cancellationToken, scopeIdentifier, userState); - } - - /// - /// Delete a container item - /// - /// - /// - /// - /// - /// - public Task DeleteContainerItem( - Int64 containerId, - String itemPath, - Guid scopeIdentifier, - CancellationToken cancellationToken = default(CancellationToken), - Object userState = null) - { - if (containerId < 1) - { - throw new ArgumentException(WebApiResources.ContainerIdMustBeGreaterThanZero(), "containerId"); - } - - List> query = AppendItemQueryString(itemPath, scopeIdentifier); - - return DeleteAsync( - FileContainerResourceIds.FileContainer, - new { containerId = containerId }, - s_currentApiVersion, - query, - userState, - cancellationToken); - } - public bool IsFastFailResponse(HttpResponseMessage response) { int statusCode = (int)response?.StatusCode; @@ -582,21 +479,6 @@ namespace GitHub.Services.FileContainer.Client return await SendAsync(requestMessage, HttpCompletionOption.ResponseHeadersRead, userState, cancellationToken).ConfigureAwait(false); } - private List> AppendContainerQueryString(List artifactUris, Guid scopeIdentifier) - { - List> collection = new List>(); - - if (artifactUris != null && artifactUris.Count > 0) - { - String artifactsString = String.Join(",", artifactUris.Select(x => x.AbsoluteUri)); - collection.Add(QueryParameters.ArtifactUris, artifactsString); - } - - collection.Add(QueryParameters.ScopeIdentifier, scopeIdentifier.ToString()); - - return collection; - } - private List> AppendItemQueryString(String itemPath, Guid scopeIdentifier, Boolean includeDownloadTickets = false, Boolean isShallow = false) { List> collection = new List>(); diff --git a/src/Sdk/WebApi/WebApi/HttpClients/IdentityHttpClient.cs b/src/Sdk/WebApi/WebApi/HttpClients/IdentityHttpClient.cs deleted file mode 100644 index e63aea129..000000000 --- a/src/Sdk/WebApi/WebApi/HttpClients/IdentityHttpClient.cs +++ /dev/null @@ -1,1167 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Net.Http; -using System.Threading; -using System.Threading.Tasks; -using GitHub.Services.Common; -using GitHub.Services.DelegatedAuthorization; -using GitHub.Services.WebApi; -using GitHub.Services.WebApi.Exceptions; -using GitHub.Services.Common.Internal; -using System.Linq; -using GitHub.Services.WebApi.Patch.Json; - -namespace GitHub.Services.Identity.Client -{ - [ResourceArea(IdentityResourceIds.AreaId)] - [ClientCircuitBreakerSettings(timeoutSeconds: 100, failurePercentage:80, MaxConcurrentRequests = 110)] - public class IdentityHttpClient : VssHttpClientBase - { - static IdentityHttpClient() - { - s_translatedExceptions = new Dictionary(); - - // 400 (Bad Request) - s_translatedExceptions.Add("IdentityDomainMismatchException", typeof(IdentityDomainMismatchException)); - s_translatedExceptions.Add("AddMemberCyclicMembershipException", typeof(AddMemberCyclicMembershipException)); - s_translatedExceptions.Add("IdentityPropertyRequiredException", typeof(IdentityPropertyRequiredException)); - s_translatedExceptions.Add("IdentityExpressionException", typeof(IdentityExpressionException)); - s_translatedExceptions.Add("InvalidDisplayNameException", typeof(InvalidDisplayNameException)); - s_translatedExceptions.Add("GroupNameNotRecognizedException", typeof(GroupNameNotRecognizedException)); - s_translatedExceptions.Add("IdentityMapReadOnlyException", typeof(IdentityMapReadOnlyException)); - s_translatedExceptions.Add("IdentityNotServiceIdentityException", typeof(IdentityNotServiceIdentityException)); - s_translatedExceptions.Add("InvalidServiceIdentityNameException", typeof(InvalidServiceIdentityNameException)); - s_translatedExceptions.Add("IllegalIdentityException", typeof(IllegalIdentityException)); - s_translatedExceptions.Add("MissingRequiredParameterException", typeof(MissingRequiredParameterException)); - s_translatedExceptions.Add("IncompatibleScopeException", typeof(IncompatibleScopeException)); - - // 403 (Forbidden) - s_translatedExceptions.Add("RemoveAccountOwnerFromAdminGroupException", typeof(RemoveAccountOwnerFromAdminGroupException)); - s_translatedExceptions.Add("RemoveSelfFromAdminGroupException", typeof(RemoveSelfFromAdminGroupException)); - s_translatedExceptions.Add("AddGroupMemberIllegalMemberException", typeof(AddGroupMemberIllegalMemberException)); - s_translatedExceptions.Add("AddGroupMemberIllegalWindowsIdentityException", typeof(AddGroupMemberIllegalWindowsIdentityException)); - s_translatedExceptions.Add("AddGroupMemberIllegalInternetIdentityException", typeof(AddGroupMemberIllegalInternetIdentityException)); - s_translatedExceptions.Add("RemoveSpecialGroupException", typeof(RemoveSpecialGroupException)); - s_translatedExceptions.Add("NotApplicationGroupException", typeof(NotApplicationGroupException)); - s_translatedExceptions.Add("ModifyEveryoneGroupException", typeof(ModifyEveryoneGroupException)); - s_translatedExceptions.Add("NotASecurityGroupException", typeof(NotASecurityGroupException)); - s_translatedExceptions.Add("RemoveMemberServiceAccountException", typeof(RemoveMemberServiceAccountException)); - s_translatedExceptions.Add("AccountPreferencesAlreadyExistException", typeof(AccountPreferencesAlreadyExistException)); - - // 404 (NotFound) - s_translatedExceptions.Add("RemoveGroupMemberNotMemberException", typeof(RemoveGroupMemberNotMemberException)); - s_translatedExceptions.Add("RemoveNonexistentGroupException", typeof(RemoveNonexistentGroupException)); - s_translatedExceptions.Add("FindGroupSidDoesNotExistException", typeof(FindGroupSidDoesNotExistException)); - s_translatedExceptions.Add("GroupScopeDoesNotExistException", typeof(GroupScopeDoesNotExistException)); - s_translatedExceptions.Add("IdentityNotFoundException", typeof(IdentityNotFoundException)); - - // 409 (Conflict) - s_translatedExceptions.Add("GroupCreationException", typeof(GroupCreationException)); - s_translatedExceptions.Add("GroupScopeCreationException", typeof(GroupScopeCreationException)); - s_translatedExceptions.Add("AddMemberIdentityAlreadyMemberException", typeof(AddMemberIdentityAlreadyMemberException)); - s_translatedExceptions.Add("GroupRenameException", typeof(GroupRenameException)); - s_translatedExceptions.Add("IdentityAlreadyExistsException", typeof(IdentityAlreadyExistsException)); - s_translatedExceptions.Add("IdentityAccountNameAlreadyInUseException", typeof(IdentityAccountNameAlreadyInUseException)); - s_translatedExceptions.Add("IdentityAliasAlreadyInUseException", typeof(IdentityAliasAlreadyInUseException)); - s_translatedExceptions.Add("AddProjectGroupProjectMismatchException", typeof(AddProjectGroupProjectMismatchException)); - - // 500 (InternalServerError) - s_translatedExceptions.Add("IdentitySyncException", typeof(IdentitySyncException)); - - // 503 (ServiceUnavailable) - s_translatedExceptions.Add("IdentityProviderUnavailableException", typeof(IdentityProviderUnavailableException)); - - s_currentApiVersion = new ApiResourceVersion(1.0); - } - - public IdentityHttpClient(Uri baseUrl, VssCredentials credentials) - : base(baseUrl, credentials) - { - } - - public IdentityHttpClient(Uri baseUrl, VssCredentials credentials, VssHttpRequestSettings settings) - : base(baseUrl, credentials, settings) - { - } - - public IdentityHttpClient(Uri baseUrl, VssCredentials credentials, params DelegatingHandler[] handlers) - : base(baseUrl, credentials, handlers) - { - } - - public IdentityHttpClient(Uri baseUrl, VssCredentials credentials, VssHttpRequestSettings settings, params DelegatingHandler[] handlers) - : base(baseUrl, credentials, settings, handlers) - { - } - - public IdentityHttpClient(Uri baseUrl, HttpMessageHandler pipeline, bool disposeHandler) - : base(baseUrl, pipeline, disposeHandler) - { - } - - #region Operations on Identities Controller - #region ReadIdentities overloads - /// - /// Reads all identities - /// - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public Task ReadIdentitiesAsync( - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - var queryParams = new List>(); - - return ReadIdentitiesAsyncInternal(queryParams, queryMembership, propertyNameFilters, includeRestrictedVisibility, requestHeadersContext: null, userState: userState, cancellationToken: cancellationToken); - } - - /// - /// Returns identities matching the passed in descriptors - /// - /// List of IdentityDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IList descriptors, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return ReadIdentitiesAsync(descriptors, requestHeadersContext: null, queryMembership: queryMembership, - propertyNameFilters: propertyNameFilters, includeRestrictedVisibility: includeRestrictedVisibility, - userState: userState, cancellationToken: cancellationToken); - } - - /// - /// Returns identities matching the passed in descriptors - /// - /// List of IdentityDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IList descriptors, - RequestHeadersContext requestHeadersContext, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(descriptors, "descriptors"); - - if (descriptors.Count > maxDescriptors) - { - return ReadIdentitiesBatchAsyncInternal( - descriptors, - queryMembership, - propertyNameFilters, - includeRestrictedVisibility, - requestHeadersContext, - userState, cancellationToken); - } - else - { - var pages = new List>(); - - pages.AddMultiple(QueryParameters.Descriptors, descriptors, SerializeDescriptor); - - return ReadIdentitiesAsyncInternal(pages, queryMembership, propertyNameFilters, includeRestrictedVisibility, requestHeadersContext, userState, cancellationToken); - } - } - - /// - /// Returns identities matching the passed in subject descriptors - /// - /// List of SocialDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IList socialDescriptors, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return ReadIdentitiesAsync(socialDescriptors, requestHeadersContext: null, queryMembership: queryMembership, - propertyNameFilters: propertyNameFilters, includeRestrictedVisibility: includeRestrictedVisibility, - userState: userState, cancellationToken: cancellationToken); - } - - /// - /// Returns identities matching the passed in descriptors - /// - /// List of SubjectDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - internal virtual Task ReadIdentitiesAsync( - IList socialDescriptors, - RequestHeadersContext requestHeadersContext, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(socialDescriptors, nameof(socialDescriptors)); - - if (socialDescriptors.Count > maxDescriptors) - { - return ReadIdentitiesBatchAsyncInternal( - socialDescriptors, - queryMembership, - propertyNameFilters, - includeRestrictedVisibility, - requestHeadersContext, - userState, cancellationToken); - } - else - { - var pages = new List>(); - - pages.AddMultiple(QueryParameters.SocialDescriptors, socialDescriptors.Select(descriptor => descriptor.ToString()).ToList()); - - return ReadIdentitiesAsyncInternal(pages, queryMembership, propertyNameFilters, includeRestrictedVisibility, requestHeadersContext, userState, cancellationToken); - } - } - - /// - /// Returns identities matching the passed in subject descriptors - /// - /// List of SubjectDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IList subjectDescriptors, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return ReadIdentitiesAsync(subjectDescriptors, requestHeadersContext: null, queryMembership: queryMembership, - propertyNameFilters: propertyNameFilters, includeRestrictedVisibility: includeRestrictedVisibility, - userState: userState, cancellationToken: cancellationToken); - } - - /// - /// Returns identities matching the passed in descriptors - /// - /// List of SubjectDescriptors to query for. - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - internal virtual Task ReadIdentitiesAsync( - IList subjectDescriptors, - RequestHeadersContext requestHeadersContext, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(subjectDescriptors, nameof(subjectDescriptors)); - - if (subjectDescriptors.Count > maxDescriptors) - { - return ReadIdentitiesBatchAsyncInternal( - subjectDescriptors, - queryMembership, - propertyNameFilters, - includeRestrictedVisibility, - requestHeadersContext, - userState, cancellationToken); - } - else - { - var pages = new List>(); - - pages.AddMultiple(QueryParameters.SubjectDescriptors, subjectDescriptors.Select(descriptor => descriptor.ToString()).ToList()); - - return ReadIdentitiesAsyncInternal(pages, queryMembership, propertyNameFilters, includeRestrictedVisibility, requestHeadersContext, userState, cancellationToken); - } - } - - /// - /// Returns identities matching the passed in identifiers - /// - /// Guids representing unique identifiers for the identities - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IList identityIds, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return ReadIdentitiesAsync(identityIds, requestHeadersContext: null, queryMembership: queryMembership, - propertyNameFilters: propertyNameFilters, includeRestrictedVisibility: includeRestrictedVisibility, - userState: userState, cancellationToken: cancellationToken); - } - - /// - /// Returns identities matching the passed in identifiers - /// - /// Guids representing unique identifiers for the identities - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - internal virtual Task ReadIdentitiesAsync( - IList identityIds, - RequestHeadersContext requestHeadersContext, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - bool includeRestrictedVisibility = false, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(identityIds, "identityIds"); - - if (identityIds.Count > maxIds) - { - return ReadIdentitiesBatchAsyncInternal( - identityIds, - queryMembership, - propertyNameFilters, - includeRestrictedVisibility, - userState, - requestHeadersContext, - cancellationToken); - } - else - { - var pages = new List>(); - - pages.AddMultiple(QueryParameters.IdentityIds, identityIds, (id) => id.ToString("N")); - - return ReadIdentitiesAsyncInternal(pages, queryMembership, propertyNameFilters, includeRestrictedVisibility, requestHeadersContext, userState, cancellationToken); - } - } - - public Task ReadIdentitiesAsync( - IdentitySearchFilter searchFilter, - string filterValue, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return ReadIdentitiesAsync(searchFilter, filterValue, ReadIdentitiesOptions.None, queryMembership, propertyNameFilters, userState, cancellationToken); - } - - /// - /// Returns identities matching the requested search factor and value - /// - /// - /// - /// Instructs the server whether to query for membership information. - /// Instructs the server which extended properties to query for. - /// Additional client state passed by caller. - /// A Task which when complete, contains the list of identities. - public virtual Task ReadIdentitiesAsync( - IdentitySearchFilter searchFilter, - string filterValue, - ReadIdentitiesOptions options, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckStringForNullOrEmpty(filterValue, "filterValue"); - - List> searchQuery = new List>(); - - searchQuery.Add(QueryParameters.SearchFilter, searchFilter.ToString()); - searchQuery.Add(QueryParameters.FilterValue, filterValue); - searchQuery.Add(QueryParameters.ReadIdentitiesOptions, options.ToString()); - - return ReadIdentitiesAsyncInternal(searchQuery, queryMembership, propertyNameFilters, includeRestrictedVisibility: false, requestHeadersContext: null, userState: userState, cancellationToken: cancellationToken); - } - - public virtual Task ReadIdentitiesAsync( - Guid scopeId, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - var query = new List>(); - query.Add(QueryParameters.ScopeId, scopeId.ToString("N")); - - return ReadIdentitiesAsyncInternal(query, queryMembership, propertyNameFilters, includeRestrictedVisibility: false, requestHeadersContext: null, userState: userState, cancellationToken: cancellationToken); - } - #endregion - - #region ReadIdentity overloads - public Task ReadIdentityAsync( - string identityPuid, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckStringForNullOrEmpty(identityPuid, "identityPuid"); - - return ReadIdentityAsyncInternal( - identityPuid, - queryMembership, - propertyNameFilters, - userState, cancellationToken); - } - - public Task ReadIdentityAsync( - Guid identityId, - QueryMembership queryMembership = QueryMembership.None, - IEnumerable propertyNameFilters = null, - object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckForEmptyGuid(identityId, "identityId"); - - return ReadIdentityAsyncInternal( - identityId.ToString("D"), - queryMembership, - propertyNameFilters, - userState, cancellationToken); - } - #endregion - - public async Task> UpdateIdentitiesAsync(IList identities, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "UpdateIdentities")) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(identities, "identities"); - - IdentitiesCollection collection = new IdentitiesCollection(identities); - HttpContent content = new ObjectContent>(new VssJsonCollectionWrapper(collection), base.Formatter); - - return await SendAsync>(HttpMethod.Put, IdentityResourceIds.Identity, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task UpdateIdentityAsync(Identity identity, object userState, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "UpdateIdentity")) - { - ArgumentUtility.CheckForNull(identity, "identity"); - - HttpContent content = new ObjectContent(identity, base.Formatter); - return await SendAsync(HttpMethod.Put, IdentityResourceIds.Identity, new { identityId = identity.Id }, s_currentApiVersion, content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task SwapIdentityAsync(Guid id1, Guid id2, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "SwapIdentity")) - { - ArgumentUtility.CheckForEmptyGuid(id1, "id1"); - ArgumentUtility.CheckForEmptyGuid(id2, "id2"); - - HttpContent content = new ObjectContent(typeof(SwapIdentityInfo), new SwapIdentityInfo(id1, id2), this.Formatter); - - return await SendAsync(HttpMethod.Post, IdentityResourceIds.SwapLocationId, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - //REST USAGE NON-STANDARD: Get operations on the same endpoint should return the same resources. This is a different - //resource. - public async Task GetIdentityChangesAsync(int identitySequenceId, int groupSequenceId, Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - int unspecifiedSequenceId = -1; - return await this.GetIdentityChangesAsync(identitySequenceId, groupSequenceId, unspecifiedSequenceId, scopeId, userState, cancellationToken).ConfigureAwait(false); - } - - public async Task GetIdentityChangesAsync(int identitySequenceId, int groupSequenceId, int organizationIdentitySequenceId, Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return await this.GetIdentityChangesAsync(identitySequenceId, groupSequenceId, organizationIdentitySequenceId, 0, scopeId, userState, cancellationToken).ConfigureAwait(false); - } - - public async Task GetIdentityChangesAsync(int identitySequenceId, int groupSequenceId, int organizationIdentitySequenceId, int pageSize, Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetIdentityChanges")) - { - List> query = new List>(); - query.Add(QueryParameters.IdentitySequenceId, identitySequenceId.ToString()); - query.Add(QueryParameters.GroupSequenceId, groupSequenceId.ToString()); - query.Add(QueryParameters.OrgIdentitySequenceId, organizationIdentitySequenceId.ToString()); - query.Add(QueryParameters.PageSize, pageSize.ToString()); - query.Add(QueryParameters.ScopeId, scopeId.ToString("N")); - - return await SendAsync(HttpMethod.Get, IdentityResourceIds.Identity, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task> GetUserIdentityIdsByDomainIdAsync( - Guid domainId, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, nameof(GetUserIdentityIdsByDomainIdAsync))) - { - ArgumentUtility.CheckForEmptyGuid(domainId, nameof(domainId)); - var query = new List>(); - query.Add(QueryParameters.DomainId, domainId.ToString("N")); - return - await - SendAsync>( - method: HttpMethod.Get, - locationId: IdentityResourceIds.Identity, - version: s_currentApiVersion, - queryParameters: query, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - #endregion - - #region Operations on IdentitySelf Controller - - public async Task GetIdentitySelfAsync(object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetIdentitySelf")) - { - return await SendAsync(HttpMethod.Get, IdentityResourceIds.IdentitySelf, version: s_currentApiVersion, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - #endregion - - #region Operations on IdentityTenant Controller - - public async Task GetTenant(string tenantId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetTenant")) - { - //NOTE [RR]: Having to re-create ApiResourceLocation here since /_apis is currently not - //Anonymous and using underlying SendAsync<> overloads throws a ObjectNullRefernceException - //when a null credential, indicating anonymous request, is - var resourceLocation = new ApiResourceLocation - { - Id = IdentityResourceIds.IdentityTenant, - ResourceName = IdentityResourceIds.IdentityTenantResource, - RouteTemplate = "_apis/identities/tenant/{tenantId}", - ResourceVersion = 1, - MinVersion = new Version(1, 0), - MaxVersion = new Version(2, 0), - ReleasedVersion = new Version(0, 0) - }; - - using (var requestMessage = CreateRequestMessage(HttpMethod.Get, resourceLocation, new { tenantId = tenantId }, version: s_currentApiVersion)) - using (var client = new HttpClient()) - { - var response = await client.SendAsync(requestMessage, cancellationToken: cancellationToken); - response.EnsureSuccessStatusCode(); - return await response.Content.ReadAsAsync(new[] { this.Formatter }, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - } - - #endregion - - #region Operations on service identities controller - - public async Task CreateFrameworkIdentityAsync(FrameworkIdentityType identityType, string role, string identifier, string displayName, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "CreateServiceIdentity")) - { - if (identityType == FrameworkIdentityType.None) - { - throw new ArgumentException(CommonResources.EmptyStringNotAllowed(), "identityType"); - } - - ArgumentUtility.CheckStringForNullOrEmpty(displayName, "role"); - ArgumentUtility.CheckStringForNullOrEmpty(displayName, "identifier"); - ArgumentUtility.CheckStringForNullOrEmpty(displayName, "displayName"); - - HttpContent content = new ObjectContent( - typeof(FrameworkIdentityInfo), - new FrameworkIdentityInfo - { - IdentityType = identityType, - Role = role, - Identifier = identifier, - DisplayName = displayName - }, - this.Formatter); - - return await SendAsync(HttpMethod.Put, IdentityResourceIds.FrameworkIdentity, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - #endregion - - #region Operations on Groups Controller - public virtual async Task ListGroupsAsync(Guid[] scopeIds = null, bool recurse = false, bool deleted = false, IEnumerable propertyNameFilters = null, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ListGroups")) - { - List> query = null; - - if (scopeIds != null || recurse != false || propertyNameFilters != null) - { - query = new List>(); - - if (scopeIds != null) - { - query.AddMultiple(QueryParameters.ScopeIds, scopeIds, (val) => val.ToString("N")); - } - - if (recurse != false) - { - query.Add(QueryParameters.Recurse, "true"); - } - - if (deleted != false) - { - query.Add(QueryParameters.Deleted, "true"); - } - - if (propertyNameFilters != null) - { - query.AddMultiple(QueryParameters.Properties, propertyNameFilters); - } - } - - return await SendAsync(HttpMethod.Get, IdentityResourceIds.Group, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public Task DeleteGroupAsync(IdentityDescriptor descriptor, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return DeleteGroupAsyncInternal(SerializeDescriptor(descriptor), userState, cancellationToken: cancellationToken); - } - - public Task DeleteGroupAsync(Guid groupId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return DeleteGroupAsyncInternal(groupId.ToString(), userState, cancellationToken); - } - - public async Task CreateGroupsAsync(Guid scopeId, IList groups, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "CreateGroup")) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - ArgumentUtility.CheckEnumerableForNullOrEmpty(groups, "groups"); - - HttpContent content = new ObjectContent(new CreateGroupsInfo(scopeId, groups), this.Formatter); - - return await SendAsync(HttpMethod.Post, IdentityResourceIds.Group, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion - - #region Operations on Scopes Controller - public async Task GetScopeAsync(string scopeName, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetScope")) - { - ArgumentUtility.CheckStringForNullOrEmpty(scopeName, "scopeName"); - - List> query = new List>(); - query.Add(QueryParameters.ScopeName, scopeName); - - return await SendAsync(HttpMethod.Get, IdentityResourceIds.Scope, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task GetScopeAsync(Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetScopeById")) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - - return await SendAsync(HttpMethod.Get, IdentityResourceIds.Scope, new { scopeId = scopeId }, version: s_currentApiVersion, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task CreateScopeAsync(Guid scopeId, Guid parentScopeId, GroupScopeType scopeType, string scopeName, string adminGroupName, string adminGroupDescription, Guid creatorId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "CreateScope")) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - - //REST USAGE NON-STANDARD: A POST to create a resource should be a reprensentation of the resource being created, in this case an IdentityScope. However, - //the create operation takes parameters not present in the new resource: specifically the adminGroupName and adminGroupDescription. We either need - //to set these in a different way -- on the correct resource -- or include them as part of IdentityScope. - - // Constructor Validates params - CreateScopeInfo info = new CreateScopeInfo(parentScopeId, scopeType, scopeName, adminGroupName, adminGroupDescription, creatorId); - - HttpContent content = new ObjectContent(info, this.Formatter); - - return await SendAsync(HttpMethod.Put, IdentityResourceIds.Scope, new { scopeId = scopeId }, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task RenameScopeAsync(Guid scopeId, string newName, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "RenameScope")) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - ArgumentUtility.CheckStringForNullOrEmpty(newName, "newName"); - - IdentityScope rename = new IdentityScope(scopeId, newName); - HttpContent content = new ObjectContent(rename, this.Formatter); - - return await SendAsync(new HttpMethod("PATCH"), IdentityResourceIds.Scope, new { scopeId = scopeId }, version: s_currentApiVersion, content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - // code for version 2 of the API - lets switch to this after the new api version has been in for a sprint - //ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - //ArgumentUtility.CheckStringForNullOrEmpty(newName, "newName"); - //return await UpdateScopeAsync(scopeId, nameof(IdentityScope.Name), newName, userState, cancellationToken); - } - - public async Task DeleteScopeAsync(Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "DeleteScope")) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - - return await SendAsync(HttpMethod.Delete, IdentityResourceIds.Scope, new { scopeId = scopeId }, version: s_currentApiVersion, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task RestoreGroupScopeAsync(Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckForEmptyGuid(scopeId, "scopeId"); - return await UpdateScopeAsync(scopeId, nameof(IdentityScope.IsActive), true, userState, cancellationToken).ConfigureAwait(false); - } - - private async Task UpdateScopeAsync(Guid scopeId, String property, object value, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using(new OperationScope(IdentityResourceIds.AreaName, "UpdateScope")) - { - JsonPatchDocument patchDocument = new JsonPatchDocument{ - new JsonPatchOperation - { - Operation = WebApi.Patch.Operation.Replace, - Path = "/" + property, - Value = value - } - }; - - HttpContent content = new ObjectContent(patchDocument, new VssJsonMediaTypeFormatter(true), "application/json-patch+json"); - - return await SendAsync(new HttpMethod("PATCH"), IdentityResourceIds.Scope, new { scopeId = scopeId }, version: new ApiResourceVersion(5.0, 2), content: content, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion - - #region Operations on Members\MembersOf Controllers\ - //These methods have analogs on the Members\MemberOf controllers but are unused... - //Task ReadMembershipsAsync(String memberId, QueryMembership queryMembership = QueryMembership.Direct) - - //This one called by IsMember, but not exposed directly - //Task ReadMembershipsAsync(String memberId, String containerId, QueryMembership queryMembership = QueryMembership.Direct) - - //Task ReadMembersAsync(String containerId, QueryMembership queryMembership = QueryMembership.Direct) - - //Task ReadMemberAsync(String containerId, String memberId, QueryMembership queryMembership = QueryMembership.Direct) - - public Task AddMemberToGroupAsync(IdentityDescriptor containerId, Guid memberId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - return AddMemberToGroupAsyncInternal(new { containerId = SerializeDescriptor(containerId), memberId = memberId }, new List>(), userState, cancellationToken); - } - - public Task AddMemberToGroupAsync(IdentityDescriptor containerId, IdentityDescriptor memberId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - //REST USAGE NON-STANDARD: This should not be a query param, as this ends up being a PUT, which should address the resource directly - // (and also see the internal method on non-standard use of PUT). But the memberId may contain a colon, which will cause it to - //be rejected by ASP.NET as dangerous (even if escaped) so doing this as a workaround. - List> query = new List>(); - query.Add(QueryParameters.MemberId, SerializeDescriptor(memberId)); - - return AddMemberToGroupAsyncInternal(new { containerId = SerializeDescriptor(containerId) }, query, userState, cancellationToken); - } - - public async Task RemoveMemberFromGroupAsync(IdentityDescriptor containerId, IdentityDescriptor memberId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "RemoveMemberFromGroup")) - { - //REST USAGE NON-STANDARD: This should not be a query param, as this DELETE which should address the resource directly - //but the memberId may contain a colon, which will cause it to be rejected by ASP.NET as dangerous (even if escaped) so doing - //this as a workaround. - List> query = new List>(); - query.Add(QueryParameters.MemberId, SerializeDescriptor(memberId)); - - return await SendAsync(HttpMethod.Delete, IdentityResourceIds.Member, new { containerId = SerializeDescriptor(containerId) }, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task IsMember(IdentityDescriptor containerId, IdentityDescriptor memberId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "IsMember")) - { - List> query = new List>(); - query.Add(QueryParameters.QueryMembership, QueryMembership.Expanded.ToString()); - - //Consider: Can this actually return null? This is how IdentityHttpComponent works... - IdentityDescriptor result = await SendAsync(HttpMethod.Get, IdentityResourceIds.MemberOf, - new { memberId = SerializeDescriptor(memberId), containerId = SerializeDescriptor(containerId) }, - version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - - return result != null; - } - } - #endregion - - #region Operations on IdentitySnapshot controller - public async Task GetIdentitySnapshotAsync(Guid scopeId, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetIdentitySnapshot")) - { - return await SendAsync(HttpMethod.Get, IdentityResourceIds.IdentitySnapshot, version: s_currentApiVersion, routeValues: new { scopeId = scopeId }, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - #endregion - - #region Operations on SignoutToken controller - public async Task GetSignoutToken(object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetSignoutToken")) - { - return await SendAsync( - HttpMethod.Get, - IdentityResourceIds.SignoutToken, - version: s_currentApiVersion, - routeValues: new object { }, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion - - #region Operations on SignedInToken controller - public async Task GetSignedInToken(object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetSignedInToken")) - { - return await SendAsync( - HttpMethod.Get, - IdentityResourceIds.SignedInToken, - version: s_currentApiVersion, - routeValues: new object { }, - userState: userState, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion - - #region Operations on IdentitySequenceId Controller - public async Task GetMaxSequenceIdAsync(object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "GetMaxSequenceId")) - { - return await SendAsync(HttpMethod.Get, IdentityResourceIds.IdentityMaxSequenceId, version: s_currentApiVersion, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion Operations on IdentitySequenceId Controller - - #region Operations on Claims Controller - public async Task CreateOrBindIdentity(Identity sourceIdentity, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "CreateOrBindWithClaims")) - { - ArgumentUtility.CheckForNull(sourceIdentity, nameof(sourceIdentity)); - ArgumentUtility.CheckForNull(sourceIdentity.Descriptor, nameof(sourceIdentity.Descriptor)); - - HttpContent content = new ObjectContent(sourceIdentity, this.Formatter); - - return await SendAsync(HttpMethod.Put, - IdentityResourceIds.Claims, - version: s_currentApiVersion, - userState: userState, - content: content, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - #endregion Operations on Claims Controller - - #region Operations on IdentityDescriptor Controller - /// - /// [Preview API] - /// - /// - /// - /// - /// The cancellation token to cancel operation. - public async Task GetDescriptorByIdAsync( - Guid id, - bool? isMasterId = null, - object userState = null, - CancellationToken cancellationToken = default(CancellationToken)) - { - object routeValues = new { id = id }; - - var queryParams = new List>(); - if (isMasterId != null) - { - queryParams.Add("isMasterId", isMasterId.Value.ToString()); - } - - return await SendAsync( - HttpMethod.Get, - IdentityResourceIds.DescriptorsResourceLocationId, - routeValues: routeValues, - version: new ApiResourceVersion("3.2-preview.1"), - queryParameters: queryParams, - userState: userState, - cancellationToken: - cancellationToken).ConfigureAwait(false); - } - #endregion Operations on IdentityDescriptor Controller - - #region Private Helpers - private async Task ReadIdentitiesAsyncInternal(List> searchQuery, QueryMembership queryMembership, IEnumerable propertyNameFilters, bool includeRestrictedVisibility, RequestHeadersContext requestHeadersContext, object userState, CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentities")) - { - AppendQueryString(searchQuery, queryMembership, propertyNameFilters, includeRestrictedVisibility); - var additionalHeaders = RequestHeadersContext.HeadersUtils.PopulateRequestHeaders(requestHeadersContext); - - return await SendAsync(HttpMethod.Get, additionalHeaders, IdentityResourceIds.Identity, version: s_currentApiVersion, queryParameters: searchQuery, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private async Task ReadIdentitiesBatchAsyncInternal( - IList socialDescriptors, - QueryMembership queryMembership, - IEnumerable propertyNameFilters, - bool includeRestrictedVisibility, - RequestHeadersContext requestHeadersContext, - object userState, CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentitiesBatch")) - { - IdentityBatchInfo info = new IdentityBatchInfo(socialDescriptors, queryMembership, propertyNameFilters, includeRestrictedVisibility); - - HttpContent content = new ObjectContent(info, base.Formatter); - - var queryParams = new List>() - { - {IdentityBatchTelemetryConstants.QueryMembershipHint, queryMembership.ToString()}, - {IdentityBatchTelemetryConstants.FlavorHint, IdentityBatchTelemetryConstants.BySocialDescriptorFlavor }, - {IdentityBatchTelemetryConstants.CountHint, (socialDescriptors?.Count ?? 0).ToString() }, - }; - - var additionalHeaders = RequestHeadersContext.HeadersUtils.PopulateRequestHeaders(requestHeadersContext); - - return await SendAsync( - HttpMethod.Post, - additionalHeaders, - IdentityResourceIds.IdentityBatch, - version: s_currentApiVersion, - content: content, - userState: userState, - queryParameters: queryParams, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private async Task ReadIdentitiesBatchAsyncInternal( - IList subjectDescriptors, - QueryMembership queryMembership, - IEnumerable propertyNameFilters, - bool includeRestrictedVisibility, - RequestHeadersContext requestHeadersContext, - object userState, CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentitiesBatch")) - { - IdentityBatchInfo info = new IdentityBatchInfo(subjectDescriptors, queryMembership, propertyNameFilters, includeRestrictedVisibility); - - HttpContent content = new ObjectContent(info, base.Formatter); - - var queryParams = new List>() - { - {IdentityBatchTelemetryConstants.QueryMembershipHint, queryMembership.ToString()}, - {IdentityBatchTelemetryConstants.FlavorHint, IdentityBatchTelemetryConstants.BySubjectDescriptorFlavor }, - {IdentityBatchTelemetryConstants.CountHint, (subjectDescriptors?.Count ?? 0).ToString() }, - }; - - var additionalHeaders = RequestHeadersContext.HeadersUtils.PopulateRequestHeaders(requestHeadersContext); - - return await SendAsync( - HttpMethod.Post, - additionalHeaders, - IdentityResourceIds.IdentityBatch, - version: s_currentApiVersion, - content: content, - userState: userState, - queryParameters: queryParams, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private async Task ReadIdentitiesBatchAsyncInternal( - IList descriptors, - QueryMembership queryMembership, - IEnumerable propertyNameFilters, - bool includeRestrictedVisibility, - RequestHeadersContext requestHeadersContext, - object userState, CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentitiesBatch")) - { - IdentityBatchInfo info = new IdentityBatchInfo(descriptors, queryMembership, propertyNameFilters, includeRestrictedVisibility); - - HttpContent content = new ObjectContent(info, base.Formatter); - - var queryParams = new List>() - { - {IdentityBatchTelemetryConstants.QueryMembershipHint, queryMembership.ToString()}, - {IdentityBatchTelemetryConstants.FlavorHint, IdentityBatchTelemetryConstants.ByDescriptorFlavor }, - {IdentityBatchTelemetryConstants.CountHint, (descriptors?.Count ?? 0).ToString() }, - }; - - var additionalHeaders = RequestHeadersContext.HeadersUtils.PopulateRequestHeaders(requestHeadersContext); - - return await SendAsync( - HttpMethod.Post, - additionalHeaders, - IdentityResourceIds.IdentityBatch, - version: s_currentApiVersion, - content: content, - userState: userState, - queryParameters: queryParams, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private async Task ReadIdentitiesBatchAsyncInternal( - IList identityIds, - QueryMembership queryMembership, - IEnumerable propertyNameFilters, - bool includeRestrictedVisibility, - object userState, - RequestHeadersContext requestHeadersContext, - CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentitiesBatch")) - { - IdentityBatchInfo info = new IdentityBatchInfo(identityIds, queryMembership, propertyNameFilters, includeRestrictedVisibility); - - HttpContent content = new ObjectContent(info, base.Formatter); - - var queryParams = new List> - { - {IdentityBatchTelemetryConstants.QueryMembershipHint, queryMembership.ToString()}, - {IdentityBatchTelemetryConstants.FlavorHint, IdentityBatchTelemetryConstants.ByIdFlavor }, - {IdentityBatchTelemetryConstants.CountHint, (identityIds?.Count ?? 0).ToString() }, - }; - - var additionalHeaders = RequestHeadersContext.HeadersUtils.PopulateRequestHeaders(requestHeadersContext); - - return await SendAsync( - HttpMethod.Post, - additionalHeaders, - IdentityResourceIds.IdentityBatch, - version: s_currentApiVersion, - content: content, - userState: userState, - queryParameters: queryParams, - cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - //Separate endpoint for identity and identities - private async Task ReadIdentityAsyncInternal( - string identityId, - QueryMembership queryMembership, - IEnumerable propertyNameFilters, - object userState, CancellationToken cancellationToken) - { - using (new OperationScope(IdentityResourceIds.AreaName, "ReadIdentity")) - { - var query = new List>(); - AppendQueryString(query, queryMembership, propertyNameFilters, false); - - return await SendAsync(HttpMethod.Get, IdentityResourceIds.Identity, new { identityId = identityId }, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private async Task DeleteGroupAsyncInternal(string groupId, object userState, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "DeleteGroup")) - { - return await SendAsync(HttpMethod.Delete, IdentityResourceIds.Group, new { groupId = groupId }, version: s_currentApiVersion, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task AddMemberToGroupAsyncInternal(object routeParams, IEnumerable> query, object userState = null, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(IdentityResourceIds.AreaName, "AddMemberToGroup")) - { - //REST USAGE NON-STANDARD: This is modeled as a PUT operation, but contains no body. PUT should create or replace the resource at this - //address, but in this case, there is no resource, it is adding a link between resources. This should be done differently - return await SendAsync(HttpMethod.Put, IdentityResourceIds.Member, routeParams, version: s_currentApiVersion, queryParameters: query, userState: userState, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - private void AppendQueryString(List> queryParams, QueryMembership queryMembership, IEnumerable propertyNameFilters, bool includeRestrictedVisibility) - { - queryParams.Add(QueryParameters.QueryMembership, queryMembership.ToString()); - - queryParams.AddMultiple(QueryParameters.Properties, propertyNameFilters); - - if (includeRestrictedVisibility) - { - queryParams.Add(QueryParameters.IncludeRestrictedVisibility, "true"); - } - } - - private static string SerializeDescriptor(IdentityDescriptor descriptor) - { - if (descriptor == null) - { - return string.Empty; - } - else - { - return string.Join(";", descriptor.IdentityType, descriptor.Identifier); - } - } - - - #endregion - - /// - /// Exceptions for account errors - /// - protected override IDictionary TranslatedExceptions - { - get - { - return s_translatedExceptions; - } - } - - private static class IdentityBatchTelemetryConstants - { - public const string QueryMembershipHint = "queryMembership"; - public const string FlavorHint = "flavor"; - public const string CountHint = "count"; - - public const string ByIdFlavor = "id"; - public const string ByDescriptorFlavor = "descriptor"; - public const string BySubjectDescriptorFlavor = "subjectDescriptor"; - public const string BySocialDescriptorFlavor = "socialDescriptor"; - } - - private static Dictionary s_translatedExceptions; - private static readonly ApiResourceVersion s_currentApiVersion; - private const int maxDescriptors = 5 /* 256 for descriptor + 64 for type + 1 */; - private const int maxIds = 50; - } -} diff --git a/src/Sdk/WebApi/WebApi/HttpClients/LocationHttpClient.cs b/src/Sdk/WebApi/WebApi/HttpClients/LocationHttpClient.cs index ab6f465ed..56a14940b 100644 --- a/src/Sdk/WebApi/WebApi/HttpClients/LocationHttpClient.cs +++ b/src/Sdk/WebApi/WebApi/HttpClients/LocationHttpClient.cs @@ -74,41 +74,6 @@ namespace GitHub.Services.Location.Client } } - public async Task UpdateServiceDefinitionsAsync(IEnumerable definitions, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "UpdateServiceDefinitions")) - { - ArgumentUtility.CheckEnumerableForNullOrEmpty(definitions, "definitions"); - - HttpContent content = new ObjectContent>>(new VssJsonCollectionWrapper>(definitions), base.Formatter); - await SendAsync(new HttpMethod("PATCH"), LocationResourceIds.ServiceDefinitions, null, s_currentApiVersion, content, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task DeleteServiceDefinitionAsync(String serviceType, Guid identifier, CancellationToken cancellationToken = default(CancellationToken)) - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "DeleteServiceDefinitions")) - { - return await SendAsync(HttpMethod.Delete, LocationResourceIds.ServiceDefinitions, new { serviceType = serviceType, identifier = identifier }, s_currentApiVersion, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task> GetServiceDefinitionsAsync() - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "GetServiceDefinitions")) - { - return await SendAsync>(HttpMethod.Get, LocationResourceIds.ServiceDefinitions, null, s_currentApiVersion).ConfigureAwait(false); - } - } - - public async Task> GetServiceDefinitionsAsync(String serviceType) - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "GetServiceDefinitions")) - { - return await SendAsync>(HttpMethod.Get, LocationResourceIds.ServiceDefinitions, new { serviceType = serviceType }, s_currentApiVersion).ConfigureAwait(false); - } - } - public Task GetServiceDefinitionAsync(String serviceType, Guid identifier, CancellationToken cancellationToken = default(CancellationToken)) { return GetServiceDefinitionAsync(serviceType, identifier, allowFaultIn: true, previewFaultIn: false, cancellationToken: cancellationToken); @@ -140,32 +105,6 @@ namespace GitHub.Services.Location.Client } } - [EditorBrowsable(EditorBrowsableState.Never)] - public async Task FlushSpsServiceDefinitionAsync(Guid hostId, CancellationToken cancellationToken = default(CancellationToken)) - { - // Used when migrating an SPS host to update all registered service definitions across other VSO instances. - using (new OperationScope(LocationResourceIds.LocationServiceArea, "FlushSpsServiceDefinition")) - { - return await SendAsync(HttpMethod.Put, LocationResourceIds.SpsServiceDefinition, new { hostId = hostId }, s_currentApiVersion, cancellationToken: cancellationToken).ConfigureAwait(false); - } - } - - public async Task> GetResourceAreasAsync() - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "GetResourceAreas")) - { - return await SendAsync>(HttpMethod.Get, LocationResourceIds.ResourceAreas, null, new ApiResourceVersion("3.2-preview.1")).ConfigureAwait(false); - } - } - - public async Task GetResourceAreaAsync(Guid areaId) - { - using (new OperationScope(LocationResourceIds.LocationServiceArea, "GetResourceAreas")) - { - return await SendAsync(HttpMethod.Get, LocationResourceIds.ResourceAreas, new { areaId = areaId } , new ApiResourceVersion("3.2-preview.1")).ConfigureAwait(false); - } - } - /// /// Exceptions for location errors /// diff --git a/src/Sdk/WebApi/WebApi/IdentityRef.cs b/src/Sdk/WebApi/WebApi/IdentityRef.cs deleted file mode 100644 index 106611864..000000000 --- a/src/Sdk/WebApi/WebApi/IdentityRef.cs +++ /dev/null @@ -1,124 +0,0 @@ -using System; -using System.ComponentModel; -using System.Runtime.Serialization; -using GitHub.Services.Common; -using GitHub.Services.Graph.Client; -using GitHub.Services.WebApi.Xml; -using Newtonsoft.Json; - -namespace GitHub.Services.WebApi -{ - [JsonObject(MemberSerialization = MemberSerialization.OptIn)] - [XmlSerializableDataContract(EnableCamelCaseNameCompat = true)] - public class IdentityRef : GraphSubjectBase, ISecuredObject - { - // The following "new" properties are inherited from the base class, - // but are reimplemented with public setters for back compat. - - public new SubjectDescriptor Descriptor - { - get { return base.Descriptor; } - set { base.Descriptor = value; } - } - - public new string DisplayName - { - get { return base.DisplayName; } - set { base.DisplayName = value; } - } - - public new string Url - { - get { return base.Url; } - set { base.Url = value; } - } - - public new ReferenceLinks Links - { - get { return base.Links; } - set { base.Links = value; } - } - - [DataMember(Name = "id")] - [JsonProperty(PropertyName = "id")] - public String Id { get; set; } - - // Deprecated. See https://dev.azure.com/mseng/VSOnline/_wiki/wikis/VSOnline.wiki?wikiVersion=GBwikiMaster&pagePath=%2FTeam%20Pages%2FPipelines%2FPublic%20projects&anchor=obsolete-identity-fields - /// - /// Deprecated - use Domain+PrincipalName instead - /// - [DataMember(Name = "uniqueName", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "uniqueName", DefaultValueHandling = DefaultValueHandling.Ignore)] - [JsonConverter(typeof(DefaultValueOnPublicAccessJsonConverter))] - public String UniqueName { get; set; } - - /// - /// Deprecated - Can be retrieved by querying the Graph user referenced in the "self" entry of the IdentityRef "_links" dictionary - /// - [DataMember(Name = "directoryAlias", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "directoryAlias", DefaultValueHandling = DefaultValueHandling.Ignore)] - [JsonConverter(typeof(DefaultValueOnPublicAccessJsonConverter))] - public String DirectoryAlias { get; set; } - - /// - /// Deprecated - not in use in most preexisting implementations of ToIdentityRef - /// - [DataMember(Name = "profileUrl", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "profileUrl", DefaultValueHandling = DefaultValueHandling.Ignore)] - [JsonConverter(typeof(DefaultValueOnPublicAccessJsonConverter))] - public String ProfileUrl { get; set; } - - /// - /// Deprecated - Available in the "avatar" entry of the IdentityRef "_links" dictionary - /// - [DataMember(Name = "imageUrl", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "imageUrl", DefaultValueHandling = DefaultValueHandling.Ignore)] - [JsonConverter(typeof(DefaultValueOnPublicAccessJsonConverter))] - public String ImageUrl { get; set; } - - /// - /// Deprecated - Can be inferred from the subject type of the descriptor (Descriptor.IsGroupType) - /// - [DataMember(Name = "isContainer", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "isContainer", DefaultValueHandling = DefaultValueHandling.Ignore)] - public Boolean IsContainer { get; set; } - - /// - /// Deprecated - Can be inferred from the subject type of the descriptor (Descriptor.IsAadUserType/Descriptor.IsAadGroupType) - /// - [DataMember(Name = "isAadIdentity", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "isAadIdentity", DefaultValueHandling = DefaultValueHandling.Ignore)] - public Boolean IsAadIdentity { get; set; } - - /// - /// Deprecated - Can be retrieved by querying the Graph membership state referenced in the "membershipState" entry of the GraphUser "_links" dictionary - /// - [DataMember(Name = "inactive", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "inactive", DefaultValueHandling = DefaultValueHandling.Ignore)] - public Boolean Inactive { get; set; } - - [DataMember(Name = "isDeletedInOrigin", EmitDefaultValue = false)] - [JsonProperty(PropertyName = "isDeletedInOrigin", DefaultValueHandling = DefaultValueHandling.IgnoreAndPopulate)] - public Boolean IsDeletedInOrigin { get; set; } - - /// - /// This property is for xml compat only. - /// - [DataMember(Name = "displayName", EmitDefaultValue = false)] - [JsonIgnore, Obsolete, EditorBrowsable(EditorBrowsableState.Never)] - public string DisplayNameForXmlSerialization { get => base.DisplayName; set => base.DisplayName = value; } - - /// - /// This property is for xml compat only. - /// - [DataMember(Name = "url", EmitDefaultValue = false)] - [JsonIgnore, Obsolete, EditorBrowsable(EditorBrowsableState.Never)] - public string UrlForXmlSerialization { get => base.Url; set => base.Url = value; } - - Guid ISecuredObject.NamespaceId => GraphSecurityConstants.NamespaceId; - - int ISecuredObject.RequiredPermissions => GraphSecurityConstants.ReadByPublicIdentifier; - - string ISecuredObject.GetToken() => GraphSecurityConstants.RefsToken; - } -} diff --git a/src/Sdk/WebApi/WebApi/Location/LocationCacheManager.cs b/src/Sdk/WebApi/WebApi/Location/LocationCacheManager.cs index aad8fc550..e2c921b20 100644 --- a/src/Sdk/WebApi/WebApi/Location/LocationCacheManager.cs +++ b/src/Sdk/WebApi/WebApi/Location/LocationCacheManager.cs @@ -29,9 +29,6 @@ namespace GitHub.Services.WebApi.Location m_lastChangeId = -1; m_cacheExpirationDate = DateTime.MinValue; -#if !NETSTANDARD - ClientCacheTimeToLive = VssClientSettings.ClientCacheTimeToLive; -#endif if (serviceOwner == Guid.Empty) { // For a legacy server (which didn't return serviceOwner in the connectionData), let's not try to break anything diff --git a/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenHttpClient.cs b/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenHttpClient.cs index 8f0158f18..994675e41 100644 --- a/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenHttpClient.cs +++ b/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenHttpClient.cs @@ -40,20 +40,6 @@ namespace GitHub.Services.OAuth } } - /// - /// Performs a token exchange using the specified token request. - /// - /// The token request - /// A token for signalling cancellation - /// A Task<VssOAuthTokenResponse> which may be used to track progress of the token request - public Task GetTokenAsync( - VssOAuthTokenRequest request, - CancellationToken cancellationToken = default(CancellationToken)) - { - ArgumentUtility.CheckForNull(request, nameof(request)); - return GetTokenAsync(request.Grant, request.ClientCredential, request.Parameters, cancellationToken); - } - /// /// Performs a token exchange using the specified authorization grant and client credentials. /// @@ -75,12 +61,10 @@ namespace GitHub.Services.OAuth requestMessage.Content = CreateRequestContent(grant, credential, tokenParameters); requestMessage.Headers.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); -#if NETSTANDARD if (VssClientHttpRequestSettings.Default.UseHttp11) { requestMessage.Version = HttpVersion.Version11; } -#endif foreach (var headerVal in VssClientHttpRequestSettings.Default.UserAgent) { @@ -128,17 +112,10 @@ namespace GitHub.Services.OAuth }, }; -#if !NETSTANDARD - WebRequestHandler messageHandler = new WebRequestHandler() - { - UseDefaultCredentials = false - }; -#else HttpClientHandler messageHandler = new HttpClientHandler() { UseDefaultCredentials = false }; -#endif // Inherit proxy setting from VssHttpMessageHandler if (VssHttpMessageHandler.DefaultWebProxy != null) @@ -158,11 +135,7 @@ namespace GitHub.Services.OAuth if (requestUri.Scheme.Equals("https", StringComparison.OrdinalIgnoreCase) && VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback != null) { -#if !NETSTANDARD - messageHandler.ServerCertificateValidationCallback = VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback; -#else messageHandler.ServerCertificateCustomValidationCallback = VssClientHttpRequestSettings.Default.ServerCertificateValidationCallback; -#endif } return new VssHttpRetryMessageHandler(retryOptions, messageHandler); diff --git a/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenRequest.cs b/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenRequest.cs index 3e21ab7e3..d9b40606c 100644 --- a/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenRequest.cs +++ b/src/Sdk/WebApi/WebApi/OAuth/VssOAuthTokenRequest.cs @@ -1,8 +1,4 @@ -using System; -using System.Collections.Generic; -using System.Net.Http.Formatting; -using GitHub.Services.Common; -using GitHub.Services.WebApi.Jwt; +using GitHub.Services.Common; namespace GitHub.Services.OAuth { @@ -79,151 +75,6 @@ namespace GitHub.Services.OAuth } } -#if !NETSTANDARD - /// - /// Initializes a new VssOAuthTokenRequest instance from the specified form input. - /// - /// The input which should be parsed into a token request - /// A new VssOAuthTokenRequest instance representative of the provided form input - public static VssOAuthTokenRequest FromFormInput(FormDataCollection form) - { - var parsedParameters = new HashSet(); - var grant = CreateGrantFromFormInput(form, parsedParameters); - var clientCredential = CreateClientCredentialFromFormInput(form, parsedParameters); - - var tokenParameters = new VssOAuthTokenParameters(); - foreach (var parameter in form) - { - // Only include parameters in the extended set if we didn't already read them in the grant and - // credentials parsing logic. - if (parsedParameters.Add(parameter.Key)) - { - tokenParameters.Add(parameter.Key, parameter.Value); - } - } - - return new VssOAuthTokenRequest(grant, clientCredential, tokenParameters); - } - - private static VssOAuthGrant CreateGrantFromFormInput( - FormDataCollection form, - ISet parsedParameters) - { - ArgumentUtility.CheckForNull(form, nameof(form)); - - var grantType = GetRequiredValue(form, VssOAuthConstants.GrantType, VssOAuthErrorCodes.InvalidRequest); - switch (grantType) - { - case VssOAuthConstants.AuthorizationCodeGrantType: - var codeValue = GetRequiredValue(form, VssOAuthConstants.Code, VssOAuthErrorCodes.InvalidRequest); - parsedParameters.Add(VssOAuthConstants.Code); - return new VssOAuthCodeGrant(codeValue); - - case VssOAuthConstants.ClientCredentialsGrantType: - return VssOAuthGrant.ClientCredentials; - - case VssOAuthConstants.JwtBearerAuthorizationGrantType: - var assertionValue = GetRequiredValue(form, VssOAuthConstants.Assertion, VssOAuthErrorCodes.InvalidRequest); - parsedParameters.Add(VssOAuthConstants.Assertion); - var assertion = JsonWebToken.Create(assertionValue); - return new VssOAuthJwtBearerGrant(new VssOAuthJwtBearerAssertion(assertion)); - - case VssOAuthConstants.RefreshTokenGrantType: - var refreshTokenValue = GetRequiredValue(form, VssOAuthConstants.RefreshToken, VssOAuthErrorCodes.InvalidRequest); - parsedParameters.Add(VssOAuthConstants.RefreshToken); - return new VssOAuthRefreshTokenGrant(refreshTokenValue); - - default: - // The OAuth 2.0 spec explicitly allows only ASCII characters in the error description - throw new VssOAuthTokenRequestException($"{VssOAuthConstants.GrantType} {grantType} is not supported") - { - Error = VssOAuthErrorCodes.UnsupportedGrantType, - }; - } - } - - private static VssOAuthClientCredential CreateClientCredentialFromFormInput( - FormDataCollection form, - ISet parsedParameters) - { - // https://tools.ietf.org/html/rfc7521#section-4.2 - // See the above document for rules on processing client assertions w.r.t other credential types. - var clientId = form[VssOAuthConstants.ClientId]; - var clientAssertionType = form[VssOAuthConstants.ClientAssertionType]; - if (clientAssertionType == VssOAuthConstants.JwtBearerClientAssertionType) - { - var clientAssertionValue = GetRequiredValue(form, VssOAuthConstants.ClientAssertion, VssOAuthErrorCodes.InvalidClient); - JsonWebToken clientAssertion = null; - try - { - clientAssertion = JsonWebToken.Create(clientAssertionValue); - } - catch (JsonWebTokenDeserializationException ex) - { - // The OAuth 2.0 spec explicitly allows only ASCII characters in the error description - throw new VssOAuthTokenRequestException($"{VssOAuthConstants.ClientAssertion} is not in the correct format", ex) - { - Error = VssOAuthErrorCodes.InvalidClient - }; - } - - // If the client id parameter is present when client assertions are used then it must match exactly - // the subject claim of the token. - if (!String.IsNullOrEmpty(clientId)) - { - if (clientId.Equals(clientAssertion.Subject, StringComparison.Ordinal)) - { - parsedParameters.Add(VssOAuthConstants.ClientId); - } - else - { - // The OAuth 2.0 spec explicitly allows only ASCII characters in the error description - throw new VssOAuthTokenRequestException($"{VssOAuthConstants.ClientId} {clientId} does not match {VssOAuthConstants.ClientAssertion} subject {clientAssertion.Subject}") - { - Error = VssOAuthErrorCodes.InvalidClient, - }; - } - } - else - { - clientId = clientAssertion.Subject; - } - - parsedParameters.Add(VssOAuthConstants.ClientAssertion); - parsedParameters.Add(VssOAuthConstants.ClientAssertionType); - return new VssOAuthJwtBearerClientCredential(clientId, new VssOAuthJwtBearerAssertion(clientAssertion)); - } - - if (!String.IsNullOrEmpty(clientId)) - { - parsedParameters.Add(VssOAuthConstants.ClientId); - - var clientSecret = form[VssOAuthConstants.ClientSecret]; - if (!String.IsNullOrEmpty(clientSecret)) - { - parsedParameters.Add(VssOAuthConstants.ClientSecret); - return new VssOAuthPasswordClientCredential(clientId, clientSecret); - } - } - - return null; - } - - private static String GetRequiredValue( - FormDataCollection form, - String parameterName, - String error) - { - var value = form[parameterName]; - if (String.IsNullOrEmpty(value)) - { - throw new VssOAuthTokenRequestException($"{parameterName} is required") { Error = error }; - } - - return value; - } -#endif - private VssOAuthTokenParameters m_tokenParameters; private readonly VssOAuthGrant m_grant; diff --git a/src/Sdk/WebApi/WebApi/PublicAccessJsonConverter.cs b/src/Sdk/WebApi/WebApi/PublicAccessJsonConverter.cs deleted file mode 100644 index 9a39a06e5..000000000 --- a/src/Sdk/WebApi/WebApi/PublicAccessJsonConverter.cs +++ /dev/null @@ -1,71 +0,0 @@ -using System; -using System.ComponentModel; -using System.Reflection; -using Newtonsoft.Json; - -namespace GitHub.Services.WebApi -{ - /// - /// A JsonConverter that sets the value of a property or field to its type's default value if the value is not null - /// and the ShouldClearValueFunction property is set and the ShouldClearValueFunction function returns true. This - /// can only be used on properties and fields. The converter will fail if used on at the class level. - /// - /// The type of the property or field. - [EditorBrowsable(EditorBrowsableState.Never)] - public class DefaultValueOnPublicAccessJsonConverter : PublicAccessJsonConverter - { - public override object GetDefaultValue() - { - return default(T); - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PublicAccessJsonConverter : PublicAccessJsonConverter - { - public PublicAccessJsonConverter() - { - if (typeof(T) == typeof(bool)) - { - // We are not supporting boolean types. This is because the converter does not get invoked in case of default values, - // therefore you can infer that a boolean type is false if the value does not exist in the json, and true if it does - // exist in the json even though the value would be set to false. - throw new ArgumentException($"The {nameof(PublicAccessJsonConverter)} does not support Boolean types, because the value can be inferred from the existance or non existance of the property in the json."); - } - } - - public override bool CanConvert(Type objectType) - { - return typeof(T).GetTypeInfo().IsAssignableFrom(objectType.GetTypeInfo()); - } - } - - [EditorBrowsable(EditorBrowsableState.Never)] - public abstract class PublicAccessJsonConverter : JsonConverter - { - public abstract object GetDefaultValue(); - - public override bool CanRead => false; - - public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) - { - throw new NotImplementedException(); - } - - public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) - { - if (value != null && ShouldClearValueFunction != null && ShouldClearValueFunction()) - { - serializer.Serialize(writer, GetDefaultValue()); - } - else - { - // this is the default serialization. This will fail if the converter is used at the class level rather than - // at the member level, because the default serialization will reinvoke this converter resulting in an exception. - serializer.Serialize(writer, value); - } - } - - internal static Func ShouldClearValueFunction { get; set; } - } -} diff --git a/src/Sdk/WebApi/WebApi/ResourceLocationIds.cs b/src/Sdk/WebApi/WebApi/ResourceLocationIds.cs index f4ccaa58b..1766977ff 100644 --- a/src/Sdk/WebApi/WebApi/ResourceLocationIds.cs +++ b/src/Sdk/WebApi/WebApi/ResourceLocationIds.cs @@ -1,729 +1,6 @@ using System; using GitHub.Services.Common; -//each resource (aka "controller") needs its own guid -//for the location service. Defined here so we can use it on the client -//to look it up. -namespace GitHub.Services.Identity -{ - public static class IdentityResourceIds - { - public const string AreaId = "8A3D49B8-91F0-46EF-B33D-DDA338C25DB3"; - public const string AreaName = "IMS"; - public static readonly Guid Identity = new Guid("{28010C54-D0C0-4C89-A5B0-1C9E188B9FB7}"); - public const string IdentityResource = "Identities"; - public static readonly Guid IdentityBatch = new Guid("{299E50DF-FE45-4D3A-8B5B-A5836FAC74DC}"); - public const string IdentityBatchResource = "IdentityBatch"; - public static readonly Guid Group = new Guid("{5966283B-4196-4D57-9211-1B68F41EC1C2}"); - public const string GroupResource = "Groups"; - public static readonly Guid Scope = new Guid("{4E11E2BF-1E79-4EB5-8F34-A6337BD0DE38}"); - public const string ScopeResource = "Scopes"; - public const string MemberLocationIdString = "8BA35978-138E-41F8-8963-7B1EA2C5F775"; - public static readonly Guid Member = new Guid(MemberLocationIdString); - public const string MemberResource = "Members"; - public const string MemberOfLocationIdString = "22865B02-9E4A-479E-9E18-E35B8803B8A0"; - public static readonly Guid MemberOf = new Guid(MemberOfLocationIdString); - public const string MemberOfResource = "MembersOf"; - public static readonly Guid IdentityDebug = new Guid("{C6B859A5-248C-448A-B770-D373C6E165BD}"); - public const string IdentityDebugResource = "IdentitiesDebug"; - public static readonly Guid IdentitySnapshot = new Guid("{D56223DF-8CCD-45C9-89B4-EDDF692400D7}"); - public const string IdentitySnapshotResource = "IdentitySnapshot"; - public static readonly Guid IdentitySelf = new Guid("{4BB02B5B-C120-4BE2-B68E-21F7C50A4B82}"); - public const string IdentitySelfResource = "me"; - public static readonly Guid SignoutToken = new Guid("{BE39E83C-7529-45E9-9C67-0410885880DA}"); - public const string SignoutTokenResource = "SignoutToken"; - public static readonly Guid SignedInToken = new Guid("{6074FF18-AAAD-4ABB-A41E-5C75F6178057}"); - public const string SignedInTokenResource = "SignedInToken"; - public static readonly Guid IdentityTenant = new Guid("{5F0A1723-2E2C-4C31-8CAE-002D01BDD592}"); - public const string IdentityTenantResource = "tenant"; - public static readonly Guid FrameworkIdentity = new Guid("{DD55F0EB-6EA2-4FE4-9EBE-919E7DD1DFB4}"); - public const string FrameworkIdentityResource = "Identity"; - public static readonly Guid IdentityMaxSequenceId = new Guid("{E4A70778-CB2C-4E85-B7CC-3F3C7AE2D408}"); - public const string IdentityMaxSequenceIdResource = "MaxSequenceId"; - public static readonly Guid Claims = new Guid("{90ddfe71-171c-446c-bf3b-b597cd562afd}"); - public const string ClaimsResource = "Claims"; - public static readonly Guid Rights = new Guid("{05F0AD48-6AEF-42A8-9D9B-9AB650875A5D}"); - public const string RightsResource = "Rights"; - public static readonly Guid RightsBatch = new Guid("{908B4EDC-4C6A-41E8-88ED-07A1F01A9A59}"); - - public static readonly Guid DescriptorsResourceLocationId = new Guid("A230389A-94F2-496C-839F-C929787496DD"); - public const string DescriptorsResourceName = "descriptors"; - - public static readonly Guid SwapLocationId = new Guid("{7A2338C2-39D8-4906-9889-E8BC9C52CBB2}"); - public const string SwapResource = "Swap"; - } -} - -namespace GitHub.Services.Graph -{ - public class GraphResourceIds - { - public const string AreaName = "Graph"; - public const string AreaId = "BB1E7EC9-E901-4B68-999A-DE7012B920F8"; - public static readonly Guid AreaIdGuid = new Guid(AreaId); - - public class Groups - { - public const string GroupsResourceName = "Groups"; - public static readonly Guid GroupsResourceLocationId = new Guid("EBBE6AF8-0B91-4C13-8CF1-777C14858188"); - } - - public class Descriptors - { - public static readonly Guid DescriptorsResourceLocationId = new Guid("048AEE0A-7072-4CDE-AB73-7AF77B1E0B4E"); - public const string DescriptorsResourceName = "Descriptors"; - } - - public class Memberships - { - public static readonly Guid MembershipsResourceLocationId = new Guid("3FD2E6CA-FB30-443A-B579-95B19ED0934C"); - public const string MembershipsResourceName = "Memberships"; - - public static readonly Guid MembershipsBatchResourceLocationId = new Guid("E34B6394-6B30-4435-94A9-409A5EEF3E31"); - public const string MembershipsBatchResourceName = "MembershipsBatch"; - - public static readonly Guid MembershipStatesResourceLocationId = new Guid("1FFE5C94-1144-4191-907B-D0211CAD36A8"); - public const string MembershipStatesResourceName = "MembershipStates"; - } - - public class Scopes - { - public const string ScopesResourceName = "Scopes"; - public static readonly Guid ScopesResourceLocationId = new Guid("21B5FEA7-2513-41D0-AF78-B8CDB0F328BB"); - } - - public class SubjectLookup - { - public const string SubjectLookupResourceName = "SubjectLookup"; - public static readonly Guid SubjectLookupResourceLocationId = new Guid("4DD4D168-11F2-48C4-83E8-756FA0DE027C"); - } - - public class Users - { - public const string UsersResourceName = "Users"; - public static readonly Guid UsersResourceLocationId = new Guid("005E26EC-6B77-4E4F-A986-B3827BF241F5"); - - public class ProviderInfo - { - public const string ProviderInfoResourceName = "ProviderInfo"; - public static readonly Guid ProviderInfoResourceLocationId = new Guid("1E377995-6FA2-4588-BD64-930186ABDCFA"); - } - } - - public class Subjects - { - public const string SubjectsResourceName = "Subjects"; - public static readonly Guid SubjectsResourceLocationId = new Guid("1D44A2AC-4F8A-459E-83C2-1C92626FB9C6"); - - public class Avatars - { - public const string AvatarsResourceName = "Avatars"; - public static readonly Guid AvatarsResourceLocationId = new Guid("801EAF9C-0585-4BE8-9CDB-B0EFA074DE91"); - } - } - - public class Members - { - public const string MembersResourceName = "Members"; - - public const string MembersByDescriptorResourceLocationIdString = "B9AF63A7-5DB6-4AF8-AAE7-387F775EA9C6"; - public static readonly Guid MembersByDescriptorResourceLocationId = new Guid(MembersByDescriptorResourceLocationIdString); - - public const string MembersResourceLocationIdString = "8B9ECDB2-B752-485A-8418-CC15CF12EE07"; - public static readonly Guid MembersResourceLocationId = new Guid(MembersResourceLocationIdString); - } - - public class CachePolicies - { - public const string CachePoliciesResourceName = "CachePolicies"; - public static readonly Guid CachePoliciesResourceLocationId = new Guid("BEB83272-B415-48E8-AC1E-A9B805760739"); - } - - public class MemberLookup - { - public const string MemberLookupResourceName = "MemberLookup"; - public static readonly Guid MemberLookupResourceLocationId = new Guid("3D74D524-AE3D-4D24-A9A7-F8A5CF82347A"); - } - - public class StorageKeys - { - public const string StorageKeysResourceName = "StorageKeys"; - public static readonly Guid StorageKeysResourceLocationId = new Guid("EB85F8CC-F0F6-4264-A5B1-FFE2E4D4801F"); - } - - public class MembershipTraversals - { - public const string MembershipTraversalsResourceName = "MembershipTraversals"; - public static readonly Guid MembershipTraversalsLocationId = new Guid("5D59D874-746F-4F9B-9459-0E571F1DED8C"); - } - - public class FederatedProviderData - { - public static readonly Guid FederatedProviderDataResourceLocationId = new Guid("5DCD28D6-632D-477F-AC6B-398EA9FC2F71"); - public const string FederatedProviderDataResourceName = "FederatedProviderData"; - } - } -} - -namespace GitHub.GraphProfile.WebApi -{ - [GenerateAllConstants] - public static class GraphProfileResourceIds - { - public const String AreaId = "4E40F190-2E3F-4D9F-8331-C7788E833080"; - public const String AreaName = "GraphProfile"; - public static readonly Guid AreaIdGuid = new Guid(AreaId); - - public class MemberAvatars - { - public const String MemberAvatarsResourceName = "MemberAvatars"; - public static readonly Guid MemberAvatarsLocationId = new Guid("D443431F-B341-42E4-85CF-A5B0D639ED8F"); - } - } -} - -namespace GitHub.Services.OAuth -{ - public static class TokenOAuth2ResourceIds - { - public const string AreaName = "tokenoauth2"; - public const string AreaId = "01c5c153-8bc0-4f07-912a-ec4dc386076d"; - - public const string TokenResource = "token"; - public static readonly Guid Token = new Guid("{bbc63806-e448-4e88-8c57-0af77747a323}"); - } - - public static class OAuth2ResourceIds - { - public const string AreaName = "oauth2"; - public const string AreaId = "585028FE-17D8-49E2-9A1B-EFB4D8502156"; - - public const string TokenResource = "token"; - public static readonly Guid Token = new Guid("{CD12634C-1D0F-4A19-9FF3-17875B764932}"); - } -} - -namespace GitHub.Services.Tokens -{ - public static class TokenAuthResourceIds - { - public const string AreaName = "TokenAuth"; - public const string AreaId = "c5a2d98b-985c-432e-825e-3c6971edae87"; - - public const string AuthorizationResource = "Authorizations"; - public static readonly Guid Authorization = new Guid("7d7ddc0d-60bd-4978-a0b5-295cb099a400"); - - public const string HostAuthorizationResource = "HostAuthorization"; - public static readonly Guid HostAuthorizeId = new Guid("{817d2b46-1507-4efe-be2b-adccf17ffd3b}"); - - public const string RegistrationResource = "Registration"; - public static readonly Guid Registration = new Guid("{522ad1a0-389d-4c6f-90da-b145fd2d3ad8}"); - - public const string RegistrationSecretResource = "RegistrationSecret"; - public static readonly Guid RegistrationSecret = new Guid("{74896548-9cdd-4315-8aeb-9ecd88fceb21}"); - } - - public static class TokenIssueResourceIds - { - public const string AreaName = "TokenIssue"; - public const string AreaId = "6b10046c-829d-44d2-8a1d-02f88f4ff032"; - - public const string AccessTokenResource = "AccessTokens"; - public static readonly Guid AccessToken = new Guid("{24691e90-c8bd-42c0-8aae-71b7511a797a}"); - - public const string SessionTokenResource = "SessionTokens"; - public static readonly Guid SessionToken = new Guid("{98e25729-952a-4b1f-ac89-7ca8b9803261}"); - - public const string AadUserTokenResource = "AadUserTokens"; - public static readonly Guid AadUserToken = new Guid("{4cbff9ec-7f69-4d40-a82e-cca1e8545d01}"); - - public const string AadAppTokenResource = "AadAppTokens"; - public static readonly Guid AadAppToken = new Guid("{f15de83d-4b1d-4387-90aa-e72c0ce10b3e}"); - - public const string AppSessionTokenResource = "AppSessionTokens"; - public static readonly Guid AppSessionToken = new Guid("{325f73ea-e978-4ad1-8f3a-c30b39000a17}"); - - public const string AppTokenPairResource = "AppTokenPairs"; - public static readonly Guid AppTokenPair = new Guid("{9030cb81-c1fd-4f3b-9910-c90eb559b830}"); - } - - public static class TokenTokenExpirationResourceIds - { - public const string AreaName = "TokenExpiration"; - public const string AreaId = "339c63b0-d305-4fd3-958a-22b8e0eb6fc2"; - - public const string TokenExpirationResource = "Token"; - public static readonly Guid TokenExpiration = new Guid("{e04f61f2-a03d-4aec-8b0f-6e8511fe5adc}"); - } - - public static class DelegatedAuthResourceIds - { - public const string AreaName = "DelegatedAuth"; - public const string AreaId = "A0848FA1-3593-4AEC-949C-694C73F4C4CE"; - - public const string AuthorizationResource = "Authorizations"; - public static readonly Guid Authorization = new Guid("EFBF6E0C-1150-43FD-B869-7E2B04FC0D09"); - - public const string HostAuthorizationResource = "HostAuthorization"; - public static readonly Guid HostAuthorizeId = new Guid("{7372FDD9-238C-467C-B0F2-995F4BFE0D94}"); - - public const string RegistrationResource = "Registration"; - public static readonly Guid Registration = new Guid("{909CD090-3005-480D-A1B4-220B76CB0AFE}"); - - public const string RegistrationSecretResource = "RegistrationSecret"; - public static readonly Guid RegistrationSecret = new Guid("{F37E5023-DFBE-490E-9E40-7B7FB6B67887}"); - } - - public static class TokenResourceIds - { - public const string AreaName = "Token"; - public const string AreaId = "0AD75E84-88AE-4325-84B5-EBB30910283C"; - - public const string AccessTokenResource = "AccessTokens"; - public static readonly Guid AccessToken = new Guid("{94C2BCFB-BF10-4B41-AC01-738122D6B5E0}"); - - public const string SessionTokenResource = "SessionTokens"; - public static readonly Guid SessionToken = new Guid("{ADA996BC-8C18-4193-B20C-CD41B13F5B4D}"); - - public const string AadUserTokenResource = "AadUserTokens"; - public static readonly Guid AadUserToken = new Guid("{6A8B6E50-FDA9-4AC1-9536-678C28BE2F7D}"); - - public const string AadAppTokenResource = "AadAppTokens"; - public static readonly Guid AadAppToken = new Guid("{11B3E525-35D3-4373-8985-EA72887427DB}"); - - public const string AppSessionTokenResource = "AppSessionTokens"; - public static readonly Guid AppSessionToken = new Guid("{B743B207-6DC5-457B-B1DF-B9B63D640F0B}"); - - public const string AppTokenPairResource = "AppTokenPairs"; - public static readonly Guid AppTokenPair = new Guid("{9CE3C96A-34A2-41AF-807D-205DA73F227B}"); - } - - public static class PropertyCacheResourceIds - { - public const string AreaName = "Cache"; - public const string AreaId = "0B808CEB-EF49-4C5E-9483-600A4ECF1224"; - - public const string PropertyCacheResource = "Properties"; - public static readonly Guid PropertyCache = new Guid("{656342EB-AE7D-4FF2-802F-19C6E35B0FE6}"); - } -} - -namespace GitHub.Services.TokenAdmin.Client -{ - public static class TokenAdminResourceIds - { - public const string AreaName = "TokenAdmin"; - public const string AreaId = "af68438b-ed04-4407-9eb6-f1dbae3f922e"; - - public const string PersonalAccessTokensResource = "PersonalAccessTokens"; - public static readonly Guid PersonalAccessTokensLocationId = new Guid("{af68438b-ed04-4407-9eb6-f1dbae3f922e}"); - - public const string RevocationsResource = "Revocations"; - public static readonly Guid RevocationsLocationId = new Guid("{a9c08b2c-5466-4e22-8626-1ff304ffdf0f}"); - - public const string RevocationRulesResource = "RevocationRules"; - public static readonly Guid RevocationRulesLocationId = new Guid("{ee4afb16-e7ab-4ed8-9d4b-4ef3e78f97e4}"); - } -} - -namespace GitHub.Services.Tokens.TokenAdmin.Client -{ - public static class TokenAdministrationResourceIds - { - public const string TokenAreaName = "TokenAdministration"; - public const string TokenAreaId = "95935461-9E54-44BD-B9FB-04F4DD05D640"; - - public const string TokenPersonalAccessTokensResource = "TokenPersonalAccessTokens"; - public static readonly Guid TokenPersonalAccessTokensLocationId = new Guid("{1BB7DB14-87C5-4762-BF77-A70AD34A9AB3}"); - - public const string TokenRevocationsResource = "TokenRevocations"; - public static readonly Guid TokenRevocationsLocationId = new Guid("{A2E4520B-1CC8-4526-871E-F3A8F865F221}"); - - public const string TokenListGlobalIdentities = "TokenListGlobalIdentities"; - public static readonly Guid TokenListGlobalIdentitiesId = new Guid("{30D3A12B-66C3-4669-B016-ECB0706C8D0F}"); - } -} - -namespace GitHub.Services.Identity.Client -{ - public static class PropertyCacheResourceIds - { - public const string AreaName = "Cache"; - public const string AreaId = "0B808CEB-EF49-4C5E-9483-600A4ECF1224"; - - public const string PropertyCacheResource = "Properties"; - public static readonly Guid PropertyCache = new Guid("{656342EB-AE7D-4FF2-802F-19C6E35B0FE6}"); - } -} - -namespace GitHub.Services.Security -{ - public static class LocationResourceIds - { - public const string SecurityBackingStoreArea = "SBS"; - - public const string SecurityBackingStoreNamespaceResource = "SBSNamespace"; - public static readonly Guid SecurityBackingStoreNamespace = new Guid("049929B0-79E1-4AD5-A548-9E192D5C049E"); - - public const string SecurityBackingStoreAclStoreResource = "SBSAclStore"; - public static readonly Guid SecurityBackingStoreAclStore = new Guid("D9DA18E4-274B-4DD4-B09D-B8B931AF3826"); - - public const string SecurityBackingStoreAclsResource = "SBSAcls"; - public static readonly Guid SecurityBackingStoreAcls = new Guid("3F95720D-2EF6-47CC-B5D7-733561D13EB9"); - - public const string SecurityBackingStoreAcesResource = "SBSAces"; - public static readonly Guid SecurityBackingStoreAces = new Guid("AB821A2B-F383-4C72-8274-8425ED30835D"); - - public const string SecurityBackingStoreInheritResource = "SBSInherit"; - public static readonly Guid SecurityBackingStoreInherit = new Guid("25DCFFD2-9F2A-4109-B4CC-000F8472107D"); - - public const string SecurityBackingStoreTokensResource = "SBSTokens"; - public static readonly Guid SecurityBackingStoreTokens = new Guid("466ECEAD-D7F1-447C-8BC1-52C22592B98E"); - - public const string SecurityServiceArea = "Security"; - - public const string SecurityPermissionsResource = "Permissions"; - public static readonly Guid SecurityPermissions = new Guid("DD3B8BD6-C7FC-4CBD-929A-933D9C011C9D"); - - public const string SecurityPermissionEvaluationBatchResource = "PermissionEvaluationBatch"; - public static readonly Guid SecurityPermissionEvaluationBatch = new Guid("CF1FAA59-1B63-4448-BF04-13D981A46F5D"); - - public const string SecurityAccessControlEntriesResource = "AccessControlEntries"; - public static readonly Guid SecurityAccessControlEntries = new Guid("AC08C8FF-4323-4B08-AF90-BCD018D380CE"); - - public const string SecurityAccessControlListsResource = "AccessControlLists"; - public static readonly Guid SecurityAccessControlLists = new Guid("18A2AD18-7571-46AE-BEC7-0C7DA1495885"); - - public const string SecurityNamespacesResource = "SecurityNamespaces"; - public static readonly Guid SecurityNamespaces = new Guid("CE7B9F95-FDE9-4BE8-A86D-83B366F0B87A"); - } -} - -namespace GitHub.Services.Account -{ - public static class AccountResourceIds - { - public const string RegionArea = "Region"; - - public const string AreaId = "0D55247A-1C47-4462-9B1F-5E2125590EE6"; - - public const string AccountServiceArea = "Account"; - public static readonly Guid Account = new Guid("{229A6A53-B428-4FFB-A835-E8F36B5B4B1E}"); - public const string AccountResource = "Accounts"; - - public static readonly Guid AccountUserId = new Guid("{DFA3B963-C8BB-4CAF-BCAC-5C066B3B5793}"); - public const string AccountUserResource = "Users"; - - public const string HostMappingsResource = "HostMappings"; - public static readonly Guid HostsLocationid = new Guid("{DC2B7A91-2350-487B-9192-8099F28D6576}"); - - public static readonly Guid AccountTenantId = new Guid("{C58B3989-1E17-4A18-9925-67186FE66833}"); - public const string AccountTenantResource = "Tenant"; - - public static readonly Guid AccountRegionLocationId = new Guid("642A93C7-8385-4D63-A5A5-20D044FE504F"); - public const string AccountRegionResource = "Regions"; - - public static readonly Guid AccountNameAvailabilityid = new Guid("65DD1DC5-53FE-4C67-9B4E-0EC3E2539998"); - public const string AccountNameAvailabilityResource = "Availability"; - - public static readonly Guid AccountSettingsid = new Guid("4E012DD4-F8E1-485D-9BB3-C50D83C5B71B"); - public const string AccountSettingsResource = "Settings"; - } -} - -namespace GitHub.Services.ClientNotification -{ - public static class ClientNotificationResourceIds - { - public const string AreaId = "C2845FF0-342A-4059-A831-AA7A5BF00FF0"; - public const string AreaName = "ClientNotification"; - - public const string SubscriptionsResource = "Subscriptions"; - public static readonly Guid SubscriptionsLocationid = new Guid("E037C69C-5AD1-4B26-B340-51C18035516F"); - - public const string NotificationsResource = "Notifications"; - public static readonly Guid NotificationsLocationid = new Guid("7F325780-EAD9-4C90-ACD1-2ECF621CE348"); - } -} - -namespace GitHub.Services.Licensing -{ - public static class LicensingResourceIds - { - public const string AreaId = "C73A23A1-59BB-458C-8CE3-02C83215E015"; - public const string AreaName = "Licensing"; - - public const string CertificateResource = "Certificate"; - public static readonly Guid CertificateLocationid = new Guid("2E0DBCE7-A327-4BC0-A291-056139393F6D"); - - public const string ClientRightsResource = "ClientRights"; - public static readonly Guid ClientRightsLocationid = new Guid("643C72DA-EAEE-4163-9F07-D748EF5C2A0C"); - - public const string MsdnResource = "Msdn"; - public const string MsdnPresenceLocationIdString = "69522C3F-EECC-48D0-B333-F69FFB8FA6CC"; - public static readonly Guid MsdnPresenceLocationId = new Guid(MsdnPresenceLocationIdString); - public const string MsdnEntitlementsLocationIdString = "1cc6137e-12d5-4d44-a4f2-765006c9e85d"; - public static readonly Guid MsdnEntitlementsLocationId = new Guid(MsdnEntitlementsLocationIdString); - - public const string ExtensionRightsResource = "ExtensionRights"; - public static readonly Guid ExtensionRightsLocationId = new Guid("5F1DBE21-F748-47C7-B5FD-3770C8BC2C08"); - - public const string ExtensionLicenseResource = "ExtensionRegistration"; - public static readonly Guid ExtensionLicenseLocationId = new Guid("004A420A-7BEF-4B7F-8A50-22975D2067CC"); - - public const string UsageRightsResource = "UsageRights"; - public static readonly Guid UsageRightsLocationid = new Guid("D09AC573-58FE-4948-AF97-793DB40A7E16"); - - public const string ServiceRightsResource = "ServiceRights"; - public static readonly Guid ServiceRightsLocationid = new Guid("78ED2F48-D449-412D-8772-E4E97317B7BE"); - - public const string UsageResource = "Usage"; - public static readonly Guid UsageLocationid = new Guid("D3266B87-D395-4E91-97A5-0215B81A0B7D"); - - public const string EntitlementsResource = "Entitlements"; - public const string EntitlementsBatchResource = "EntitlementsBatch"; - public const string ExtensionsAssignedToAccountResource = "AccountAssignedExtensions"; - public const string ExtensionsAssignedToAccountLocationIdString = "01BCE8D3-C130-480F-A332-474AE3F6662E"; - public static readonly Guid ExtensionsAssignedToAccountLocationId = new Guid(ExtensionsAssignedToAccountLocationIdString); - - public const string EntitlementsLocationIdString = "EA37BE6F-8CD7-48DD-983D-2B72D6E3DA0F"; - public static readonly Guid EntitlementsLocationid = new Guid(EntitlementsLocationIdString); - public const string UserEntitlementsLocationIdString = "6490E566-B299-49A7-A4E4-28749752581F"; - public static readonly Guid UserEntitlementsLocationId = new Guid(UserEntitlementsLocationIdString); - - public const string UserEntitlementsBatchLocationIdString = "CC3A0130-78AD-4A00-B1CA-49BEF42F4656"; - public static readonly Guid UserEntitlementsBatchLocationId = new Guid(UserEntitlementsBatchLocationIdString); - - public const string CurrentUserEntitlementsLocationIdString = "C01E9FD5-0D8C-4D5E-9A68-734BD8DA6A38"; - public static readonly Guid CurrentUserEntitlementsLocationId = new Guid(CurrentUserEntitlementsLocationIdString); - public const string AssignAvailableEntitlementsLocationIdString = "C01E9FD5-0D8C-4D5E-9A68-734BD8DA6A38"; - public static readonly Guid AssignAvailableEntitlementsLocationId = new Guid(AssignAvailableEntitlementsLocationIdString); - - public const string ExtensionEntitlementsResource = "ExtensionEntitlements"; - public const string UserExtensionEntitlementsLocationIdString = "8CEC75EA-044F-4245-AB0D-A82DAFCC85EA"; - public static readonly Guid UserExtensionEntitlementsLocationId = new Guid(UserExtensionEntitlementsLocationIdString); - public const string ExtensionEntitlementsLocationIdString = "5434F182-7F32-4135-8326-9340D887C08A"; - public static readonly Guid ExtensionEntitlementsLocationId = new Guid(ExtensionEntitlementsLocationIdString); - - public const string TransferIdentitiesExtensionsResource = "TransferIdentitiesExtensions"; - public const string TransferIdentitiesExtensionsLocationIdString = "DA46FE26-DBB6-41D9-9D6B-86BF47E4E444"; - public static readonly Guid TransferIdentitiesExtensionsLocationId = - new Guid(TransferIdentitiesExtensionsLocationIdString); - - public const string ExtensionEntitlementsBatchResource = "ExtensionEntitlementsBatch"; - public const string UsersBatchExtensionEntitlementsLocationIdString = "1D42DDC2-3E7D-4DAA-A0EB-E12C1DBD7C72"; - public static readonly Guid UsersBatchExtensionEntitlementsLocationId = new Guid(UsersBatchExtensionEntitlementsLocationIdString); - - public const string LicensingRightsResource = "LicensingRights"; - public const string LicensingRightsLocationIdString = "8671B016-FA74-4C88-B693-83BBB88C2264"; - public static readonly Guid LicensingRightsLocationId = new Guid(LicensingRightsLocationIdString); - - public const string LicensingSettingsResource = "Settings"; - public const string LicensingSettingsLocationIdString = "6BA7740F-A387-4D74-B71A-969A9F2B49FB"; - public static readonly Guid LicensingSettingsLocationId = new Guid(LicensingSettingsLocationIdString); - } - - public static class LicensingResourceVersions - { - public const int AccountRightsResourcePreviewVersion = 1; - public const int CertificateResourcePreviewVersion = 1; - public const int ClientRightsResourcePreviewVersion = 1; - public const int UsageRightsResourcePreviewVersion = 1; - public const int ServiceRightsResourceRtmVersion = 1; - public const int AccountUsageResourceRtmVersion = 1; - public const int EntitlementResourceRtmVersion = 1; - public const int EntitlementsBatchResourcePreviewVersion = 1; - public const int LicensingRightsResourceRtmVersion = 1; - public const int MsdnResourceRtmVersion = 1; - public const int ExtensionRightsResourceRtmVersion = 1; - public const int ExtensionLicenseResourceRtmVersion = 1; - public const int ExtensionEntitlementsResourceRtmVersion = 1; - public const int ExtensionEntitlementsBatchResourceRtmVersion = 1; - public const int ExtensionEntitlementsBatch2ResourceRtmVersion = 2; - public const int TransferExtensionsForIdentitiesRtmVersion = 1; - public const int LicensingSettingsResourceRtmVersion = 1; - } -} - -namespace GitHub.Services.GroupLicensingRule -{ - public static class LicensingRuleResourceIds - { - public const string AreaId = "4F9A6C65-A750-4DE3-96D3-E4BCCF3A39B0"; - public const string AreaName = "LicensingRule"; - - public static class GroupLicensingRules - { - public const string GroupLicensingRulesResourceName = "GroupLicensingRules"; - public const string GroupLicensingRuleLocationIdString = "1DAE9AF4-C85D-411B-B0C1-A46AFAEA1986"; - public static readonly Guid GroupLicensingRuleLocationId = new Guid(GroupLicensingRuleLocationIdString); - } - - public static class GroupLicensingRulesLookup - { - public const string GroupLicensingRulesLookupResourceName = "GroupLicensingRulesLookup"; - public const string GroupLicensingRulesLookupResourceLocationIdString = "6282B958-792B-4F26-B5C8-6D035E02289F"; - public static readonly Guid GroupLicensingRulesLookupResourceLocationId = new Guid(GroupLicensingRulesLookupResourceLocationIdString); - } - - public static class GroupLicensingRulesUserApplication - { - public const string GroupLicensingRulesUserApplicationResourceName = "GroupLicensingRulesUserApplication"; - public const string GroupLicensingRulesUserApplicationResourceLocationIdString = "74A9DE62-9AFC-4A60-A6D9-F7C65E028619"; - public static readonly Guid GroupLicensingRulesUserApplicationResourceLocationId = new Guid(GroupLicensingRulesUserApplicationResourceLocationIdString); - } - - public static class GroupLicensingRulesApplication - { - public const string GroupLicensingRulesApplicationResourceName = "GroupLicensingRulesApplication"; - public const string GroupLicensingRulesApplicationResourceLocationIdString = "14602853-288e-4711-a613-c3f27ffce285"; - public static readonly Guid GroupLicensingRulesApplicationResourceLocationId = new Guid(GroupLicensingRulesApplicationResourceLocationIdString); - } - public static class GroupLicensingRulesApplicationStatus - { - public const string GroupLicensingRulesApplicationStatusResourceName = "GroupLicensingRulesApplicationStatus"; - public const string GroupLicensingRulesApplicationStatusResourceLocationIdString = "8953c613-d07f-43d3-a7bd-e9b66f960839"; - public static readonly Guid GroupLicensingRulesApplicationStatusResourceLocationId = new Guid(GroupLicensingRulesApplicationStatusResourceLocationIdString); - } - - public static class GroupLicensingRulesEvaluationLog - { - public const string GroupLicensingRulesEvaluationLogResourceName = "GroupLicensingRulesEvaluationLog"; - public const string GroupLicensingRulesEvaluationLogResourceLocationIdString = "C3C87024-5143-4631-94CE-CB2338B04BBC"; - public static readonly Guid GroupLicensingRulesEvaluationLogResourceLocationId = new Guid(GroupLicensingRulesEvaluationLogResourceLocationIdString); - } - } - - public static class GroupLicensingResourceVersions - { - public const int GroupLicensingRulesResourceVersion = 1; - public const int GroupLicensingRulesLookupResourceVersion = 1; - } -} - -namespace GitHub.Services.Invitation -{ - public static class InvitationResourceVersions - { - public const int InvitationAPIVersion = 1; - } - - public static class InvitationResourceIds - { - public const string AreaId = "287A6D53-7DC8-4618-8D57-6945B848A4AD"; - public const string AreaName = "Invitation"; - - public const string InvitationsResourceName = "Invitations"; - public const string InvitationsLocationIdString = "BC7CA053-E204-435B-A143-6240BA8A93BF"; - public static readonly Guid InvitationsLocationId = new Guid(InvitationsLocationIdString); - } -} - -namespace GitHub.Services.Compliance -{ - public static class ComplianceResourceVersions - { - public const int AccountRightsResourceVersion = 1; - public const int ConfigurationResourceVersion = 1; - public const int ValidationResourceVersion = 1; - } - - public static class ComplianceResourceIds - { - public const string AreaId = "7E7BAADD-B7D6-46A0-9CE5-A6F95DDA0E62"; - public const string AreaName = "Compliance"; - - public const string AccountRightsResource = "AccountRights"; - public static readonly Guid AccountRightsLocationId = new Guid("5FCEC4F4-491A-473D-B2F9-205977E66F01"); - - public const string ConfigurationResource = "Configuration"; - public static readonly Guid ConfigurationLocationId = new Guid("64076419-AC67-4F85-B709-B8C28D5B4F1D"); - - public const string ValidationResource = "Validation"; - public static readonly Guid ValidationLocationId = new Guid("A9994840-76C7-4C5B-97CF-2B353AD0E01C"); - } -} - -namespace GitHub.Services.Profile -{ - public static class ProfileResourceIds - { - public const string AreaId = "8CCFEF3D-2B87-4E99-8CCB-66E343D2DAA8"; - public const string AreaName = "Profile"; - public static readonly Guid AreaIdGuid = new Guid(AreaId); - - public const string ProfileHttpClientV2AreaId = "31C4AD39-B95A-4AC2-87FE-D8CE878D32A8"; - - public const string ProfileResource = "Profiles"; - public static readonly Guid ProfileLocationid = new Guid("F83735DC-483F-4238-A291-D45F6080A9AF"); - - public const string UserDefaultsResource = "UserDefaults"; - public static readonly Guid UserDefaultsLocationId = new Guid("B583A356-1DA7-4237-9F4C-1DEB2EDBC7E8"); - - public const string AttributeResource = "Attributes"; - public static readonly Guid AttributeLocationid = new Guid("EF743E8C-9A94-4E55-9392-CCFE55CFAE55"); - public static readonly Guid AttributeLocationId2 = new Guid("1392B6AC-D511-492E-AF5B-2263E5545A5D"); - - public const string AvatarResource = "Avatar"; - public static readonly Guid AvatarLocationid = new Guid("855C48A5-ED0C-4762-A640-3D212B2244B8"); - public static readonly Guid Avatar2LocationId = new Guid("67436615-B382-462A-B659-5367A492FB3C"); - - public const string DisplayNameResource = "DisplayName"; - public static readonly Guid DisplayNameLocationid = new Guid("5D969C0D-9A4A-45AB-A4EA-0C902AF8D39C"); - - public const string PublicAliasResource = "PublicAlias"; - public static readonly Guid PublicAliasLocationid = new Guid("B63E58B3-B830-40EA-A382-C198E6E9BB2C"); - - public const string EmailAddressResource = "EmailAddress"; - public static readonly Guid EmailAddressLocationid = new Guid("F47E1E09-08B3-436F-A541-495B3088635A"); - - public const string CountryResource = "Country"; - public static readonly Guid CountryLocationid = new Guid("C96428D6-5805-48A4-B4FD-DC6F1C39BE92"); - - public const string TermsOfServiceResource = "TermsOfService"; - public static readonly Guid TermsOfServiceLocationid = new Guid("E3411396-DA5F-4757-AA9E-521B48EEF625"); - - public const string PreferredEmailConfirmationResource = "PreferredEmailConfirmation"; - public static readonly Guid PreferredEmailConfirmationLocationid = new Guid("238437E4-73B9-4BB9-B467-DE4E5DC0FC78"); - - public const string CountriesResource = "Countries"; - public static readonly Guid CountriesLocationid = new Guid("775F46ED-26B3-4A6F-B7B1-01CF195ACDD0"); - - public const string SupportedLcidsResource = "SupportedLcids"; - public static readonly Guid SupportedLcidsLocationId = new Guid("D5BD1AA6-C269-4BCD-AD32-75FA17475584"); - - public const string RegionsResource = "Regions"; - public static readonly Guid RegionsLocationId = new Guid("92D8D1C9-26B8-4774-A929-D640A73DA524"); - - public const string LocationsResource = "Locations"; - public static readonly Guid LocationsLocationid = new Guid("EEA7DE6F-00A4-42F3-8A29-1BA615691880"); - - public const string LatestTosResource = "LatestTermsofService"; - public static readonly Guid LatestTosLocationid = new Guid("A4A9FB9D-FD32-4F9A-95A8-4B05FAF8C661"); - - public const string SettingsResource = "Settings"; - public static readonly Guid SettingsLocationid = new Guid("5081DFF5-947B-4CE6-9BBE-6C7C094DDCE0"); - - public const string GeoRegionResource = "GeoRegion"; - public static readonly Guid GeoRegionLocationid = new Guid("3BCDA9C0-3078-48A5-A1E0-83BD05931AD0"); - - public const string MigratingProfilesResource = "MigratingProfiles"; - public static readonly Guid MigratingProfilesLocationid = new Guid("397E8E6D-00BB-405F-90F4-02B38B2AC8F6"); - } - - public static class ProfileResourceVersions - { - public const int GenericResourcePreviewVersion = 1; - - public const int ProfileResourcePreviewVersion = 1; - public const int ProfileResourceRcVersion = 2; - public const int ProfileResourceRtmVersion = 3; - - public const int AttributeResourcePreviewVersion = 1; - public const int AttributeResourceRcVersion = 2; - } -} - namespace GitHub.Services.FileContainer { public static class FileContainerResourceIds @@ -739,285 +16,6 @@ namespace GitHub.Services.FileContainer } } -namespace GitHub.Services.WebApi -{ - public static class CvsFileDownloadResourceIds - { - public const string AreaName = "CvsFileDownload"; - - public const string LocationIdString = "0CF03C5A-D16D-4297-BFEB-F38A56D86670"; - public static readonly Guid LocationId = new Guid(LocationIdString); - - public const string Resource = "CvsFileDownload"; - } -} - -namespace GitHub.Services.Commerce -{ - public static class CommerceResourceIds - { - public const string AreaId = "365D9DCD-4492-4AE3-B5BA-AD0FF4AB74B3"; - public const string AreaName = "Commerce"; - - public const string MeterResource = "Meters"; - public static readonly Guid MeterLocationid = new Guid("AFB09D56-7740-4EB0-867F-792021FAB7C9"); - - public const string CommercePackageResource = "CommercePackage"; - public static readonly Guid CommercePackageLocationId = new Guid("E8135F49-A1DC-4135-80F4-120BBFC2ACF0"); - - public const string UsageEventResource = "UsageEvents"; - public static readonly Guid UsageEventLocationid = new Guid("EED7D28A-12A9-47ED-9A85-91A76C63E74B"); - - public const string ReportingEventResource = "ReportingEvents"; - public static readonly Guid ReportingEventLocationId = new Guid("E3296A33-647F-4A09-85C6-64B9259DADB8"); - - public const string SubscriptionResource = "Subscription"; - public static readonly Guid SubscriptionLocationId = new Guid("64485509-D692-4B70-B440-D02B3B809820"); - - public const string RegionsResource = "Regions"; - public static readonly Guid RegionsLocationId = new Guid("9527c79d-9f3e-465d-8178-069106c39457"); - - public const string OfferSubscriptionResource = "OfferSubscription"; - public static readonly Guid OfferSubscriptionResourceId = new Guid("E8950CE5-80BC-421F-B093-033C18FD3D79"); - - public const string OfferMeterResource = "OfferMeter"; - public static readonly Guid OfferMeterLocationId = new Guid("8B79E1FB-777B-4D0A-9D2E-6A4B2B8761B9"); - - public const string OfferMeterPriceResource = "OfferMeterPrice"; - public static readonly Guid OfferMeterPriceLocationId = new Guid("1C67C343-2269-4608-BC53-FE62DAA8E32B"); - - public const string ConnectedServerResource = "ConnectedServer"; - public static readonly Guid ConnectedServerLocationId = new Guid("C9928A7A-8102-4061-BDCE-B090068C0D2B"); - - public const string PurchaseRequestResource = "PurchaseRequest"; - public static readonly Guid PurchaseRequestLocationId = new Guid("A349B796-BDDB-459E-8921-E1967672BE86"); - - public const string ResourceMigrationResource = "ResourceMigration"; - public static readonly Guid ResourceMigrationLocationId = new Guid("2F11E604-83B2-4596-B3C6-242BAB102DA3"); - - public const string CommerceHostHelperResource = "CommerceHostHelperResource"; - public static readonly Guid CommerceHostHelperLocationId = new Guid("8B4C702A-7449-4FEB-9B23-ADD4288DDA1A"); - } - - public static class CommerceResourceVersions - { - public const int MeterV1Resources = 1; - - public const int MeterV2Resources = 2; - - public const int BillingV1Resources = 1; - - public const int OfferMeterV1Resources = 1; - - public const int OfferMeterPriceV1Resources = 1; - - public const int CommercePackageV1Resources = 1; - - public const int ReportingV1Resources = 1; - - public const int PurchaseRequestV1Resources = 1; - - public const int ResourceMigrationV1Resources = 1; - - public const int InfrastructureOrganizationV1Resources = 1; - } - - public static class CsmResourceIds - { - public const string AreaId = "B3705FD5-DC18-47FC-BB2F-7B0F19A70822"; - public const string AreaName = "Csm"; - - public const string ExtensionResourceResource = "ExtensionResource"; - public static readonly Guid ExtensionResourceLocationId = new Guid("9cb405cb-4a72-4a50-ab6d-be1da1726c33"); - - public const string ExtensionResourceGroupResource = "ExtensionResourceGroup"; - public static readonly Guid ExtensionResourceGroupLocationId = new Guid("a509d9a8-d23f-4e0f-a69f-ad52b248943b"); - - public const string AccountResourceResource = "AccountResource"; - public static readonly Guid AccountResourceResourceLocationId = new Guid("5745408e-6e9e-49c7-92bf-62932c8df69d"); - - public const string AccountResourceGroupResource = "AccountResourceGroup"; - public static readonly Guid AccountResourceGroupLocationId = new Guid("73d8b171-a2a0-4ac6-ba0b-ef762098e5ec"); - - public const string SubscriptionResourceGroupResource = "SubscriptionResourceGroup"; - public static readonly Guid SubscriptionResourceGroupLocationId = new Guid("f34be62f-f215-4bda-8b57-9e8a7a5fd66a"); - - public const string AccountResourceOperationsResource = "AccountResourceOperations"; - public static readonly Guid AccountResourceOperationsLocationId = new Guid("454d976b-812e-4947-bc4e-c2c23160317e"); - - public const string NameAvailabilityResource = "NameAvailability"; - public static readonly Guid NameAvailabilityResourceLocationId = new Guid("031d6b9b-a0d4-4b46-97c5-9ddaca1aa5cd"); - - public const string SubscriptionEventsResource = "SubscriptionEvents"; - public static readonly Guid SubscriptionEventsLocationId = new Guid("97bc4c4d-ce2e-4ca3-87cc-2bd07aeee500"); - - public const string ResourceGroupsResourceName = "ResourceGroups"; - public static readonly Guid ResourceGroupsResourceLocationId = new Guid("9e0fa51b-9d61-4899-a5a1-e1f0f5e75bc0"); - } - - public static class CommerceServiceResourceIds - { - // Offer Meter Area - public const string OfferMeterAreaId = "000080C1-AA68-4FCE-BBC5-C68D94BFF8BE"; - public const string OfferMeterAreaName = "OfferMeter"; - - public const string OfferMeterLocationString = "81E37548-A9E0-49F9-8905-650A7260A440"; - public static readonly Guid OfferMeterLocationId = new Guid(OfferMeterLocationString); - public const string OfferMeterResource = "OfferMeter"; - - public const string OfferMeterPriceResource = "OfferMeterPrice"; - public const string OfferMeterPriceLocationString = "D7197E00-DDDF-4029-9F9B-21B935A6CF9F"; - public static readonly Guid OfferMeterPriceLocationId = new Guid(OfferMeterPriceLocationString); - - // Meters Area - public const string MeterAreaId = "4C19F9C8-67BD-4C18-800B-55DC62C3017F"; - public const string MetersAreaName = "Meters"; - - public const string MeterResource = "Meters"; - public const string MeterLocationString = "4BD6E06B-1EDF-41A6-9BAF-D15B874DC539"; - public static readonly Guid MeterLocationid = new Guid(MeterLocationString); - - // Commerce Package Area - public const string CommercePackageAreaName = "Package"; - public const string CommercePackageAreaId = "45FB9450-A28D-476D-9B0F-FB4AEDDDFF73"; - - public const string CommercePackageResource = "CommercePackage"; - public const string CommercePackageLocationString = "A5E80D85-9718-44E0-BBED-461109268DBC"; - public static readonly Guid CommercePackageLocationId = new Guid(CommercePackageLocationString); - - // Usage Events Area - public const string UsageEventsAreaName = "UsageEvents"; - public const string UsageEventsAreaId = "3B16A4DB-B853-4C64-AA16-72138F5BB750"; - - public const string UsageEventsResource = "UsageEvents"; - public const string UsageEventsLocationString = "78741F74-E4F0-41B2-BB93-28C886443027"; - public static readonly Guid UsageEventLocationid = new Guid(UsageEventsLocationString); - - // Reporting Event Area - public const string ReportingEventsAreaName = "ReportingEvents"; - public const string ReportingEventsAreaId = "C890B7C4-5CF6-4280-91AC-331E439B8119"; - - public const string ReportingEventsResource = "ReportingEvents"; - public const string ReportingEventsLocationString = "D0BA838F-9253-46C5-ABB2-0ACF551C23D7"; - public static readonly Guid ReportingEventsLocationId = new Guid(ReportingEventsLocationString); - - // Subscription Area - public const string SubscriptionAreaId = "AC02550F-721A-4913-8EA5-CADAE535B03F"; - public const string SubscriptionAreaName = "Subscription"; - - public const string SubscriptionResource = "Subscription"; - public const string SubscriptionLocationString = "94DE86A2-03E3-42DB-A2E8-1A82BF13A262"; - public static readonly Guid SubscriptionLocationId = new Guid(SubscriptionLocationString); - - public const string AccountDetailsResource = "AccountDetails"; - public const string AccountDetailsLocationString = "0288F4E6-21D3-4529-AC5F-1719F99A4396"; - public static readonly Guid AccountDetailsLocationId = new Guid(AccountDetailsLocationString); - - // Region Area - public const string RegionsAreaName = "Regions"; - public const string RegionsAreaId = "A6ACEE79-C91A-47BA-87DF-AF36581833B6"; - - public const string RegionsResource = "Regions"; - public const string RegionsLocationString = "AAE8A531-9968-456F-9EF1-FE0ECF4724E8"; - public static readonly Guid RegionsLocationId = new Guid(RegionsLocationString); - - // Offer Subscription Area - public const string OfferSubscriptionAreaName = "OfferSubscription"; - public const string OfferSubscriptionAreaId = "5D4A2F52-5A08-41FB-8CCA-768ADD070E18"; - - public const string OfferSubscriptionResource = "OfferSubscription"; - public const string OfferSubscriptionLocationString = "7C13D166-01C5-4CCD-8A75-E5AD6AB3B0A6"; - public static readonly Guid OfferSubscriptionResourceId = new Guid(OfferSubscriptionLocationString); - - // Connected Server Area - public const string ConnectedServerAreaName = "ConnectedServer"; - public const string ConnectedServerAreaId = "05A2B228-317C-4886-9FE9-828F9EA3815A"; - - public const string ConnectedServerResource = "ConnectedServer"; - public const string ConnectedServerLocationString = "AB6E0E2F-A3CA-4478-BAFC-8E7AD022BE01"; - public static readonly Guid ConnectedServerLocationId = new Guid(ConnectedServerLocationString); - - // Purchase Request Area - public const string PurchaseRequestAreaName = "PurchaseRequest"; - public const string PurchaseRequestAreaId = "9D439667-F8CF-4991-89A9-95CA6A763327"; - - public const string PurchaseRequestResource = "PurchaseRequest"; - public const string PurchaseRequestLocationString = "6F905B2D-292A-4D30-B38A-2D254EAB06B7"; - public static readonly Guid PurchaseRequestLocationId = new Guid(PurchaseRequestLocationString); - - // Resource Migration Area - public const string ResourceMigrationAreaName = "ResourceMigration"; - public const string ResourceMigrationAreaId = "FFCFC36A-0BE8-412A-A2BB-93C2ABD4048B"; - - public const string ResourceMigrationResource = "ResourceMigration"; - public const string ResourceMigrationLocationString = "00432895-B3F6-488C-BA71-792FA5E07383"; - public static readonly Guid ResourceMigrationLocationId = new Guid(ResourceMigrationLocationString); - } - - public static class CsmResourceProviderResourceIds - { - public const string AreaId = "2900E97E-7BBD-4D87-95EE-BE54611B6184"; - public const string AreaName = "CsmResourceProvider"; - - public const string ExtensionResourceResource = "VssExtensionResource"; - public static readonly Guid ExtensionResourceLocationId = new Guid("8DF1CB68-197E-4BAF-8CE2-C96021879971"); - - public const string ExtensionResourceGroupResource = "VssExtensionResourceGroup"; - public static readonly Guid ExtensionResourceGroupLocationId = new Guid("E14787AB-FBD5-4064-A75D-0603C9ED66A8"); - - public const string AccountResourceResource = "VssAccountResource"; - public static readonly Guid AccountResourceResourceLocationId = new Guid("58FA3A85-AF20-408D-B46D-6D369408E3DA"); - - public const string AccountResourceGroupResource = "VssAccountResourceGroup"; - public static readonly Guid AccountResourceGroupLocationId = new Guid("955956A7-FBEB-48E6-9D78-C60F3F84BAE9"); - - public const string SubscriptionResourceGroupResource = "VssSubscriptionResourceGroup"; - public static readonly Guid SubscriptionResourceGroupLocationId = new Guid("8A066194-3817-4E76-9BBC-2A1446FA0FC5"); - - public const string AccountResourceOperationsResource = "VssAccountResourceOperations"; - public static readonly Guid AccountResourceOperationsLocationId = new Guid("14917175-ECBE-453B-B436-50430219EBA9"); - - public const string NameAvailabilityResource = "VssNameAvailability"; - public static readonly Guid NameAvailabilityResourceLocationId = new Guid("7DBAE6E1-993E-4AC9-B20D-6A39EEE4028B"); - - public const string SubscriptionEventsResource = "VssSubscriptionEvents"; - public static readonly Guid SubscriptionEventsLocationId = new Guid("A7F5BE2F-9AF8-4CC2-863F-D07377B2C079"); - - public const string ResourceGroupsResource = "VssResourceGroups"; - public static readonly Guid ResourceGroupsResourceLocationId = new Guid("8D9245EE-19A2-45B2-BE3E-03234122298E"); - } -} - -namespace GitHub.Services.Health -{ - public static class HealthResourceIds - { - public const string HealthArea = "Health"; - public const string HealthResource = "Health"; - public static readonly Guid HealthLocationId = new Guid("30964BA7-2A11-4792-B7BA-DF191DBCC3BB"); - } -} - -namespace GitHub.Services.ActivityStatistic -{ - public static class ActivityStatisticIds - { - public const string ActivityStatisticArea = "Stats"; - public const string ActivityStatisticResource = "Activities"; - public static readonly Guid ActivityStatisticId = new Guid("5F4C431A-4D8F-442D-96E7-1E7522E6EABD"); - } -} - -namespace GitHub.Services.ContentSecurityPolicy -{ - public static class ContentSecurityPolicyResourceIds - { - public const string CspReportArea = "CspReport"; - public const string CspReportResource = "CspReport"; - public static readonly Guid CspLocationId = new Guid("FA48A6B6-C4A9-42B4-AFE7-2640F68F99B6"); - } -} - namespace GitHub.Services.Location { [GenerateAllConstants] @@ -1042,470 +40,4 @@ namespace GitHub.Services.Location public static readonly Guid SpsServiceDefinition = new Guid("{DF5F298A-4E06-4815-A13E-6CE90A37EFA4}"); } -} - -namespace GitHub.Services.Notification -{ - public static class PersistedNotificationResourceIds - { - public const string AreaId = "BA8495F8-E9EE-4A9E-9CBE-142897543FE9"; - public const string AreaName = "PersistedNotification"; - - public static readonly Guid NotificationsId = new Guid("E889FFCE-9F0A-4C6C-B749-7FB1ECFA6950"); - public const string NotificationsResource = "Notifications"; - - public static readonly Guid RecipientMetadataId = new Guid("1AAFF2D2-E2F9-4784-9F93-412A9F2EFD86"); - public const string RecipientMetadataResource = "RecipientMetadata"; - } - - public static class PersistedNotificationResourceVersions - { - public const int NotificationsResourcePreviewVersion = 1; - public const int RecipientMetadataPreviewVersion = 1; - } -} - -namespace GitHub.Services.Operations -{ - [GenerateAllConstants] - public static class OperationsResourceIds - { - public const string AreaName = "operations"; - public const string OperationsResource = "operations"; - public const string OperationsRouteName = "Operations"; - public const string OperationsPluginRouteName = "OperationsPlugin"; - public const string OperationsApi = "OperationsApi"; - public const string TagOperationsLocationId = "9A1B74B4-2CA8-4A9F-8470-C2F2E6FDC949"; - public static readonly Guid OperationsLocationId = new Guid(TagOperationsLocationId); - public const string TagOperationsPluginLocationId = "7F82DF6D-7D09-46C1-A015-643B556B3A1E"; - public static readonly Guid OperationsPluginLocationId = new Guid(TagOperationsPluginLocationId); - } -} - -namespace GitHub.Services.Directories.DirectoryService -{ - public static class DirectoryResourceIds - { - public const string DirectoryServiceArea = "Directory"; - public const string DirectoryService = "2B98ABE4-FAE0-4B7F-8562-7141C309B9EE"; - - public const string MembersResource = "Members"; - public static readonly Guid Members = Guid.Parse("{89526A2C-E9E3-1F40-A3FB-54D16BDA15B0}"); - public static readonly Guid MemberStatusLocationId = Guid.Parse("{714914b2-ad3f-4933-bf2e-fc3cabb37696}"); - } -} - -namespace GitHub.Services.FeatureAvailability -{ - [GenerateAllConstants] - public static class FeatureAvailabilityResourceIds - { - public const string AreaId = "C8E5AF97-4B95-4E73-9E7F-69A06507967C"; - public const string FeatureAvailabilityAreaName = "FeatureAvailability"; - public static readonly Guid FeatureFlagsLocationId = Guid.Parse("{3E2B80F8-9E6F-441E-8393-005610692D9C}"); - } -} - -namespace GitHub.Services.IdentityPicker -{ - //Common identity picker in the framework - [GenerateAllConstants] - public static class CommonIdentityPickerResourceIds - { - public const string ServiceArea = "IdentityPicker"; - - public const string IdentitiesResource = "Identities"; - - public static readonly Guid IdentitiesLocationId = new Guid("4102F006-0B23-4B26-BB1B-B661605E6B33"); - public static readonly Guid IdentityAvatarLocationId = new Guid("4D9B6936-E96A-4A42-8C3B-81E8337CD010"); - public static readonly Guid IdentityFeatureMruLocationId = new Guid("839E4258-F559-421B-A38E-B6E691967AB3"); - public static readonly Guid IdentityConnectionsLocationId = new Guid("C01AF8FD-2A61-4811-A7A3-B85BCEC080AF"); - } -} - -namespace GitHub.Services.Settings -{ - [GenerateAllConstants] - public static class SettingsApiResourceIds - { - public const string SettingsAreaName = "Settings"; - - public const string SettingEntriesResource = "Entries"; - public const string SettingEntriesLocationIdString = "CD006711-163D-4CD4-A597-B05BAD2556FF"; - public static readonly Guid SettingEntriesLocationId = new Guid(SettingEntriesLocationIdString); - public const string NamedScopeSettingEntriesLocationIdString = "4CBAAFAF-E8AF-4570-98D1-79EE99C56327"; - public static readonly Guid NamedScopeSettingEntriesLocationId = new Guid(NamedScopeSettingEntriesLocationIdString); - } -} - -namespace GitHub.Services.WebPlatform -{ - [GenerateAllConstants] - public static class AuthenticationResourceIds - { - public const string AreaId = "A084B81B-0F23-4136-BAEA-98E07F3C7446"; - public const string AuthenticationAreaName = "WebPlatformAuth"; - public static readonly Guid AuthenticationLocationId = Guid.Parse("{11420B6B-3324-490A-848D-B8AAFDB906BA}"); - public const string SessionTokenResource = "SessionToken"; - } - - [GenerateAllConstants] - public static class CustomerIntelligenceResourceIds - { - public const string AreaId = "40132BEE-F5F3-4F39-847F-80CC44AD9ADD"; - public const string CustomerIntelligenceAreaName = "CustomerIntelligence"; - public static readonly Guid EventsLocationId = Guid.Parse("{B5CC35C2-FF2B-491D-A085-24B6E9F396FD}"); - } - - public static class ContributionResourceIds - { - public const string AreaId = "39675476-C858-48A1-A5CD-80ED65E86532"; - public const string AreaName = "Contribution"; - public const string HierarchyLocationIdString = "8EC9F10C-AB9F-4618-8817-48F3125DDE6A"; - public static readonly Guid HierarchyLocationId = Guid.Parse(HierarchyLocationIdString); - public const string HierarchyResource = "Hierarchy"; - public const string HierarchyQueryLocationIdString = "3353E165-A11E-43AA-9D88-14F2BB09B6D9"; - public static readonly Guid HierarchyQueryLocationId = Guid.Parse(HierarchyQueryLocationIdString); - public const string HierarchyQueryResource = "HierarchyQuery"; - } - - [GenerateAllConstants] - public static class ClientTraceResourceIds - { - public const string AreaId = "054EEB0E-108E-47DC-848A-7074B14774A9"; - public const string ClientTraceAreaName = "ClientTrace"; - public static readonly Guid EventsLocationId = Guid.Parse("{06BCC74A-1491-4EB8-A0EB-704778F9D041}"); - public const string ClientTraceEventsResource = "Events"; - } -} - -namespace GitHub.Services.Zeus -{ - [GenerateAllConstants] - public static class BlobCopyLocationIds - { - public const string ResourceString = "{8907fe1c-346a-455b-9ab9-dde883687231}"; - public static readonly Guid ResourceId = new Guid(ResourceString); - public const string ResouceName = "BlobCopyRequest"; - public const string AreaName = "BlobCopyRequest"; - } - - [GenerateAllConstants] - public static class DatabaseMigrationLocationIds - { - public const string ResourceString = "{D56223DF-8CCD-45C9-89B4-EDDF69240000}"; - public static readonly Guid ResourceId = new Guid(ResourceString); - public const string ResouceName = "DatabaseMigration"; - public const string AreaName = "DatabaseMigration"; - } -} - -namespace GitHub.Services.Identity.Mru -{ - [GenerateAllConstants] - public static class IdentityMruResourceIds - { - public const string AreaId = "FC3682BE-3D6C-427A-87C8-E527B16A1D05"; - public const string AreaName = "Identity"; - - public static readonly Guid MruIdentitiesLocationId = new Guid("15D952A1-BB4E-436C-88CA-CFE1E9FF3331"); - public const string MruIdentitiesResource = "MruIdentities"; - } -} - -namespace GitHub.Services.Servicing -{ - public static class ServicingResourceIds - { - public const string AreaName = "Servicing"; - - public static readonly Guid JobsLocationId = new Guid("807F536E-0C6D-46D9-B856-4D5F3C27BEF5"); - public static readonly Guid LogsLocationId = new Guid("B46254F3-9523-4EF8-B69E-FD6EED5D0BB8"); - public static readonly Guid ServiceLevelLocationId = new Guid("3C4BFE05-AEB6-45F8-93A6-929468401657"); - - public const string JobsResourceName = "Jobs"; - public const string LogsResourceName = "Logs"; - public const string ServiceLevelResource = "ServiceLevel"; - } -} - -namespace GitHub.Services.Auditing -{ - public static class AuditingResourceIds - { - public const string AreaName = "Auditing"; - - public static readonly Guid EndpointsLocationId = new Guid("D4AB3CD0-66BE-4551-844E-CC2C32FA64C5"); - public const string EndpointResourceName = "Endpoints"; - } -} - -namespace GitHub.Services.ServicePrincipal -{ - public static class ServicePrincipalResourceIds - { - public const string AreaName = "ServicePrincipal"; - public const string ServicePrincipalsResourceName = "ServicePrincipals"; - public static readonly Guid ServicePrincipalsLocationId = new Guid("992CB93B-847E-4683-88C9-848CD450FDF6"); - } -} - -namespace GitHub.Services.TokenSigningKeyLifecycle -{ - public static class TokenSigningKeyLifecycleResourceIds - { - public const string AreaName = "TokenSigning"; - public const string AreaId = "{f189ca86-04a2-413c-81a0-abdbd7c472da}"; - - public const string SigningKeysResourceName = "SigningKeys"; - public static readonly Guid SigningKeysLocationId = new Guid("62361140-9bb7-4d57-8223-12e6155ce354"); - - public const string NamespaceResourceName = "SigningNamespace"; - public static readonly Guid NamespaceLocationId = new Guid("29f94429-6088-4394-afd9-0435df55f079"); - } -} - -namespace GitHub.Services.GitHubConnector -{ - public static class GitHubConnectorResourceIds - { - public const string AreaId = "85738938-9FAE-4EB4-B4F0-871502E6B549"; - public const string AreaName = "GitHubConnector"; - - public static readonly Guid ResourceAreaId = new Guid(AreaId); - - public static readonly Guid ConnectionsResourceLocationId = new Guid("EBE1CF27-8F19-4955-A47B-09F125F06518"); - public const string ConnectionsResourceName = "Connections"; - - public static readonly Guid InstallationTokensResourceLocationId = new Guid("05188D9F-DD80-4C9E-BA91-4B0B3A8A67D7"); - public const string InstallationTokensResourceName = "InstallationTokens"; - - public static readonly Guid WebhookEventsResourceLocationId = new Guid("063EC204-5C0D-402F-86CF-36B1703E187F"); - public const string WebhookEventsResourceName = "WebhookEvents"; - - public static readonly Guid UserOAuthUrlsResourceLocationId = new Guid("9EA35039-A91F-4E02-A81D-573623FF7235"); - public const string UserOAuthUrlsResourceName = "UserOAuthUrls"; - - public const string DefaultResourceId = "default"; - } -} - -namespace GitHub.Services.Organization -{ - public static class OrganizationResourceIds - { - public const string AreaId = "0D55247A-1C47-4462-9B1F-5E2125590EE6"; - - public static readonly Guid ResourceAreaId = new Guid(AreaId); - - public const string OrganizationArea = "Organization"; - - public const string PropertiesResourceName = "Properties"; - - public const string LogoResourceName = "Logo"; - - // organization resources - public static readonly Guid OrganizationsResourceLocationId = new Guid("95F49097-6CDC-4AFE-A039-48B4D4C4CBF7"); - - public const string OrganizationsResourceName = "Organizations"; - - // organization properties resources - public static readonly Guid OrganizationPropertiesResourceLocationId = new Guid("103707C6-236D-4434-A0A2-9031FBB65FA6"); - - public const string OrganizationPropertiesResourceName = "OrganizationProperties"; - - // organization logo resources - public static readonly Guid OrganizationLogoResourceLocationId = new Guid("A9EEEC19-85B4-40AE-8A52-B4F697260AC4"); - - public const string OrganizationLogoResourceName = "OrganizationLogo"; - - // organization migration blobs resources - public static readonly Guid OrganizationMigrationBlobsResourceLocationId = new Guid("93F69239-28BA-497E-B4D4-33E51E6303C3"); - - public const string OrganizationMigrationBlobsResourceName = "OrganizationMigrationBlobs"; - - // collection resources - public static readonly Guid CollectionsResourceLocationId = new Guid("668B5607-0DB2-49BB-83F8-5F46F1094250"); - - public const string CollectionsResourceName = "Collections"; - - // collection properties resources - public static readonly Guid CollectionPropertiesResourceLocationId = new Guid("A0F9C508-A3C4-456B-A812-3FB0C4743521"); - - public const string CollectionPropertiesResourceName = "CollectionProperties"; - - // region resources - public static readonly Guid RegionsResourceLocationId = new Guid("6F84936F-1801-46F6-94FA-1817545D366D"); - - public const string RegionsResourceName = "Regions"; - } - - public static class OrganizationPolicyResourceIds - { - public const string OrganizationPolicyArea = "OrganizationPolicy"; - - // policy - public static readonly Guid PoliciesLocationId = new Guid("D0AB077B-1B97-4F78-984C-CFE2D248FC79"); - - public const string PoliciesResourceName = "Policies"; - - // policies batch - public static readonly Guid PoliciesBatchLocationId = new Guid("7EF423E0-59D8-4C00-B951-7143B18BD97B"); - - public const string PoliciesBatchResourceName = "PoliciesBatch"; - - // policy metadata - public static readonly Guid PolicyInformationLocationId = new Guid("222AF71B-7280-4A95-80E4-DCB0DEEAC834"); - - public const string PolicyInformationResourceName = "PolicyInformation"; - } -} - -namespace GitHub.Services.UserMapping -{ - public static class UserMappingResourceIds - { - public const string AreaId = "C8C8FFD0-2ECF-484A-B7E8-A226955EE7C8"; - public const string UserMappingArea = "UserMapping"; - - public static readonly Guid UserAccountMappingsResourceLocationId = new Guid("0DBF02CC-5EC3-4250-A145-5BEB580E0086"); - public const string UserAccountMappingsResourceName = "UserAccountMappings"; - } -} - -namespace GitHub.Services.TokenRevocation -{ - public static class TokenRevocationResourceIds - { - public const string AreaName = "TokenRevocation"; - public const string AreaId = "{3C25A612-6355-4A43-80FE-75AEBE07E981}"; - - public const string RulesResourceName = "Rules"; - public static readonly Guid RulesLocationId = new Guid("03923358-D412-40BA-A63F-36A1836C7706"); - } -} - -namespace GitHub.Services.MarketingPreferences -{ - public static class MarketingPreferencesResourceIds - { - public const string AreaId = "F4AA2205-FF00-4EEE-8216-C7A73CEE155C"; - public const string AreaName = "MarketingPreferences"; - - public const string ContactWithOffersResource = "ContactWithOffers"; - public static readonly Guid ContactWithOffersLocationid = new Guid("6E529270-1F14-4E92-A11D-B496BBBA4ED7"); - - public const string MarketingPreferencesResource = "MarketingPreferences"; - public static readonly Guid MarketingPreferencesLocationId = new Guid("0e2ebf6e-1b6c-423d-b207-06b1afdfe332"); - } - - public static class MarketingPreferencesResourceVersions - { - public const int GenericResourcePreviewVersion = 1; - } -} - -namespace GitHub.Services.HostAcquisition -{ - public static class HostAcquisitionResourceIds - { - public const string AreaName = "HostAcquisition"; - public const string AreaId = "8E128563-B59C-4A70-964C-A3BD7412183D"; - - public static readonly Guid ResourceAreaId = new Guid(AreaId); - - public const string HostAcquisitionArea = "HostAcquisition"; - - // collection resources - public static readonly Guid CollectionsResourceLocationId = new Guid("2BBEAD06-CA34-4DD7-9FE2-148735723A0A"); - - public const string CollectionsResourceName = "Collections"; - - // NameAvailability resources - public static readonly Guid NameAvailabilityResourceLocationId = new Guid("01A4CDA4-66D1-4F35-918A-212111EDC9A4"); - - public const string NameAvailabilityResourceName = "NameAvailability"; - - // region resources - public static readonly Guid RegionsResourceLocationId = new Guid("776EF918-0DAD-4EB1-A614-04988CA3A072"); - - public const string RegionsResourceName = "Regions"; - } -} - -namespace GitHub.Services.OAuthWhitelist -{ - public static class OAuthWhitelistResourceIds - { - public const string AreaId = "BED1E9DD-AE97-4D73-9E01-4797F66ED0D3"; - public const string AreaName = "OAuthWhitelist"; - - public const string OAuthWhitelistEntriesResource = "OAuthWhitelistEntries"; - public static readonly Guid OAuthWhitelistEntriesLocationId = new Guid("3AFD5B3F-12B1-4551-B6D7-B33E0E2D45D6"); - } -} - -namespace GitHub.Services.CentralizedFeature -{ - public class CentralizedFeatureResourceIds - { - public const string AreaName = "CentralizedFeature"; - public const string AreaId = "86BF2186-3092-4F5E-86A6-13997CE0924A"; - public static readonly Guid AreaIdGuid = new Guid(AreaId); - - public class Availability - { - public static readonly Guid LocationId = new Guid("EB8B51A6-1BE5-4337-B4C1-BAE7BCB587C2"); - public const string Resource = "Availability"; - } - } -} - -namespace GitHub.Services.AzureFrontDoor -{ - public static class AfdResourceIds - { - public const string AreaName = "AzureFrontDoor"; - - public const string AfdEndpointLookupResource = "AfdEndpointLookup"; - public static readonly Guid EndpointLookupLocationId = new Guid("39738637-F7C6-439A-82D7-83EFAA3A7DB4"); - } -} - -namespace GitHub.Services.WebApi -{ - public static class BasicAuthBatchResourceIds - { - public const string AreaName = "BasicAuthBatch"; - public const string AreaId = "31D56A90-A194-4567-AACF-EFE0007E3309"; - - public const string BasicAuthBatchResource = "BasicAuthBatch"; - public static readonly Guid BasicAuthBatch = new Guid("{8214680a-5c4a-4333-9b3c-228030c136f6}"); - } -} - -namespace GitHub.Services.PermissionLevel -{ - public static class PermissionLevelDefinitionResourceIds - { - public const string AreaName = "PermissionLevel"; - public const string AreaId = "E97D4D3C-C339-4745-A987-BD6F6C496788"; - - public static readonly Guid ResourceAreaId = new Guid(AreaId); - - public static readonly Guid PermissionLevelDefinitionsResourceLocationId = new Guid("D9247EA2-4E01-47C1-8662-980818AAE5D3"); - - public const string PermissionLevelDefinitionsResourceName = "PermissionLevelDefinitions"; - } - - public static class PermissionLevelAssignmentResourceIds - { - public const string AreaName = "PermissionLevel"; - public const string AreaId = "E97D4D3C-C339-4745-A987-BD6F6C496788"; - - public static readonly Guid ResourceAreaId = new Guid(AreaId); - public static readonly Guid PermissionLevelAssignmentsResourceLocationId = new Guid("005E0302-7988-4066-9AC0-1D93A42A9F0B"); - - public const string PermissionLevelAssignmentsResourceName = "PermissionLevelAssignments"; - } -} +} \ No newline at end of file diff --git a/src/Sdk/WebApi/WebApi/ServiceEvent.cs b/src/Sdk/WebApi/WebApi/ServiceEvent.cs deleted file mode 100644 index b1813c1a6..000000000 --- a/src/Sdk/WebApi/WebApi/ServiceEvent.cs +++ /dev/null @@ -1,91 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Reflection; -using System.Runtime.Serialization; - -namespace GitHub.Services.WebApi -{ - // This is the event that shall be published on the service bus by different services for other first party services. - [DataContract] - public class ServiceEvent - { - private Object m_resource; - - /// - /// This is the id of the type. - /// Constants that will be used by subscribers to identify/filter events being published on a topic. - /// - [DataMember] - public String EventType { get; set; } - - /// - /// This is the service that published this event. - /// - [DataMember] - public Publisher Publisher { get; set; } - - /// - /// The resource object that carries specific information about the event. The object must have - /// the ServiceEventObject applied for serialization/deserialization to work. - /// - [DataMember] - public Object Resource - { - get - { - return m_resource; - } - set - { - Type type = value.GetType(); - if (!type.GetTypeInfo().GetCustomAttributes(true).Any()) - { - throw new InvalidOperationException($"Resource of type {type.FullName} must have ServiceEventObject attribute"); - } - m_resource = value; - } - } - - /// - /// This is the version of the resource. - /// - [DataMember] - public String ResourceVersion { get; set; } - - /// - /// This dictionary carries the context descriptors along with their ids. - /// - [DataMember] - public Dictionary ResourceContainers { get; set; } - } - - [DataContract] - public class Publisher - { - /// - /// Name of the publishing service. - /// - [DataMember] - public String Name { get; set; } - - /// - /// Service Owner Guid - /// Eg. Tfs : 00025394-6065-48CA-87D9-7F5672854EF7 - /// - [DataMember] - public Guid ServiceOwnerId { get; set; } - } - - public class ResourceContainerTypes - { - public const String Account = "Account"; - public const String Collection = "Collection"; - } - - [System.AttributeUsage(System.AttributeTargets.Class, Inherited = true)] - public class ServiceEventObjectAttribute : Attribute - { - public ServiceEventObjectAttribute() { } - } -} diff --git a/src/Sdk/WebApi/WebApi/Utilities/ClientGeneratorAttributes.cs b/src/Sdk/WebApi/WebApi/Utilities/ClientGeneratorAttributes.cs index 134a9e5e0..cde87c0f1 100644 --- a/src/Sdk/WebApi/WebApi/Utilities/ClientGeneratorAttributes.cs +++ b/src/Sdk/WebApi/WebApi/Utilities/ClientGeneratorAttributes.cs @@ -13,24 +13,6 @@ namespace GitHub.Services.WebApi.Internal } } - /// - /// When a method or class has this attribute, we will only generate client methods for the specified languages. - /// - [AttributeUsage(AttributeTargets.Method | AttributeTargets.Class | AttributeTargets.Parameter, AllowMultiple = false)] - public sealed class ClientIncludeAttribute : Attribute - { - /// - /// - /// - /// A list of languages to generate methods for. - public ClientIncludeAttribute(RestClientLanguages languages) - { - Languages = languages; - } - - public RestClientLanguages Languages { get; private set; } - } - [Flags] public enum RestClientLanguages { @@ -45,15 +27,4 @@ namespace GitHub.Services.WebApi.Internal Python = 64, TypeScriptWebPlatform = 128 } - - /// - /// Suppresses the default constant enum generation behavior in typescriptwebplatform clientgen. When using this attribute, and affected code generation will product a .ts file instead of a .d.ts file (non-constant enumerations should not be generated into .d.ts files). - /// - [AttributeUsage(AttributeTargets.Enum)] - public class ClientDontGenerateTypeScriptEnumAsConst : Attribute - { - public ClientDontGenerateTypeScriptEnumAsConst() - { - } - } } diff --git a/src/Sdk/WebApi/WebApi/Utilities/UserAgentUtility.cs b/src/Sdk/WebApi/WebApi/Utilities/UserAgentUtility.cs index b5fbec3d6..6a8d74cc7 100644 --- a/src/Sdk/WebApi/WebApi/Utilities/UserAgentUtility.cs +++ b/src/Sdk/WebApi/WebApi/Utilities/UserAgentUtility.cs @@ -2,22 +2,16 @@ using System.Collections.Generic; using System.ComponentModel; using System.Diagnostics; -using System.Globalization; -using System.IO; using System.Net.Http.Headers; using System.Reflection; using System.Runtime.InteropServices; -using System.Text; -using GitHub.Services.Common; -using GitHub.Services.Common.Internal; -using Microsoft.Win32; namespace GitHub.Services.WebApi.Utilities.Internal { [EditorBrowsable(EditorBrowsableState.Never)] public static class UserAgentUtility { - private static Lazy> s_defaultRestUserAgent + private static Lazy> s_defaultRestUserAgent = new Lazy>(ConstructDefaultRestUserAgent); public static List GetDefaultRestUserAgent() @@ -27,38 +21,6 @@ namespace GitHub.Services.WebApi.Utilities.Internal private static List ConstructDefaultRestUserAgent() { -#if !NETSTANDARD - // Get just the exe file name without the path. - String exe; - try - { - exe = Path.GetFileName(NativeMethods.GetModuleFileName()); - } - catch (Exception e) - { - Trace.WriteLine("DefaultUserAgent: Unable to get exe. " + e.ToString()); - - // We weren't allowed to get the exe file name, so we go on. - exe = "unavailable"; - } - - Tuple skuInfo = null; - if (String.Equals(exe, "devenv.exe", StringComparison.OrdinalIgnoreCase)) - { - skuInfo = GetCurrentSkuInfo(); - } - - String app = String.Empty; - if (AppDomain.CurrentDomain != null) - { - app = (String)AppDomain.CurrentDomain.GetData(AdminConstants.ApplicationName); - } - - if (!String.IsNullOrEmpty(app)) - { - exe = String.Concat(exe, "[", app, "]"); - } -#endif // Pick up the assembly version from this dll String fileVersion = "unavailable"; try @@ -74,144 +36,11 @@ namespace GitHub.Services.WebApi.Utilities.Internal Trace.WriteLine("DefaultUserAgent: Unable to get fileVersion: " + e.ToString()); } - -#if !NETSTANDARD - - Debug.Assert(fileVersion.StartsWith("16", StringComparison.OrdinalIgnoreCase), - "The SKU numbers here are only meant to work with Dev16. For later versions the SKU numbers mapped in the GetSkuNumber method need to be updated."); - StringBuilder builder = new StringBuilder(); - builder.Append("("); - builder.Append(exe); - if (skuInfo != null) - { - builder.Append(", "); - builder.Append(skuInfo.Item1); - builder.Append(", SKU:"); - builder.Append(skuInfo.Item2.ToString(CultureInfo.InvariantCulture)); - } - builder.Append(")"); - - String commentValue = builder.ToString(); -#else String commentValue = string.Format("(NetStandard; {0})", RuntimeInformation.OSDescription.Replace('(', '[').Replace(')', ']').Trim()); -#endif + return new List { new ProductInfoHeaderValue("VSServices", fileVersion), new ProductInfoHeaderValue(commentValue) }; } - - -#if !NETSTANDARD - private static Lazy s_defaultSoapUserAgent = new Lazy(ConstructDefaultSoapUserAgent); - - public static String GetDefaultSoapUserAgent() - { - return s_defaultSoapUserAgent.Value; - } - - private static string ConstructDefaultSoapUserAgent() - { - // Get just the exe file name without the path. - String exe; - try - { - exe = Path.GetFileName(NativeMethods.GetModuleFileName()); - } - catch (Exception e) - { - Trace.WriteLine("DefaultUserAgent: Unable to get exe: " + e.ToString()); - - // We weren't allowed to get the exe file name, so we go on. - exe = "unavailable"; - } - - Tuple skuInfo = null; - if (String.Equals(exe, "devenv.exe", StringComparison.OrdinalIgnoreCase)) - { - skuInfo = GetCurrentSkuInfo(); - } - - String app = String.Empty; - if (AppDomain.CurrentDomain != null) - { - app = (String)AppDomain.CurrentDomain.GetData("ApplicationName"); - } - - if (!String.IsNullOrEmpty(app)) - { - exe = String.Concat(exe, "[", app, "]"); - } - - // Pick up the assembly version from the current dll. - String fileVersion = String.Empty; - try - { - Object[] attrs = typeof(UserAgentUtility).Assembly.GetCustomAttributes(false); - foreach (Object attr in attrs) - { - if (attr is AssemblyFileVersionAttribute) - { - fileVersion = ((AssemblyFileVersionAttribute)attr).Version; - break; - } - } - } - catch (Exception e) - { - Trace.WriteLine("DefaultUserAgent: Unable to get fileVersion: " + e.ToString()); - - // We weren't allowed to get the version info, so we go on. - fileVersion = "unavailable"; - } - - StringBuilder userAgent = new StringBuilder(); - userAgent.Append("Team Foundation ("); - userAgent.Append(exe); - userAgent.Append(", "); - userAgent.Append(fileVersion); - if (skuInfo != null) - { - userAgent.Append(", "); - userAgent.Append(skuInfo.Item1); - userAgent.Append(", SKU:"); - userAgent.Append(skuInfo.Item2.ToString(CultureInfo.InvariantCulture)); - } - userAgent.Append(")"); - return userAgent.ToString(); - } - - - private static Tuple GetCurrentSkuInfo() - { - string vsSkuEdition = Environment.GetEnvironmentVariable("VSSKUEDITION"); - if (!string.IsNullOrEmpty(vsSkuEdition)) - { - Tuple skuInfo; - if (s_dev16SkuToAgentStringMap.TryGetValue(vsSkuEdition, out skuInfo)) - { - return skuInfo; - } - else - { - Debug.Fail("Unrecognized value for VSSKUEDITION: '{0}'. This value needs to be added to the s_dev16SkuToAgentStringMap.", vsSkuEdition); - } - } - - return new Tuple(ClientSkuNames.Dev16.Other, ClientSkuNumbers.Dev16Other); - } - - /// - /// The key is the SKU name provided by VSSKUEDITION env variable. The value is a tuple. Item1 is a string for the SKU Name to put in the User Agent string, and Item2 is an int for the SkuCode. - /// - private static readonly Dictionary> s_dev16SkuToAgentStringMap = new Dictionary>(StringComparer.OrdinalIgnoreCase) - { - { "Enterprise", new Tuple(ClientSkuNames.Dev16.Enterprise, ClientSkuNumbers.Dev16Enterprise) }, - { "Professional", new Tuple(ClientSkuNames.Dev16.Pro, ClientSkuNumbers.Dev16Pro) }, - { "Community", new Tuple(ClientSkuNames.Dev16.Community, ClientSkuNumbers.Dev16Community) }, - { "V3|UNKNOWN", new Tuple(ClientSkuNames.Dev16.TE, ClientSkuNumbers.Dev16TeamExplorer) }, - { "V4|UNKNOWN", new Tuple(ClientSkuNames.Dev16.Sql, ClientSkuNumbers.Dev16Sql) }, // future release as of 4/25/2017. - { "IntShell", new Tuple(ClientSkuNames.Dev16.IntShell, ClientSkuNumbers.Dev16IntShell) } // future release as of 4/25/2017. This key may change. - }; -#endif } } diff --git a/src/Sdk/WebApi/WebApi/Utilities/XmlSerializableDataContractExtensions.cs b/src/Sdk/WebApi/WebApi/Utilities/XmlSerializableDataContractExtensions.cs index 06cea3ca9..10427a1a0 100644 --- a/src/Sdk/WebApi/WebApi/Utilities/XmlSerializableDataContractExtensions.cs +++ b/src/Sdk/WebApi/WebApi/Utilities/XmlSerializableDataContractExtensions.cs @@ -27,103 +27,6 @@ namespace GitHub.Services.WebApi.Xml /// public static class XmlSerializableDataContractExtensions { - // This method has a class constraint because we can't use reflection to mutate the properties of a struct without boxing - public static void ReadDataMemberXml(this XmlReader reader, T destination) where T : class - { - ArgumentUtility.CheckForNull(reader, nameof(reader)); - - var isEmptyElement = reader.IsEmptyElement; - - reader.ReadStartElement(); - - if (isEmptyElement) - { - return; - } - - var serializableProperties = GetSerializableProperties(destination.GetType().GetTypeInfo()).MappedByName; - - while (reader.IsStartElement()) - { - if (!serializableProperties.TryGetValue(reader.LocalName, out var property)) - { - reader.ReadOuterXml(); - continue; - } - - isEmptyElement = reader.IsEmptyElement; - - object propertyValue; - - if (destination is GraphSubjectBase && property.SerializedName == nameof(GraphSubjectBase.Descriptor)) - { - var propertySerializer = GetSerializer(reader.NamespaceURI, reader.LocalName, typeof(SubjectDescriptor)); - propertyValue = propertySerializer.Deserialize(reader.ReadSubtree()).ToString(); - } - else - { - var propertySerializer = GetSerializer(reader.NamespaceURI, reader.LocalName, property.SerializedType); - propertyValue = propertySerializer.Deserialize(reader.ReadSubtree()); - } - - property.SetValue(destination, propertyValue); - - if (isEmptyElement) - { - reader.ReadOuterXml(); - } - else - { - reader.ReadEndElement(); - } - } - - reader.ReadEndElement(); - } - - public static void WriteDataMemberXml(this XmlWriter writer, object source) - { - ArgumentUtility.CheckForNull(writer, nameof(writer)); - - var type = source.GetType().GetTypeInfo(); - var shouldWriteNamespace = writer.Settings == null; - var rootNamespace = shouldWriteNamespace ? GetNamespace(type) : null; - var serializableProperties = GetSerializableProperties(type).EnumeratedInOrder; - foreach (var property in serializableProperties) - { - if (!property.ShouldSerialize(source)) - { - continue; - } - - var propertyValue = property.GetValue(source); - if (property.IsIgnorableDefaultValue(propertyValue)) - { - continue; - } - - var propertySerializer = GetSerializer(rootNamespace, property.SerializedName, property.SerializedType); - propertySerializer.Serialize(writer, propertyValue); - - if (!string.IsNullOrEmpty(property.SerializedNameForCamelCaseCompat)) - { - propertySerializer = GetSerializer(rootNamespace, property.SerializedNameForCamelCaseCompat, property.SerializedType); - propertySerializer.Serialize(writer, propertyValue); - } - } - } - - private static string GetNamespace(TypeInfo type) - { - if (!NamespacesByType.TryGetValue(type, out string outputNamespace)) - { - outputNamespace = $"http://schemas.datacontract.org/2004/07/{type.Namespace}"; - NamespacesByType.TryAdd(type, outputNamespace); - } - - return outputNamespace; - } - private static SerializableProperties GetSerializableProperties(TypeInfo type) { if (SerializablePropertiesByType.TryGetValue(type, out var properties)) diff --git a/src/Sdk/WebApi/WebApi/VssClientHttpRequestSettings.cs b/src/Sdk/WebApi/WebApi/VssClientHttpRequestSettings.cs index b7b741667..eab6e16e7 100644 --- a/src/Sdk/WebApi/WebApi/VssClientHttpRequestSettings.cs +++ b/src/Sdk/WebApi/WebApi/VssClientHttpRequestSettings.cs @@ -51,101 +51,8 @@ namespace GitHub.Services.WebApi { // Set up reasonable defaults in case the registry keys are not present var settings = new VssClientHttpRequestSettings(); - -#if !NETSTANDARD - try - { - // Prefer HKCU over HKLM. - RegistryKey key = null; - - // Default store: HKCU - using (RegistryKey userRoot = VssClientEnvironment.TryGetUserRegistryRoot()) - { - if (userRoot != null) - { - key = userRoot.OpenSubKey(c_settingsKey); - } - } - - // Alternate store: HKLM - if (key == null) - { - using (RegistryKey applicationRoot = VssClientEnvironment.TryGetApplicationRegistryRoot()) - { - if (applicationRoot != null) - { - key = applicationRoot.OpenSubKey(c_settingsKey); - } - } - } - - // If no store, create the default store - if (key == null) - { - using (RegistryKey userRoot = VssClientEnvironment.TryGetUserRegistryRoot()) - { - if (userRoot != null) - { - key = userRoot.CreateSubKey(c_settingsKey); - } - } - - // Write defaults - String defaultAgentId = String.Format(CultureInfo.InvariantCulture, "VSS: {0}", Guid.NewGuid().ToString("D")); - key.SetValue(c_settingsAgentId, defaultAgentId); - } - - if (key != null) - { - using (key) - { - Boolean boolValue; - - if (Boolean.TryParse(key.GetValue(c_settingBypassProxyOnLocal) as String, out boolValue)) - { - settings.BypassProxyOnLocal = boolValue; - } - - if (Boolean.TryParse(key.GetValue(c_settingEnableCompression) as String, out boolValue)) - { - settings.CompressionEnabled = boolValue; - } - - if (key.GetValue(c_settingsDefaultTimeout) != null && key.GetValueKind(c_settingsDefaultTimeout) == RegistryValueKind.DWord) - { - settings.SendTimeout = TimeSpan.FromMilliseconds(Math.Max(1, (Int32)key.GetValue(c_settingsDefaultTimeout))); - } - - if (key.GetValue(c_settingsAgentId) != null && key.GetValueKind(c_settingsAgentId) == RegistryValueKind.String) - { - settings.AgentId = (String)key.GetValue(c_settingsAgentId); - } - } - } - - String bypass = Environment.GetEnvironmentVariable("TFS_BYPASS_PROXY_ON_LOCAL"); - if (!String.IsNullOrEmpty(bypass)) - { - settings.BypassProxyOnLocal = String.Equals(bypass, "1", StringComparison.Ordinal); - } - } - catch (Exception e) - { - // If the current account doesn't have privileges to access the registry (e.g. TFS service account) - // ignore any registry access errors... - if (!(e is SecurityException || e is UnauthorizedAccessException)) - { - Trace.WriteLine("An exception was encountered and ignored while reading settings: " + e); - } - } -#endif - settings.UserAgent = UserAgentUtility.GetDefaultRestUserAgent(); -#if !NETSTANDARD - //default this to true on client\server connections - settings.ClientCertificateManager = VssClientCertificateManager.Instance; -#endif return settings; } diff --git a/src/Sdk/WebApi/WebApi/VssClientSettings.cs b/src/Sdk/WebApi/WebApi/VssClientSettings.cs index 01d2097a2..3b5a7e324 100644 --- a/src/Sdk/WebApi/WebApi/VssClientSettings.cs +++ b/src/Sdk/WebApi/WebApi/VssClientSettings.cs @@ -42,84 +42,6 @@ namespace GitHub.Services.WebApi } } -#if !NETSTANDARD - /// - /// Defines the expiration interval for the location service client disk cache. - /// - internal static int? ClientCacheTimeToLive - { - get - { - if (s_clientCacheTimeToLive == null && !s_checkedClientCacheTimeToLive) - { - // Check once per process lifetime, but don't keep checking the registry over and over - s_checkedClientCacheTimeToLive = true; - - // Prefer HKCU over HKLM. - RegistryKey key = null; - - // Default store: HKCU - using (RegistryKey userRoot = VssClientEnvironment.TryGetUserRegistryRoot()) - { - if (userRoot != null) - { - key = userRoot.OpenSubKey(c_cacheSettingsKey); - } - } - - // Alternate store: HKLM - if (key == null) - { - using (RegistryKey applicationRoot = VssClientEnvironment.TryGetApplicationRegistryRoot()) - { - if (applicationRoot != null) - { - key = applicationRoot.OpenSubKey(c_cacheSettingsKey); - } - } - } - - if (key != null) - { - if (key.GetValue(c_settingClientCacheTimeToLive) != null && key.GetValueKind(c_settingClientCacheTimeToLive) == RegistryValueKind.DWord) - { - s_clientCacheTimeToLive = Math.Max(1, (int)key.GetValue(c_settingClientCacheTimeToLive)); - } - } - } - - return s_clientCacheTimeToLive; - } - set - { - // For testing purposes only - s_clientCacheTimeToLive = value; - } - } - - /// - /// Gets Connect() options which are overriden in the user registry hive. - /// - internal static void GetConnectionOverrides( - out VssConnectMode? connectModeOverride, - out string userOverride) - { - connectModeOverride = null; - userOverride = VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.FederatedAuthenticationUser); - - var modeOverride = VssClientEnvironment.GetSharedConnectedUserValue(VssConnectionParameterOverrideKeys.FederatedAuthenticationMode); - - VssConnectMode modeOverrideValue = VssConnectMode.Automatic; - - if (modeOverride != null && Enum.TryParse(modeOverride, out modeOverrideValue)) - { - connectModeOverride = modeOverrideValue; - } - } - - private static int? s_clientCacheTimeToLive; - private static bool s_checkedClientCacheTimeToLive; -#endif private const string c_cacheSettingsKey = "Services\\CacheSettings"; private const string c_settingClientCacheTimeToLive = "ClientCacheTimeToLive"; } diff --git a/src/Sdk/WebApi/WebApi/VssConnection.cs b/src/Sdk/WebApi/WebApi/VssConnection.cs index ee7d6aa50..38bfad8c7 100644 --- a/src/Sdk/WebApi/WebApi/VssConnection.cs +++ b/src/Sdk/WebApi/WebApi/VssConnection.cs @@ -83,10 +83,6 @@ namespace GitHub.Services.WebApi { innerHandler.Credentials.Federated.TokenStorageUrl = baseUrl; } - if (innerHandler.Credentials.Windows != null) - { - innerHandler.Credentials.Windows.TokenStorageUrl = baseUrl; - } } } @@ -99,13 +95,6 @@ namespace GitHub.Services.WebApi return ConnectAsync(VssConnectMode.Automatic, null, cancellationToken); } - public Task ConnectAsync( - VssConnectMode connectMode, - CancellationToken cancellationToken = default(CancellationToken)) - { - return ConnectAsync(connectMode, null, cancellationToken); - } - public Task ConnectAsync( VssConnectMode connectMode, IDictionary parameters, @@ -139,20 +128,6 @@ namespace GitHub.Services.WebApi promptToSetParametersOn = Credentials.Federated.Prompt; } -#if DEBUG && !NETSTANDARD - VssConnectMode? connectModeOverride; - String userOverride; - VssClientSettings.GetConnectionOverrides(out connectModeOverride, out userOverride); - - if (connectModeOverride != null) - { - connectMode = connectModeOverride.Value; - } - if (userOverride != null) - { - parameters[VssConnectionParameterKeys.User] = userOverride; - } -#endif parameters[VssConnectionParameterKeys.VssConnectionMode] = connectMode.ToString(); promptToSetParametersOn.Parameters = parameters; } @@ -208,42 +183,6 @@ namespace GitHub.Services.WebApi return GetClientAsync().SyncResult(); } - /// - /// Retrieves an HTTP client of the specified type. - /// - /// The type of client to retrieve - /// Optional parameter. If supplied, the identifier will be used to resolve the - /// base address for the HTTP client. Otherwise the base address will be resolved using the service identifier - /// in the metadata of the requested client type (i.e. the ResourceArea attribute) - /// The client of the specified type - public T GetClient(Guid serviceIdentifier) where T : VssHttpClientBase - { - return GetClientAsync(serviceIdentifier).SyncResult(); - } - - /// - /// Retrieves an HTTP client of the specified type. - /// - /// The type of client to retrieve - /// The client of the specified type - public T GetClient(CancellationToken cancellationToken) where T : VssHttpClientBase - { - return GetClientAsync(cancellationToken).SyncResult(); - } - - /// - /// Retrieves an HTTP client of the specified type. - /// - /// The type of client to retrieve - /// Optional parameter. If supplied, the identifier will be used to resolve the - /// base address for the HTTP client. Otherwise the base address will be resolved using the service identifier - /// in the metadata of the requested client type (i.e. the ResourceArea attribute) - /// The client of the specified type - public T GetClient(Guid serviceIdentifier, CancellationToken cancellationToken) where T : VssHttpClientBase - { - return GetClientAsync(serviceIdentifier, cancellationToken).SyncResult(); - } - /// /// Retrieves an HTTP client of the specified type. /// @@ -263,38 +202,6 @@ namespace GitHub.Services.WebApi return (T)await GetClientServiceImplAsync(typeof(T), serviceIdentifier, GetClientInstanceAsync, cancellationToken).ConfigureAwait(false); } - /// - /// Retrieves an HTTP client of the specified type. - /// - /// The type of client to retrieve - /// Optional parameter. If supplied, the identifier will be used to resolve the - /// base address for the HTTP client. Otherwise the base address will be resolved using the service identifier - /// in the metadata of the requested client type (i.e. the ResourceArea attribute) - /// The client of the specified type - public async Task GetClientAsync(Guid serviceIdentifier, CancellationToken cancellationToken = default(CancellationToken)) where T : VssHttpClientBase - { - return (T)await GetClientServiceImplAsync(typeof(T), serviceIdentifier, GetClientInstanceAsync, cancellationToken).ConfigureAwait(false); - } - - /// - /// - /// - /// - /// - public Object GetClient(Type clientType) - { - // Verify incoming type is assignable from VssHttpClientBase - Type requiredBaseType = typeof(VssHttpClientBase); - - if (!requiredBaseType.GetTypeInfo().IsAssignableFrom(clientType.GetTypeInfo())) - { - throw new ArgumentException(requiredBaseType.FullName); - } - - // Return client instance - return GetClientServiceImplAsync(clientType, GetServiceIdentifier(clientType), GetClientInstanceAsync).SyncResult(); - } - /// /// /// @@ -358,24 +265,6 @@ namespace GitHub.Services.WebApi return GetClientInstanceAsync(managedType, serviceIdentifier, cancellationToken, null, null); } - /// - /// - /// - /// - /// - /// - /// - /// - [EditorBrowsable(EditorBrowsableState.Never)] - internal Task GetClientInstanceAsync( - Type managedType, - CancellationToken cancellationToken, - VssHttpRequestSettings settings, - DelegatingHandler[] handlers) - { - return GetClientInstanceAsync(managedType, GetServiceIdentifier(managedType), cancellationToken, settings, handlers); - } - /// /// /// @@ -543,33 +432,6 @@ namespace GitHub.Services.WebApi m_extensibleServiceTypes[typeName] = type; } - /// - /// Used for Testing Only - /// - /// - /// - internal void RegisterClientServiceInstance( - Type type, - Object instance) - { - ArgumentUtility.CheckForNull(type, "type"); - ArgumentUtility.CheckForNull(instance, "instance"); - CheckForDisposed(); - - if (!type.GetTypeInfo().IsAssignableFrom(instance.GetType().GetTypeInfo())) - { - // This is just a test method -- no need to resource the string - throw new ArgumentException("Object is not an instance of the specified type."); - } - - Type instanceType = instance.GetType(); - ClientCacheKey cacheKey = new ClientCacheKey(instanceType, GetServiceIdentifier(type)); - - // Now add the service to the service list. - RegisterExtensibleType(type.Name, instanceType); - m_cachedTypes[cacheKey] = instance; - } - private bool m_isDisposed = false; private object m_disposeLock = new object(); diff --git a/src/Sdk/WebApi/WebApi/VssConnectionParameterKeys.cs b/src/Sdk/WebApi/WebApi/VssConnectionParameterKeys.cs index 11969bec2..402605d69 100644 --- a/src/Sdk/WebApi/WebApi/VssConnectionParameterKeys.cs +++ b/src/Sdk/WebApi/WebApi/VssConnectionParameterKeys.cs @@ -5,21 +5,6 @@ namespace GitHub.Services.WebApi.Internal [EditorBrowsable(EditorBrowsableState.Never)] public static class VssConnectionParameterKeys { - public const string User = "user"; - public const string AccessToken = "accessToken"; public const string VssConnectionMode = "vssConnectionMode"; } - - [EditorBrowsable(EditorBrowsableState.Never)] - public static class VssConnectionParameterOverrideKeys - { - public const string AadInstance = "AadInstance"; - public const string AadNativeClientIdentifier = "AadClientIdentifier"; - public const string AadNativeClientRedirect = "AadNativeClientRedirect"; - public const string AadApplicationTenant = "AadApplicationTenant"; - public const string ConnectedUserRoot = "ConnectedUser"; - public const string FederatedAuthenticationMode = "FederatedAuthenticationMode"; - public const string FederatedAuthenticationUser = "FederatedAuthenticationUser"; - public const string UseAadWindowsIntegrated = "UseAadWindowsIntegrated"; - } } diff --git a/src/Sdk/WebApi/WebApi/VssHttpClientBase.cs b/src/Sdk/WebApi/WebApi/VssHttpClientBase.cs index d0fffda2b..b6c0f5e72 100644 --- a/src/Sdk/WebApi/WebApi/VssHttpClientBase.cs +++ b/src/Sdk/WebApi/WebApi/VssHttpClientBase.cs @@ -97,11 +97,6 @@ namespace GitHub.Services.WebApi { vssHttpMessageHandler.Credentials.Federated.TokenStorageUrl = m_client.BaseAddress; } - if (vssHttpMessageHandler.Credentials.Windows != null - && vssHttpMessageHandler.Credentials.Windows.TokenStorageUrl == null) - { - vssHttpMessageHandler.Credentials.Windows.TokenStorageUrl = m_client.BaseAddress; - } } } else if (handler is DelegatingHandler delegatingHandler) diff --git a/src/Sdk/WebApi/WebApi/VssRequestTimerTrace.cs b/src/Sdk/WebApi/WebApi/VssRequestTimerTrace.cs index 86826b0b3..160f7af60 100644 --- a/src/Sdk/WebApi/WebApi/VssRequestTimerTrace.cs +++ b/src/Sdk/WebApi/WebApi/VssRequestTimerTrace.cs @@ -70,9 +70,6 @@ namespace GitHub.Services.WebApi VssPerformanceEventSource.Log.RESTStart(Guid.Empty, requestString); _requestTimer.Start(); -#if !NETSTANDARD - EventActivityIdControl(1, ref _activityId); -#endif #endif } internal void TraceResponse(HttpResponseMessage response) @@ -80,22 +77,10 @@ namespace GitHub.Services.WebApi #if TRACE _requestTimer.Stop(); String responseString = response.GetResponseString(_requestTimer.ElapsedMilliseconds); - -#if !NETSTANDARD - VssPerformanceEventSource.Log.RESTStop(Guid.Empty, _activityId, responseString, _requestTimer.ElapsedMilliseconds); -#endif #endif } #if TRACE private Stopwatch _requestTimer; -#if !NETSTANDARD - private Guid _activityId; -#endif -#endif - -#if !NETSTANDARD - [DllImport("ADVAPI32.DLL", ExactSpelling = true, EntryPoint = "EventActivityIdControl")] - internal static extern uint EventActivityIdControl([In] int ControlCode, [In][Out] ref Guid ActivityId); #endif } diff --git a/src/Sdk/WebApi/WebApi/VssSigningCredentials.cs b/src/Sdk/WebApi/WebApi/VssSigningCredentials.cs index 70c3ebf05..e9b4b054f 100644 --- a/src/Sdk/WebApi/WebApi/VssSigningCredentials.cs +++ b/src/Sdk/WebApi/WebApi/VssSigningCredentials.cs @@ -106,28 +106,11 @@ namespace GitHub.Services.WebApi if (certificate.HasPrivateKey) { - -// Once we move the ClientObjectModelTargetFrameworkVersion to 4.6 we should remove the #else sections -// in this file. The NETSTANDARD sections should be the code for both NetStandard and desktop. 4.5 does -// not support these new cryptography classes, which is why we need these #ifs for now. -#if NETSTANDARD var rsa = certificate.GetRSAPrivateKey(); if (rsa == null) { throw new SignatureAlgorithmUnsupportedException(certificate.SignatureAlgorithm.FriendlyName); } -#else - var rsa = certificate.PrivateKey as RSACryptoServiceProvider; - if (rsa == null) - { - throw new SignatureAlgorithmUnsupportedException(certificate.PrivateKey.SignatureAlgorithm); - } - - if (rsa.CspKeyContainerInfo.ProviderType != 24) - { - throw new SignatureAlgorithmUnsupportedException(rsa.CspKeyContainerInfo.ProviderType); - } -#endif if (rsa.KeySize < c_minKeySize) { @@ -138,7 +121,6 @@ namespace GitHub.Services.WebApi return new X509Certificate2SigningToken(certificate); } -#if NETSTANDARD /// /// Creates a new VssSigningCredentials instance using the specified /// callback function to retrieve the signing key. @@ -164,33 +146,6 @@ namespace GitHub.Services.WebApi return new RSASigningToken(factory, rsa.KeySize); } } -#else - /// - /// Creates a new VssSigningCredentials instance using the specified - /// callback function to retrieve the signing key. - /// - /// The factory which creates RSACryptoServiceProvider keys used for signing and verification - /// A new VssSigningCredentials instance which uses the specified provider for signing - public static VssSigningCredentials Create(Func factory) - { - ArgumentUtility.CheckForNull(factory, nameof(factory)); - - using (var rsa = factory()) - { - if (rsa == null) - { - throw new InvalidCredentialsException(JwtResources.SignatureAlgorithmUnsupportedException("None")); - } - - if (rsa.KeySize < c_minKeySize) - { - throw new InvalidCredentialsException(JwtResources.SigningTokenKeyTooSmall()); - } - - return new RSASigningToken(factory, rsa.KeySize); - } - } -#endif /// /// Creates a new VssSigningCredentials instance using the specified as the signing @@ -300,11 +255,7 @@ namespace GitHub.Services.WebApi { get { -#if NETSTANDARD return m_certificate.GetRSAPublicKey().KeySize; -#else - return m_certificate.PublicKey.Key.KeySize; -#endif } } @@ -328,32 +279,14 @@ namespace GitHub.Services.WebApi Byte[] input, Byte[] signature) { -#if NETSTANDARD var rsa = m_certificate.GetRSAPublicKey(); return rsa.VerifyData(input, signature, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1); -#else - var rsa = m_certificate.PublicKey.Key as RSACryptoServiceProvider; - - using (var hash = SHA256CryptoServiceProvider.Create()) - { - return rsa.VerifyData(input, hash, signature); - } -#endif } protected override Byte[] GetSignature(Byte[] input) { -#if NETSTANDARD var rsa = m_certificate.GetRSAPrivateKey(); return rsa.SignData(input, HashAlgorithmName.SHA256, RSASignaturePadding.Pkcs1); -#else - var rsa = m_certificate.PrivateKey as RSACryptoServiceProvider; - - using (var hash = SHA256CryptoServiceProvider.Create()) - { - return rsa.SignData(input, hash); - } -#endif } protected override Boolean HasPrivateKey() @@ -369,7 +302,6 @@ namespace GitHub.Services.WebApi private readonly X509Certificate2 m_certificate; } -#if NETSTANDARD private class RSASigningToken : AsymmetricKeySigningToken { public RSASigningToken( @@ -425,65 +357,6 @@ namespace GitHub.Services.WebApi private readonly Int32 m_keySize; private readonly Func m_factory; } -#else - private class RSASigningToken : AsymmetricKeySigningToken - { - public RSASigningToken( - Func factory, - Int32 keySize) - { - m_keySize = keySize; - m_factory = factory; - } - - public override Int32 KeySize - { - get - { - return m_keySize; - } - } - - protected override Byte[] GetSignature(Byte[] input) - { - using (var rsa = m_factory()) - using (var hash = new SHA256CryptoServiceProvider()) - { - return rsa.SignData(input, hash); - } - } - - protected override Boolean HasPrivateKey() - { - try - { - // As unfortunate as this is, there is no way to tell from an RSA implementation, based on querying - // properties alone, if it supports signature operations or has a private key. This is a one-time - // hit for the signing credentials implementation, so it shouldn't be a huge deal. - GetSignature(new Byte[1] { 1 }); - return true; - } - catch (CryptographicException) - { - return false; - } - } - - public override Boolean VerifySignature( - Byte[] input, - Byte[] signature) - { - using (var rsa = m_factory()) - using (var hash = new SHA256CryptoServiceProvider()) - { - return rsa.VerifyData(input, hash, signature); - } - } - - private readonly Int32 m_keySize; - private readonly Func m_factory; - } -#endif #endregion } diff --git a/src/Sdk/nuget.config b/src/Sdk/nuget.config deleted file mode 100644 index 5a8826814..000000000 --- a/src/Sdk/nuget.config +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - - - - diff --git a/src/Test/L0/Listener/CommandSettingsL0.cs b/src/Test/L0/Listener/CommandSettingsL0.cs index a6ba943ff..f5b5187a6 100644 --- a/src/Test/L0/Listener/CommandSettingsL0.cs +++ b/src/Test/L0/Listener/CommandSettingsL0.cs @@ -385,7 +385,7 @@ namespace GitHub.Runner.Common.Tests [Fact] [Trait("Level", "L0")] [Trait("Category", nameof(CommandSettings))] - public void PromptsForPassword() + public void PromptsForRunnerRegisterToken() { using (TestHostContext hc = CreateTestContext()) { @@ -393,46 +393,19 @@ namespace GitHub.Runner.Common.Tests var command = new CommandSettings(hc, args: new string[0]); _promptManager .Setup(x => x.ReadValue( - Constants.Runner.CommandLine.Args.Password, // argName - "What is your GitHub password?", // description + Constants.Runner.CommandLine.Args.Token, // argName + "What is your runner register token?", // description true, // secret string.Empty, // defaultValue Validators.NonEmptyValidator, // validator false)) // unattended - .Returns("some password"); + .Returns("some token"); // Act. - string actual = command.GetPassword(); + string actual = command.GetRunnerRegisterToken(); // Assert. - Assert.Equal("some password", actual); - } - } - - [Fact] - [Trait("Level", "L0")] - [Trait("Category", nameof(CommandSettings))] - public void PromptsForPool() - { - using (TestHostContext hc = CreateTestContext()) - { - // Arrange. - var command = new CommandSettings(hc, args: new string[0]); - _promptManager - .Setup(x => x.ReadValue( - Constants.Runner.CommandLine.Args.Pool, // argName - "Enter the name of your runner pool:", // description - false, // secret - "default", // defaultValue - Validators.NonEmptyValidator, // validator - false)) // unattended - .Returns("some pool"); - - // Act. - string actual = command.GetPool(); - - // Assert. - Assert.Equal("some pool", actual); + Assert.Equal("some token", actual); } } @@ -498,7 +471,7 @@ namespace GitHub.Runner.Common.Tests _promptManager .Setup(x => x.ReadValue( Constants.Runner.CommandLine.Args.Token, // argName - "Enter your personal access token:", // description + "What is your pool admin oauth access token?", // description true, // secret string.Empty, // defaultValue Validators.NonEmptyValidator, // validator @@ -567,33 +540,6 @@ namespace GitHub.Runner.Common.Tests } } - [Fact] - [Trait("Level", "L0")] - [Trait("Category", nameof(CommandSettings))] - public void PromptsForUserName() - { - using (TestHostContext hc = CreateTestContext()) - { - // Arrange. - var command = new CommandSettings(hc, args: new string[0]); - _promptManager - .Setup(x => x.ReadValue( - Constants.Runner.CommandLine.Args.UserName, // argName - "What is your GitHub username?", // description - false, // secret - string.Empty, // defaultValue - Validators.NonEmptyValidator, // validator - false)) // unattended - .Returns("some user name"); - - // Act. - string actual = command.GetUserName(); - - // Assert. - Assert.Equal("some user name", actual); - } - } - [Fact] [Trait("Level", "L0")] [Trait("Category", nameof(CommandSettings))] diff --git a/src/Test/L0/Listener/Configuration/ArgumentValidatorTestsL0.cs b/src/Test/L0/Listener/Configuration/ArgumentValidatorTestsL0.cs index c43ca9853..6f3a62d62 100644 --- a/src/Test/L0/Listener/Configuration/ArgumentValidatorTestsL0.cs +++ b/src/Test/L0/Listener/Configuration/ArgumentValidatorTestsL0.cs @@ -25,7 +25,7 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration { using (TestHostContext hc = new TestHostContext(this)) { - Assert.True(Validators.AuthSchemeValidator("pat")); + Assert.True(Validators.AuthSchemeValidator("OAuth")); Assert.False(Validators.AuthSchemeValidator("Fail")); } } @@ -47,7 +47,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration [Fact] [Trait("Level", "L0")] [Trait("Category", "ArgumentValidator")] -#endif public void WindowsLogonAccountValidator() { using (TestHostContext hc = new TestHostContext(this)) @@ -56,5 +55,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration Assert.True(Validators.NTAccountValidator("NT AUTHORITY\\LOCAL SERVICE")); } } +#endif } } diff --git a/src/Test/L0/Listener/Configuration/ConfigurationManagerL0.cs b/src/Test/L0/Listener/Configuration/ConfigurationManagerL0.cs index a4108cce8..08b1ec625 100644 --- a/src/Test/L0/Listener/Configuration/ConfigurationManagerL0.cs +++ b/src/Test/L0/Listener/Configuration/ConfigurationManagerL0.cs @@ -26,7 +26,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration private Mock _promptManager; private Mock _store; private Mock _extnMgr; - private Mock _cert; #if OS_WINDOWS private Mock _serviceControlManager; @@ -44,7 +43,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration private string _expectedAuthType = "pat"; private string _expectedWorkFolder = "_work"; private int _expectedPoolId = 1; - private int _expectedDeploymentMachineId = 81; private RSACryptoServiceProvider rsa = null; private RunnerSettings _configMgrAgentSettings = new RunnerSettings(); @@ -57,7 +55,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration _store = new Mock(); _extnMgr = new Mock(); _rsaKeyManager = new Mock(); - _cert = new Mock(); #if OS_WINDOWS _serviceControlManager = new Mock(); @@ -68,7 +65,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration #endif var expectedAgent = new TaskAgent(_expectedAgentName) { Id = 1 }; - var expectedDeploymentMachine = new DeploymentMachine() { Agent = expectedAgent, Id = _expectedDeploymentMachineId }; expectedAgent.Authorization = new TaskAgentAuthorization { ClientId = Guid.NewGuid(), @@ -124,7 +120,6 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration tc.SetSingleton(_extnMgr.Object); tc.SetSingleton(_runnerServer.Object); tc.SetSingleton(_locationServer.Object); - tc.SetSingleton(_cert.Object); #if OS_WINDOWS tc.SetSingleton(_serviceControlManager.Object); @@ -155,10 +150,7 @@ namespace GitHub.Runner.Common.Tests.Listener.Configuration tc, new[] { - "configure", -#if !OS_WINDOWS - "--acceptteeeula", -#endif + "configure", "--url", _expectedServerUrl, "--name", _expectedAgentName, "--pool", _expectedPoolName, diff --git a/src/Test/L0/Listener/Configuration/RunnerCredentialL0.cs b/src/Test/L0/Listener/Configuration/RunnerCredentialL0.cs index 8e2e2f654..57aa88dce 100644 --- a/src/Test/L0/Listener/Configuration/RunnerCredentialL0.cs +++ b/src/Test/L0/Listener/Configuration/RunnerCredentialL0.cs @@ -1,24 +1,24 @@ using GitHub.Runner.Listener; using GitHub.Runner.Listener.Configuration; -using GitHub.Services.Client; using GitHub.Services.Common; +using GitHub.Services.OAuth; namespace GitHub.Runner.Common.Tests.Listener.Configuration { public class TestRunnerCredential : CredentialProvider { - public TestRunnerCredential(): base("TEST") {} + public TestRunnerCredential() : base("TEST") { } public override VssCredentials GetVssCredentials(IHostContext context) { - Tracing trace = context.GetTrace("PersonalAccessToken"); + Tracing trace = context.GetTrace("OuthAccessToken"); trace.Info("GetVssCredentials()"); - - VssBasicCredential loginCred = new VssBasicCredential("test", "password"); + + var loginCred = new VssOAuthAccessTokenCredential("sometoken"); VssCredentials creds = new VssCredentials(loginCred); trace.Verbose("cred created"); return creds; - } + } public override void EnsureCredential(IHostContext context, CommandSettings command, string serverUrl) { } diff --git a/src/Test/L0/Listener/JobDispatcherL0.cs b/src/Test/L0/Listener/JobDispatcherL0.cs index 60955b6fb..5f774c174 100644 --- a/src/Test/L0/Listener/JobDispatcherL0.cs +++ b/src/Test/L0/Listener/JobDispatcherL0.cs @@ -32,11 +32,8 @@ namespace GitHub.Runner.Common.Tests.Listener { TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = null; - JobEnvironment environment = new JobEnvironment(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); - var jobRequest = new AgentJobRequestMessage(plan, timeline, JobId, "someJob", "someJob", environment, tasks); - var result = Pipelines.AgentJobRequestMessageUtil.Convert(jobRequest); + Guid jobId = Guid.NewGuid(); + var result = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, "someJob", "someJob", null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); result.ContextData["github"] = new Pipelines.ContextData.DictionaryContextData(); return result; } diff --git a/src/Test/L0/Listener/MessageListenerL0.cs b/src/Test/L0/Listener/MessageListenerL0.cs index 626d924a0..e6da526cd 100644 --- a/src/Test/L0/Listener/MessageListenerL0.cs +++ b/src/Test/L0/Listener/MessageListenerL0.cs @@ -160,7 +160,7 @@ namespace GitHub.Runner.Common.Tests.Listener { Body = "somebody1", MessageId = 4234, - MessageType = JobRequestMessageTypes.AgentJobRequest + MessageType = JobRequestMessageTypes.PipelineAgentJobRequest }, new TaskAgentMessage { @@ -174,7 +174,7 @@ namespace GitHub.Runner.Common.Tests.Listener { Body = "somebody3", MessageId = 4236, - MessageType = JobRequestMessageTypes.AgentJobRequest + MessageType = JobRequestMessageTypes.PipelineAgentJobRequest } }; var messages = new Queue(arMessages); diff --git a/src/Test/L0/Listener/RunnerL0.cs b/src/Test/L0/Listener/RunnerL0.cs index 0003ba5cd..8548a035d 100644 --- a/src/Test/L0/Listener/RunnerL0.cs +++ b/src/Test/L0/Listener/RunnerL0.cs @@ -23,7 +23,6 @@ namespace GitHub.Runner.Common.Tests.Listener private Mock _runnerServer; private Mock _term; private Mock _configStore; - private Mock _cert; private Mock _updater; public RunnerL0() @@ -36,19 +35,15 @@ namespace GitHub.Runner.Common.Tests.Listener _runnerServer = new Mock(); _term = new Mock(); _configStore = new Mock(); - _cert = new Mock(); _updater = new Mock(); } - private AgentJobRequestMessage CreateJobRequestMessage(string jobName) + private Pipelines.AgentJobRequestMessage CreateJobRequestMessage(string jobName) { TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = null; - JobEnvironment environment = new JobEnvironment(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); - var jobRequest = new AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, environment, tasks); - return jobRequest as AgentJobRequestMessage; + Guid jobId = Guid.NewGuid(); + return new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, "test", "test", null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); } private JobCancelMessage CreateJobCancelMessage() @@ -72,7 +67,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_messageListener.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_runnerServer.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); runner.Initialize(hc); var settings = new RunnerSettings @@ -177,7 +171,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_configurationManager.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_messageListener.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); var command = new CommandSettings(hc, args); @@ -209,7 +202,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_configurationManager.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_messageListener.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); var command = new CommandSettings(hc, new[] { "run" }); @@ -247,7 +239,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_messageListener.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_runnerServer.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); runner.Initialize(hc); var settings = new RunnerSettings @@ -337,7 +328,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_messageListener.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_runnerServer.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); runner.Initialize(hc); var settings = new RunnerSettings @@ -434,7 +424,6 @@ namespace GitHub.Runner.Common.Tests.Listener hc.SetSingleton(_messageListener.Object); hc.SetSingleton(_promptManager.Object); hc.SetSingleton(_runnerServer.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_configStore.Object); hc.SetSingleton(_updater.Object); diff --git a/src/Test/L0/ProcessInvokerL0.cs b/src/Test/L0/ProcessInvokerL0.cs index 735a35dc2..accf01a07 100644 --- a/src/Test/L0/ProcessInvokerL0.cs +++ b/src/Test/L0/ProcessInvokerL0.cs @@ -53,7 +53,7 @@ namespace GitHub.Runner.Common.Tests Assert.Equal(1, stdout.Count); Assert.Equal("From STDOUT 'ç'", stdout[0]); Assert.True(stderr.Count > 0); - Assert.True(stderr[0].Contains("From STDERR 'ç'")); + Assert.Contains("From STDERR 'ç'", stderr[0]); } } #endif diff --git a/src/Test/L0/TestHostContext.cs b/src/Test/L0/TestHostContext.cs index 6f2b6aed1..622c19bde 100644 --- a/src/Test/L0/TestHostContext.cs +++ b/src/Test/L0/TestHostContext.cs @@ -72,8 +72,6 @@ namespace GitHub.Runner.Common.Tests public CultureInfo DefaultCulture { get; private set; } - public RunMode RunMode { get; set; } - public string TraceFileName { get; private set; } public StartupType StartupType diff --git a/src/Test/L0/Worker/ActionCommandManagerL0.cs b/src/Test/L0/Worker/ActionCommandManagerL0.cs index ac52bd8e8..f2e8d6755 100644 --- a/src/Test/L0/Worker/ActionCommandManagerL0.cs +++ b/src/Test/L0/Worker/ActionCommandManagerL0.cs @@ -203,12 +203,9 @@ namespace GitHub.Runner.Common.Tests.Worker // 1. Job request message (with ACTIONS_STEP_DEBUG = true) TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = new TimelineReference(); - JobEnvironment environment = new JobEnvironment(); - environment.SystemConnection = new ServiceEndpoint(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); + Guid jobId = Guid.NewGuid(); string jobName = "some job name"; - var jobRequest = Pipelines.AgentJobRequestMessageUtil.Convert(new AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, environment, tasks)); + var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, jobName, jobName, null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); jobRequest.Resources.Repositories.Add(new Pipelines.RepositoryResource() { Alias = Pipelines.PipelineConstants.SelfAlias, diff --git a/src/Test/L0/Worker/ExecutionContextL0.cs b/src/Test/L0/Worker/ExecutionContextL0.cs index 0660c4a74..6293a3bef 100644 --- a/src/Test/L0/Worker/ExecutionContextL0.cs +++ b/src/Test/L0/Worker/ExecutionContextL0.cs @@ -23,12 +23,9 @@ namespace GitHub.Runner.Common.Tests.Worker // Arrange: Create a job request message. TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = new TimelineReference(); - JobEnvironment environment = new JobEnvironment(); - environment.SystemConnection = new ServiceEndpoint(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); + Guid jobId = Guid.NewGuid(); string jobName = "some job name"; - var jobRequest = Pipelines.AgentJobRequestMessageUtil.Convert(new AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, environment, tasks)); + var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, jobName, jobName, null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); jobRequest.Resources.Repositories.Add(new Pipelines.RepositoryResource() { Alias = Pipelines.PipelineConstants.SelfAlias, @@ -102,12 +99,9 @@ namespace GitHub.Runner.Common.Tests.Worker // Arrange: Create a job request message. TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = new TimelineReference(); - JobEnvironment environment = new JobEnvironment(); - environment.SystemConnection = new ServiceEndpoint(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); + Guid jobId = Guid.NewGuid(); string jobName = "some job name"; - var jobRequest = Pipelines.AgentJobRequestMessageUtil.Convert(new AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, environment, tasks)); + var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, jobName, jobName, null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); jobRequest.Resources.Repositories.Add(new Pipelines.RepositoryResource() { Alias = Pipelines.PipelineConstants.SelfAlias, @@ -156,12 +150,9 @@ namespace GitHub.Runner.Common.Tests.Worker // Arrange: Create a job request message. TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = new TimelineReference(); - JobEnvironment environment = new JobEnvironment(); - environment.SystemConnection = new ServiceEndpoint(); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); + Guid jobId = Guid.NewGuid(); string jobName = "some job name"; - var jobRequest = Pipelines.AgentJobRequestMessageUtil.Convert(new AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, environment, tasks)); + var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, jobName, jobName, null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); jobRequest.Resources.Repositories.Add(new Pipelines.RepositoryResource() { Alias = Pipelines.PipelineConstants.SelfAlias, @@ -256,10 +247,6 @@ namespace GitHub.Runner.Common.Tests.Worker configurationStore.Setup(x => x.GetSettings()).Returns(new RunnerSettings()); hc.SetSingleton(configurationStore.Object); - // Arrange: Setup the cert configation. - var cert = new Mock(); - hc.SetSingleton(cert.Object); - // Arrange: Create the execution context. hc.SetSingleton(new Mock().Object); diff --git a/src/Test/L0/Worker/JobExtensionL0.cs b/src/Test/L0/Worker/JobExtensionL0.cs index 2fd2c1401..447a760dc 100644 --- a/src/Test/L0/Worker/JobExtensionL0.cs +++ b/src/Test/L0/Worker/JobExtensionL0.cs @@ -20,7 +20,6 @@ namespace GitHub.Runner.Common.Tests.Worker private Mock _directoryManager; private Mock _actionManager; private Mock _jobServerQueue; - private Mock _cert; private Mock _config; private Mock _logger; private Mock _express; @@ -36,7 +35,6 @@ namespace GitHub.Runner.Common.Tests.Worker _jobServerQueue = new Mock(); _config = new Mock(); _logger = new Mock(); - _cert = new Mock(); _express = new Mock(); _containerProvider = new Mock(); _diagnosticLogManager = new Mock(); @@ -110,7 +108,6 @@ namespace GitHub.Runner.Common.Tests.Worker hc.SetSingleton(_actionManager.Object); hc.SetSingleton(_config.Object); hc.SetSingleton(_jobServerQueue.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_express.Object); hc.SetSingleton(_containerProvider.Object); hc.SetSingleton(_directoryManager.Object); diff --git a/src/Test/L0/Worker/JobRunnerL0.cs b/src/Test/L0/Worker/JobRunnerL0.cs index b47faf0e3..8445ce9cf 100644 --- a/src/Test/L0/Worker/JobRunnerL0.cs +++ b/src/Test/L0/Worker/JobRunnerL0.cs @@ -22,7 +22,6 @@ namespace GitHub.Runner.Common.Tests.Worker private CancellationTokenSource _tokenSource; private Mock _jobServer; private Mock _jobServerQueue; - private Mock _cert; private Mock _config; private Mock _extensions; private Mock _stepRunner; @@ -42,7 +41,6 @@ namespace GitHub.Runner.Common.Tests.Worker _jobExtension = new Mock(); _jobServer = new Mock(); _jobServerQueue = new Mock(); - _cert = new Mock(); _stepRunner = new Mock(); _logger = new Mock(); _temp = new Mock(); @@ -64,22 +62,23 @@ namespace GitHub.Runner.Common.Tests.Worker TaskOrchestrationPlanReference plan = new TaskOrchestrationPlanReference(); TimelineReference timeline = new Timeline(Guid.NewGuid()); - JobEnvironment environment = new JobEnvironment(); - environment.Variables[Constants.Variables.System.Culture] = "en-US"; - environment.SystemConnection = new ServiceEndpoint() + Guid jobId = Guid.NewGuid(); + _message = new Pipelines.AgentJobRequestMessage(plan, timeline, jobId, testName, testName, null, null, null, new Dictionary(), new List(), new Pipelines.JobResources(), new Pipelines.ContextData.DictionaryContextData(), new Pipelines.WorkspaceOptions(), new List(), null); + _message.Variables[Constants.Variables.System.Culture] = "en-US"; + _message.Resources.Endpoints.Add(new ServiceEndpoint() { Name = WellKnownServiceEndpointNames.SystemVssConnection, Url = new Uri("https://test.visualstudio.com"), Authorization = new EndpointAuthorization() { Scheme = "Test", - } - }; - environment.SystemConnection.Authorization.Parameters["AccessToken"] = "token"; + Parameters = { + {"AccessToken", "token"} + } + }, + + }); - List tasks = new List(); - Guid JobId = Guid.NewGuid(); - _message = Pipelines.AgentJobRequestMessageUtil.Convert(new AgentJobRequestMessage(plan, timeline, JobId, testName, testName, environment, tasks)); _message.Resources.Repositories.Add(new Pipelines.RepositoryResource() { Alias = Pipelines.PipelineConstants.SelfAlias, @@ -109,7 +108,6 @@ namespace GitHub.Runner.Common.Tests.Worker hc.SetSingleton(_config.Object); hc.SetSingleton(_jobServer.Object); hc.SetSingleton(_jobServerQueue.Object); - hc.SetSingleton(_cert.Object); hc.SetSingleton(_stepRunner.Object); hc.SetSingleton(_extensions.Object); hc.SetSingleton(_temp.Object); diff --git a/src/Test/L0/Worker/WorkerL0.cs b/src/Test/L0/Worker/WorkerL0.cs index b84abb870..bd8989bea 100644 --- a/src/Test/L0/Worker/WorkerL0.cs +++ b/src/Test/L0/Worker/WorkerL0.cs @@ -16,13 +16,11 @@ namespace GitHub.Runner.Common.Tests.Worker { private Mock _processChannel; private Mock _jobRunner; - private Mock _cert; public WorkerL0() { _processChannel = new Mock(); _jobRunner = new Mock(); - _cert = new Mock(); } private Pipelines.AgentJobRequestMessage CreateJobRequestMessage(string jobName) @@ -37,15 +35,15 @@ namespace GitHub.Runner.Common.Tests.Worker serviceEndpoint.Authorization.Parameters.Add("nullValue", null); resources.Endpoints.Add(serviceEndpoint); - List tasks = new List(); - tasks.Add(new Pipelines.TaskStep() + List actions = new List(); + actions.Add(new Pipelines.ActionStep() { Id = Guid.NewGuid(), - Reference = new Pipelines.TaskStepDefinitionReference() + Reference = new Pipelines.RepositoryPathReference() { - Id = Guid.NewGuid(), - Name = "TestTask", - Version = "1.0.0" + RepositoryType = "GitHub", + Name = "actions/test", + Ref = "v1" } }); Guid JobId = Guid.NewGuid(); @@ -69,7 +67,7 @@ namespace GitHub.Runner.Common.Tests.Worker new Pipelines.ContextData.DictionaryContextData() }, }; - var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, new StringToken(null, null, null, "ubuntu"), sidecarContainers, null, variables, new List(), resources, context, null, tasks, null); + var jobRequest = new Pipelines.AgentJobRequestMessage(plan, timeline, JobId, jobName, jobName, new StringToken(null, null, null, "ubuntu"), sidecarContainers, null, variables, new List(), resources, context, null, actions, null); return jobRequest; } @@ -90,7 +88,6 @@ namespace GitHub.Runner.Common.Tests.Worker var worker = new GitHub.Runner.Worker.Worker(); hc.EnqueueInstance(_processChannel.Object); hc.EnqueueInstance(_jobRunner.Object); - hc.SetSingleton(_cert.Object); worker.Initialize(hc); var jobMessage = CreateJobRequestMessage("job1"); var arWorkerMessages = new WorkerMessage[] @@ -142,7 +139,6 @@ namespace GitHub.Runner.Common.Tests.Worker var worker = new GitHub.Runner.Worker.Worker(); hc.EnqueueInstance(_processChannel.Object); hc.EnqueueInstance(_jobRunner.Object); - hc.SetSingleton(_cert.Object); worker.Initialize(hc); var jobMessage = CreateJobRequestMessage("job1"); var cancelMessage = CreateJobCancelMessage(jobMessage.JobId);