public void Execute(IExecutionContext context, Command command)
        {
            ArgUtil.NotNull(context, nameof(context));
            ArgUtil.NotNull(context.Endpoints, nameof(context.Endpoints));

            var eventProperties = command.Properties;
            var data            = command.Data;

            ServiceEndpoint systemConnection = context.Endpoints.FirstOrDefault(e => string.Equals(e.Name, WellKnownServiceEndpointNames.SystemVssConnection, StringComparison.OrdinalIgnoreCase));

            ArgUtil.NotNull(systemConnection, nameof(systemConnection));
            ArgUtil.NotNull(systemConnection.Url, nameof(systemConnection.Url));

            Uri            projectUrl        = systemConnection.Url;
            VssCredentials projectCredential = VssUtil.GetVssCredential(systemConnection);

            Guid projectId = context.Variables.System_TeamProjectId ?? Guid.Empty;

            ArgUtil.NotEmpty(projectId, nameof(projectId));

            int?buildId = context.Variables.Build_BuildId;

            ArgUtil.NotNull(buildId, nameof(buildId));

            string artifactName;

            if (!eventProperties.TryGetValue(ArtifactAssociateEventProperties.ArtifactName, out artifactName) ||
                string.IsNullOrEmpty(artifactName))
            {
                throw new Exception(StringUtil.Loc("ArtifactNameRequired"));
            }

            string artifactType;

            if (!eventProperties.TryGetValue(ArtifactAssociateEventProperties.ArtifactType, out artifactType))
            {
                artifactType = ArtifactCommandExtensionUtil.InferArtifactResourceType(context, data);
            }

            if (string.IsNullOrEmpty(artifactType))
            {
                throw new Exception(StringUtil.Loc("ArtifactTypeRequired"));
            }
            else if ((artifactType.Equals(ArtifactResourceTypes.Container, StringComparison.OrdinalIgnoreCase) ||
                      artifactType.Equals(ArtifactResourceTypes.FilePath, StringComparison.OrdinalIgnoreCase) ||
                      artifactType.Equals(ArtifactResourceTypes.VersionControl, StringComparison.OrdinalIgnoreCase)) &&
                     string.IsNullOrEmpty(data))
            {
                throw new Exception(StringUtil.Loc("ArtifactLocationRequired"));
            }

            if (!artifactType.Equals(ArtifactResourceTypes.FilePath, StringComparison.OrdinalIgnoreCase) &&
                context.Variables.System_HostType != HostTypes.Build)
            {
                throw new Exception(StringUtil.Loc("AssociateArtifactCommandNotSupported", context.Variables.System_HostType));
            }

            var propertyDictionary = ArtifactCommandExtensionUtil.ExtractArtifactProperties(eventProperties);

            string artifactData = "";

            if (ArtifactCommandExtensionUtil.IsContainerPath(data) ||
                ArtifactCommandExtensionUtil.IsValidServerPath(data))
            {
                //if data is a file container path or a tfvc server path
                artifactData = data;
            }
            else if (ArtifactCommandExtensionUtil.IsUncSharePath(context, data))
            {
                //if data is a UNC share path
                artifactData = new Uri(data).LocalPath;
            }
            else
            {
                artifactData = data ?? string.Empty;
            }

            // queue async command task to associate artifact.
            context.Debug($"Associate artifact: {artifactName} with build: {buildId.Value} at backend.");
            var commandContext = context.GetHostContext().CreateService <IAsyncCommandContext>();

            commandContext.InitializeCommandContext(context, StringUtil.Loc("AssociateArtifact"));
            commandContext.Task = ArtifactCommandExtensionUtil.AssociateArtifactAsync(commandContext,
                                                                                      WorkerUtilities.GetVssConnection(context),
                                                                                      projectId,
                                                                                      buildId.Value,
                                                                                      artifactName,
                                                                                      context.Variables.System_JobId,
                                                                                      artifactType,
                                                                                      artifactData,
                                                                                      propertyDictionary,
                                                                                      context.CancellationToken);
            context.AsyncCommands.Add(commandContext);
        }
        public void Execute(IExecutionContext context, Command command)
        {
            ArgUtil.NotNull(context, nameof(context));
            ArgUtil.NotNull(context.Endpoints, nameof(context.Endpoints));

            var eventProperties = command.Properties;
            var data            = command.Data;

            Guid projectId = context.Variables.System_TeamProjectId ?? Guid.Empty;

            ArgUtil.NotEmpty(projectId, nameof(projectId));

            int?buildId = context.Variables.Build_BuildId;

            ArgUtil.NotNull(buildId, nameof(buildId));

            long?containerId = context.Variables.Build_ContainerId;

            ArgUtil.NotNull(containerId, nameof(containerId));

            string artifactName;

            if (!eventProperties.TryGetValue(ArtifactUploadEventProperties.ArtifactName, out artifactName) ||
                string.IsNullOrEmpty(artifactName))
            {
                throw new Exception(StringUtil.Loc("ArtifactNameRequired"));
            }

            string containerFolder;

            if (!eventProperties.TryGetValue(ArtifactUploadEventProperties.ContainerFolder, out containerFolder) ||
                string.IsNullOrEmpty(containerFolder))
            {
                containerFolder = artifactName;
            }

            var propertyDictionary = ArtifactCommandExtensionUtil.ExtractArtifactProperties(eventProperties);

            // Translate file path back from container path
            string localPath = context.TranslateToHostPath(data);

            if (string.IsNullOrEmpty(localPath))
            {
                throw new Exception(StringUtil.Loc("ArtifactLocationRequired"));
            }

            if (!ArtifactCommandExtensionUtil.IsUncSharePath(context, localPath) && (context.Variables.System_HostType != HostTypes.Build))
            {
                throw new Exception(StringUtil.Loc("UploadArtifactCommandNotSupported", context.Variables.System_HostType));
            }

            string fullPath = Path.GetFullPath(localPath);

            if (!File.Exists(fullPath) && !Directory.Exists(fullPath))
            {
                // if localPath is not a file or folder on disk
                throw new FileNotFoundException(StringUtil.Loc("PathDoesNotExist", localPath));
            }
            else if (Directory.Exists(fullPath) && Directory.EnumerateFiles(fullPath, "*", SearchOption.AllDirectories).FirstOrDefault() == null)
            {
                // if localPath is a folder but the folder contains nothing
                context.Warning(StringUtil.Loc("DirectoryIsEmptyForArtifact", fullPath, artifactName));
                return;
            }

            // queue async command task to associate artifact.
            context.Debug($"Upload artifact: {fullPath} to server for build: {buildId.Value} at backend.");
            var commandContext = context.GetHostContext().CreateService <IAsyncCommandContext>();

            commandContext.InitializeCommandContext(context, StringUtil.Loc("UploadArtifact"));
            commandContext.Task = ArtifactCommandExtensionUtil.UploadArtifactAsync(commandContext,
                                                                                   WorkerUtilities.GetVssConnection(context),
                                                                                   projectId,
                                                                                   containerId.Value,
                                                                                   containerFolder,
                                                                                   buildId.Value,
                                                                                   artifactName,
                                                                                   context.Variables.System_JobId,
                                                                                   propertyDictionary,
                                                                                   fullPath,
                                                                                   context.CancellationToken);
            context.AsyncCommands.Add(commandContext);
        }