2019-12-26 23:01:54 -05:00
// Copyright Epic Games, Inc. All Rights Reserved.
2016-12-08 08:52:44 -05:00
using System ;
2016-05-10 08:49:41 -04:00
using System.Collections.Generic ;
using System.Linq ;
using System.Text ;
using System.Threading.Tasks ;
using System.Xml ;
2017-08-31 12:08:38 -04:00
using Tools.DotNETCommon ;
2016-05-10 08:49:41 -04:00
using UnrealBuildTool ;
namespace AutomationTool.Tasks
{
/// <summary>
/// Parameters for the submit task
/// </summary>
public class SubmitTaskParameters
{
/// <summary>
2019-10-11 16:59:16 -04:00
/// The description for the submitted changelist.
2016-05-10 08:49:41 -04:00
/// </summary>
[TaskParameter]
public string Description ;
/// <summary>
2019-10-11 16:59:16 -04:00
/// The files to submit.
2016-05-10 08:49:41 -04:00
/// </summary>
2016-08-18 10:28:43 -04:00
[TaskParameter(ValidationType = TaskParameterValidationType.FileSpec)]
2016-05-10 08:49:41 -04:00
public string Files ;
/// <summary>
2019-10-11 16:59:16 -04:00
/// The Perforce file type for the submitted files (for example, binary+FS32).
2016-05-10 08:49:41 -04:00
/// </summary>
[TaskParameter(Optional = true)]
public string FileType ;
/// <summary>
2016-08-18 10:28:43 -04:00
/// The workspace name. If specified, a new workspace will be created using the given stream and root directory to submit the files. If not, the current workspace will be used.
2016-05-10 08:49:41 -04:00
/// </summary>
[TaskParameter(Optional=true)]
public string Workspace ;
/// <summary>
2019-10-11 16:59:16 -04:00
/// The stream for the workspace -- defaults to the current stream. Ignored unless the Workspace attribute is also specified.
2016-05-10 08:49:41 -04:00
/// </summary>
[TaskParameter(Optional = true)]
public string Stream ;
/// <summary>
/// Root directory for the stream. If not specified, defaults to the current root directory.
/// </summary>
2018-09-27 16:51:24 -04:00
[TaskParameter(Optional = true)]
public DirectoryReference RootDir ;
2017-03-14 15:48:33 -04:00
/// <summary>
2019-10-11 16:59:16 -04:00
/// Whether to revert unchanged files before attempting to submit.
2017-03-14 15:48:33 -04:00
/// </summary>
[TaskParameter(Optional = true)]
public bool RevertUnchanged ;
2019-01-14 12:11:24 -05:00
/// <summary>
2019-10-11 16:59:16 -04:00
/// Force the submit to happen -- even if a resolve is needed (always accept current version).
2019-01-14 12:11:24 -05:00
/// </summary>
[TaskParameter(Optional = true)]
public bool Force ;
2016-05-10 08:49:41 -04:00
}
/// <summary>
2016-08-18 10:28:43 -04:00
/// Creates a new changelist and submits a set of files to a Perforce stream.
2016-05-10 08:49:41 -04:00
/// </summary>
[TaskElement("Submit", typeof(SubmitTaskParameters))]
public class SubmitTask : CustomTask
{
/// <summary>
/// Parameters for the task
/// </summary>
SubmitTaskParameters Parameters ;
/// <summary>
/// Construct a version task
/// </summary>
/// <param name="InParameters">Parameters for this task</param>
public SubmitTask ( SubmitTaskParameters InParameters )
{
Parameters = InParameters ;
}
/// <summary>
/// Execute the task.
/// </summary>
/// <param name="Job">Information about the current job</param>
/// <param name="BuildProducts">Set of build products produced by this node.</param>
/// <param name="TagNameToFileSet">Mapping from tag names to the set of files they include</param>
2017-07-21 12:42:36 -04:00
public override void Execute ( JobContext Job , HashSet < FileReference > BuildProducts , Dictionary < string , HashSet < FileReference > > TagNameToFileSet )
2016-05-10 08:49:41 -04:00
{
HashSet < FileReference > Files = ResolveFilespec ( CommandUtils . RootDirectory , Parameters . Files , TagNameToFileSet ) ;
2018-04-26 14:11:04 -04:00
if ( Files . Count = = 0 )
{
Log . TraceInformation ( "No files to submit." ) ;
}
else if ( ! CommandUtils . AllowSubmit )
{
Log . TraceWarning ( "Submitting to Perforce is disabled by default. Run with the -submit argument to allow." ) ;
}
else
2016-05-10 08:49:41 -04:00
{
// Get the connection that we're going to submit with
P4Connection SubmitP4 = CommandUtils . P4 ;
if ( Parameters . Workspace ! = null )
{
// Create a brand new workspace
P4ClientInfo Client = new P4ClientInfo ( ) ;
2017-07-21 12:42:36 -04:00
Client . Owner = CommandUtils . P4Env . User ;
2016-05-10 08:49:41 -04:00
Client . Host = Environment . MachineName ;
2017-08-31 12:08:38 -04:00
Client . Stream = Parameters . Stream ? ? CommandUtils . P4Env . Branch ;
2018-09-27 16:51:24 -04:00
Client . RootPath = Parameters . RootDir . FullName ? ? CommandUtils . RootDirectory . FullName ;
2016-05-10 08:49:41 -04:00
Client . Name = Parameters . Workspace ;
Client . Options = P4ClientOption . NoAllWrite | P4ClientOption . Clobber | P4ClientOption . NoCompress | P4ClientOption . Unlocked | P4ClientOption . NoModTime | P4ClientOption . RmDir ;
Client . LineEnd = P4LineEnd . Local ;
CommandUtils . P4 . CreateClient ( Client , AllowSpew : false ) ;
// Create a new connection for it
SubmitP4 = new P4Connection ( Client . Owner , Client . Name ) ;
}
// Get the latest version of it
2018-05-23 21:04:31 -04:00
int NewCL = SubmitP4 . CreateChange ( Description : Parameters . Description . Replace ( "\\n" , "\n" ) ) ;
2016-05-10 08:49:41 -04:00
foreach ( FileReference File in Files )
{
SubmitP4 . Revert ( String . Format ( "-k \"{0}\"" , File . FullName ) ) ;
SubmitP4 . Sync ( String . Format ( "-k \"{0}\"" , File . FullName ) , AllowSpew : false ) ;
SubmitP4 . Add ( NewCL , String . Format ( "\"{0}\"" , File . FullName ) ) ;
SubmitP4 . Edit ( NewCL , String . Format ( "\"{0}\"" , File . FullName ) ) ;
if ( Parameters . FileType ! = null )
{
SubmitP4 . P4 ( String . Format ( "reopen -t \"{0}\" \"{1}\"" , Parameters . FileType , File . FullName ) , AllowSpew : false ) ;
}
}
2017-03-14 15:48:33 -04:00
// Revert any unchanged files
if ( Parameters . RevertUnchanged )
{
SubmitP4 . RevertUnchanged ( NewCL ) ;
if ( SubmitP4 . TryDeleteEmptyChange ( NewCL ) )
{
2018-08-14 18:32:34 -04:00
CommandUtils . LogInformation ( "No files to submit; ignored." ) ;
2017-07-21 12:42:36 -04:00
return ;
2017-03-14 15:48:33 -04:00
}
}
2016-05-10 08:49:41 -04:00
// Submit it
int SubmittedCL ;
2019-01-14 12:11:24 -05:00
SubmitP4 . Submit ( NewCL , out SubmittedCL , Force : Parameters . Force ) ;
2016-05-10 08:49:41 -04:00
if ( SubmittedCL < = 0 )
{
throw new AutomationException ( "Submit failed." ) ;
}
2018-08-14 18:32:34 -04:00
CommandUtils . LogInformation ( "Submitted in changelist {0}" , SubmittedCL ) ;
2016-05-10 08:49:41 -04:00
}
}
/// <summary>
/// Output this task out to an XML writer.
/// </summary>
public override void Write ( XmlWriter Writer )
{
Write ( Writer , Parameters ) ;
}
2016-06-21 09:17:49 -04:00
/// <summary>
/// Find all the tags which are used as inputs to this task
/// </summary>
/// <returns>The tag names which are read by this task</returns>
public override IEnumerable < string > FindConsumedTagNames ( )
{
return FindTagNamesFromFilespec ( Parameters . Files ) ;
}
/// <summary>
/// Find all the tags which are modified by this task
/// </summary>
/// <returns>The tag names which are modified by this task</returns>
public override IEnumerable < string > FindProducedTagNames ( )
{
yield break ;
}
2016-05-10 08:49:41 -04:00
}
}