// Copyright Epic Games, Inc. All Rights Reserved. using System; using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using System.Xml; using EpicGames.Core; using Microsoft.Extensions.Logging; using UnrealBuildBase; namespace AutomationTool.Tasks { /// /// Parameters for a . /// public class WriteTextFileTaskParameters { /// /// Path to the file to write. /// [TaskParameter] public FileReference File { get; set; } /// /// Optional, whether or not to append to the file rather than overwrite. /// [TaskParameter(Optional = true)] public bool Append { get; set; } /// /// The text to write to the file. /// [TaskParameter(Optional = true)] public string Text { get; set; } /// /// If specified, causes the given list of files to be printed after the given message. /// [TaskParameter(Optional = true, ValidationType = TaskParameterValidationType.FileSpec)] public string Files { get; set; } /// /// Tag to be applied to build products of this task. /// [TaskParameter(Optional = true, ValidationType = TaskParameterValidationType.TagList)] public string Tag { get; set; } } /// /// Writes text to a file. /// [TaskElement("WriteTextFile", typeof(WriteTextFileTaskParameters))] public class WriteTextFileTask : BgTaskImpl { /// /// Parameters for this task. /// readonly WriteTextFileTaskParameters _parameters; /// /// Constructor. /// /// Parameters for this task. public WriteTextFileTask(WriteTextFileTaskParameters parameters) { _parameters = parameters; } /// /// ExecuteAsync the task. /// /// Information about the current job. /// Set of build products produced by this node. /// Mapping from tag names to the set of files they include. public override async Task ExecuteAsync(JobContext job, HashSet buildProducts, Dictionary> tagNameToFileSet) { string fileText = _parameters.Text; // If any files or tagsets are provided, add them to the text output. if (!String.IsNullOrEmpty(_parameters.Files)) { if (!String.IsNullOrWhiteSpace(fileText)) { fileText += Environment.NewLine; } HashSet files = ResolveFilespec(Unreal.RootDirectory, _parameters.Files, tagNameToFileSet); if (files.Any()) { fileText += String.Join(Environment.NewLine, files.Select(f => f.FullName)); } } // Make sure output folder exists. if (!DirectoryReference.Exists(_parameters.File.Directory)) { DirectoryReference.CreateDirectory(_parameters.File.Directory); } if (_parameters.Append) { Logger.LogInformation("{Text}", String.Format("Appending text to file '{0}': {1}", _parameters.File, fileText)); await FileReference.AppendAllTextAsync(_parameters.File, Environment.NewLine + fileText); } else { Logger.LogInformation("{Text}", String.Format("Writing text to file '{0}': {1}", _parameters.File, fileText)); await FileReference.WriteAllTextAsync(_parameters.File, fileText); } // Apply the optional tag to the build products foreach (string tagName in FindTagNamesFromList(_parameters.Tag)) { FindOrAddTagSet(tagNameToFileSet, tagName).Add(_parameters.File); } // Add them to the set of build products buildProducts.Add(_parameters.File); } /// /// Output this task out to an XML writer. /// public override void Write(XmlWriter writer) { Write(writer, _parameters); } /// /// Find all the tags which are used as inputs to this task /// /// The tag names which are read by this task public override IEnumerable FindConsumedTagNames() { foreach (string tagName in FindTagNamesFromFilespec(_parameters.Files)) { yield return tagName; } } /// /// Find all the tags which are modified by this task /// /// The tag names which are modified by this task public override IEnumerable FindProducedTagNames() { return FindTagNamesFromList(_parameters.Tag); } } }