public BuildItem (string itemName, ITaskItem taskItem) { if (taskItem == null) throw new ArgumentNullException ("taskItem"); this.name = itemName; this.finalItemSpec = taskItem.ItemSpec; this.itemInclude = MSBuildUtils.Escape (taskItem.ItemSpec); this.evaluatedMetadata = (Hashtable) taskItem.CloneCustomMetadata (); this.unevaluatedMetadata = (Hashtable) taskItem.CloneCustomMetadata (); }
public BuildItem(string itemName, ITaskItem taskItem) { if (taskItem == null) { throw new ArgumentNullException("taskItem"); } this.name = itemName; this.finalItemSpec = taskItem.ItemSpec; this.itemInclude = MSBuildUtils.Escape(taskItem.ItemSpec); this.evaluatedMetadata = (Hashtable)taskItem.CloneCustomMetadata(); this.unevaluatedMetadata = (Hashtable)taskItem.CloneCustomMetadata(); }
public TaskItem(ITaskItem sourceItem) { if (sourceItem == null) { throw new ArgumentNullException("sourceItem"); } #if NET_4_0 var ti2 = sourceItem as ITaskItem2; if (ti2 != null) { escapedItemSpec = ti2.EvaluatedIncludeEscaped; escapedMetadata = ti2.CloneCustomMetadataEscaped(); } else #endif { escapedItemSpec = MSBuildUtils.Escape(sourceItem.ItemSpec); escapedMetadata = sourceItem.CloneCustomMetadata(); foreach (string key in new ArrayList(escapedMetadata.Keys)) { escapedMetadata [key] = MSBuildUtils.Escape((string)escapedMetadata [key]); } } }
private static AssemblyAttribute ExtractAttributeFromItem(ITaskItem item) { var type = item.ItemSpec; // Some attributes only allow positional constructor arguments, or the user may just prefer them. // To set those, use metadata names like "_Parameter1", "_Parameter2" etc. // If a parameter index is skipped, it's an error. var customMetadata = item.CloneCustomMetadata() ?? new Dictionary <string, string>(); var orderedParameters = new List <object?>(customMetadata.Count + 1 /* max possible slots needed */); var namedParameters = new Dictionary <string, object?>(); foreach (var customMetadataEntry in customMetadata) { if (customMetadataEntry is not DictionaryEntry entry) { continue; } var name = (string)entry.Key; var valueStr = (string?)entry.Value; if (!CodeGeneratorConfigurationUtility.TryParseConstantValue(valueStr, out var value)) { throw new BuildErrorException(Strings.LiteralAssemblyAttributes.InvalidParameterValueFmt, name); } if (name.StartsWith("_Parameter", StringComparison.OrdinalIgnoreCase)) { if (!int.TryParse(name["_Parameter".Length..], out var index))
private void Write(ITaskItem item) { Write(item.ItemSpec); IDictionary customMetadata = item.CloneCustomMetadata(); Write(customMetadata.Count); foreach (string metadataName in customMetadata.Keys) { Write(metadataName); string valueOrError; try { valueOrError = item.GetMetadata(metadataName); } catch (InvalidProjectFileException e) { valueOrError = e.Message; } // Temporarily try catch all to mitigate frequent NullReferenceExceptions in // the logging code until CopyOnWritePropertyDictionary is replaced with // ImmutableDictionary. Calling into Debug.Fail to crash the process in case // the exception occures in Debug builds. catch (Exception e) { valueOrError = e.Message; Debug.Fail(e.ToString()); } Write(valueOrError); } }
/// <summary> /// Serialize metadata for use as a property value passed into an inner build. /// </summary> /// <param name="item">The item to serialize.</param> /// <returns>A <see cref="string"/> containing the serialized metadata.</returns> /// <remarks>Uses same hex-encoded format as MSBuild's EscapeUtilities.</remarks> public static string SerializeMetadata(ITaskItem item) { var builder = new StringBuilder(); if (item is ITaskItem2 item2) { builder.Append($"Identity={item2.EvaluatedIncludeEscaped}"); var metadata = item2.CloneCustomMetadataEscaped(); foreach (var key in metadata.Keys) { var value = metadata[key]; builder.Append($"|{key.ToString()}={value.ToString()}"); } } else { builder.Append($"Identity="); EscapeValue(item.ItemSpec, builder); var metadata = item.CloneCustomMetadata(); foreach (var key in metadata.Keys) { builder.Append($"|{key.ToString()}="); var value = metadata[key]; EscapeValue(value.ToString(), builder); } } return(builder.ToString()); }
public static void AddMetadata(ITaskItem item, Item itemNode) { if (item.CloneCustomMetadata() is ArrayDictionary <string, string> metadata) { int count = metadata.Count; if (count == 0) { return; } itemNode.EnsureChildrenCapacity(count); var keys = metadata.KeyArray; var values = metadata.ValueArray; for (int i = 0; i < count; i++) { var key = keys[i]; var value = values[i]; var metadataNode = new Metadata { Name = key, Value = value }; // hot path, do not use AddChild // itemNode.AddChild(metadataNode); itemNode.Children.Add(metadataNode); metadataNode.Parent = itemNode; } } }
/// <summary> /// Asserts the equality (or lack thereof) of two ITaskItems. /// </summary> internal static void AreEqual(ITaskItem x, ITaskItem y) { if (x == null && y == null) { return; } if (x == null || y == null) { Assert.True(false, "The two items are not equal -- one of them is null"); } Assert.Equal(x.ItemSpec, y.ItemSpec); IDictionary metadataFromX = x.CloneCustomMetadata(); IDictionary metadataFromY = y.CloneCustomMetadata(); Assert.Equal(metadataFromX.Count, metadataFromY.Count); foreach (object metadataName in metadataFromX.Keys) { if (!metadataFromY.Contains(metadataName)) { Assert.True(false, string.Format("Only one item contains the '{0}' metadata", metadataName)); } else { Assert.Equal(metadataFromX[metadataName], metadataFromY[metadataName]); } } }
public static void CopyMetadataTo(this ITaskItem source, ITaskItem destination, string prefix) { foreach (string key in source.CloneCustomMetadata().Keys.OfType <string>()) { destination.SetMetadata(String.Concat(prefix, key), source.GetMetadata(key)); } }
private string GetAttributeArguments(ITaskItem attributeItem, string namedArgumentString, Func <string, string> quoteString) { // Some attributes only allow positional constructor arguments, or the user may just prefer them. // To set those, use metadata names like "_Parameter1", "_Parameter2" etc. // If a parameter index is skipped, it's an error. IDictionary customMetadata = attributeItem.CloneCustomMetadata(); // Initialize count + 1 to access starting at 1 var orderedParameters = new List <string>(new string[customMetadata.Count + 1]); var namedParameters = new List <string>(); foreach (DictionaryEntry entry in customMetadata) { string name = (string)entry.Key; string value = entry.Value is string?quoteString(entry.Value.ToString()) : entry.Value.ToString(); if (name.StartsWith("_Parameter", StringComparison.OrdinalIgnoreCase)) { if (!int.TryParse(name.Substring("_Parameter".Length), out int index)) { Log.LogErrorWithCodeFromResources("General.InvalidValue", name, "WriteCodeFragment"); return(null); } if (index > orderedParameters.Count || index < 1) { Log.LogErrorWithCodeFromResources("WriteCodeFragment.SkippedNumberedParameter", index); return(null); } // "_Parameter01" and "_Parameter1" would overwrite each other orderedParameters[index - 1] = value; } else { namedParameters.Add($"{name}{namedArgumentString}{value}"); } } bool encounteredNull = false; for (int i = 0; i < orderedParameters.Count; i++) { if (orderedParameters[i] == null) { // All subsequent args should be null, else a slot was missed encounteredNull = true; continue; } if (encounteredNull) { Log.LogErrorWithCodeFromResources("WriteCodeFragment.SkippedNumberedParameter", i + 1 /* back to 1 based */); return(null); } } return(string.Join(", ", orderedParameters.Union(namedParameters).Where(p => !string.IsNullOrWhiteSpace(p)))); }
private ItemInfo CreateItemInfo(ITaskItem item) => new ItemInfo( Intern(item.ItemSpec), item .CloneCustomMetadata() .Cast <KeyValuePair <string, string> >() .Select(metadata => new KeyValuePair <string, string>(Intern(Convert.ToString(metadata.Key)), Intern(Convert.ToString(metadata.Value)))));
private static void LogItemMetadata(Task task, ITaskItem item, MessageImportance importance) { var metadata = item.CloneCustomMetadata(); foreach (var name in metadata.Keys.Cast<string>()) { LogMetadata(task, name, (string)metadata[name], importance); } }
public TaskItem (ITaskItem sourceItem) { if (sourceItem == null) throw new ArgumentNullException ("sourceItem"); this.itemSpec = sourceItem.ItemSpec; this.metadata = sourceItem.CloneCustomMetadata (); }
public TaskItem(ITaskItem sourceItem) { if (sourceItem == null) { throw new ArgumentNullException("sourceItem"); } this.itemSpec = sourceItem.ItemSpec; this.metadata = sourceItem.CloneCustomMetadata(); }
void AddEvaluatedItem(Project project, bool evaluatedTo, ITaskItem taskitem) { if (IsDynamic && evaluatedTo && !KeepDuplicates && ContainsItem(project, taskitem)) { return; } BuildItemGroup big; BuildItem bi = new BuildItem(this); bi.finalItemSpec = ((ITaskItem2)taskitem).EvaluatedIncludeEscaped; foreach (DictionaryEntry de in taskitem.CloneCustomMetadata()) { bi.unevaluatedMetadata.Add((string)de.Key, (string)de.Value); bi.evaluatedMetadata.Add((string)de.Key, (string)de.Value); } project.EvaluatedItemsIgnoringCondition.AddItem(bi); if (evaluatedTo) { project.EvaluatedItems.AddItem(bi); if (!project.EvaluatedItemsByName.ContainsKey(bi.Name)) { big = new BuildItemGroup(null, project, null, true); project.EvaluatedItemsByName.Add(bi.Name, big); } else { big = project.EvaluatedItemsByName [bi.Name]; } big.AddItem(bi); } if (!project.EvaluatedItemsByNameIgnoringCondition.ContainsKey(bi.Name)) { big = new BuildItemGroup(null, project, null, true); project.EvaluatedItemsByNameIgnoringCondition.Add(bi.Name, big); } else { big = project.EvaluatedItemsByNameIgnoringCondition [bi.Name]; } big.AddItem(bi); if (IsDynamic) { AddAndRemoveMetadata(project, bi); } }
public static NameValueCollection GetCustomItemMetadata(ITaskItem taskItem) { var nameValueCollection = new NameValueCollection(); foreach (string key in taskItem.CloneCustomMetadata().Keys) { nameValueCollection.Add(key, taskItem.GetMetadata(key)); } return nameValueCollection; }
public static NameValueCollection GetCustomItemMetadata(ITaskItem taskItem) { var nameValueCollection = new NameValueCollection(); foreach (string key in taskItem.CloneCustomMetadata().Keys) { nameValueCollection.Add(key, taskItem.GetMetadata(key)); } return(nameValueCollection); }
private async Task <IEnumerable <ITaskItem> > GetFailedWorkItemsAsync(ITaskItem job, CancellationToken cancellationToken) { var jobName = job.GetMetadata("Identity"); Log.LogMessage($"Getting status of job {jobName}"); var status = await HelixApi.Job.PassFailAsync(jobName, cancellationToken).ConfigureAwait(false); if (status.Working > 0) { Log.LogError( FailureCategory.Build, $"This task can only be used on completed jobs. There are {status.Working} of {status.Total} unfinished work items."); return(Array.Empty <ITaskItem>()); } List <ITaskItem> failedWorkItemObjects = new List <ITaskItem>(); foreach (string workItemName in status.Failed) { string wi = Helpers.CleanWorkItemName(workItemName); // copy all job metadata into the new item var metadata = job.CloneCustomMetadata(); metadata["JobName"] = jobName; metadata["WorkItemName"] = wi; var consoleUri = HelixApi.Options.BaseUri.AbsoluteUri.TrimEnd('/') + $"/api/2019-06-17/jobs/{jobName}/workitems/{Uri.EscapeDataString(wi)}/console"; metadata["ConsoleOutputUri"] = consoleUri; try { // Do this serially with a delay because total failure can hit throttling var files = await HelixApi.WorkItem.ListFilesAsync(wi, jobName, cancellationToken).ConfigureAwait(false); if (!string.IsNullOrEmpty(AccessToken)) { // Add AccessToken to all file links because the api requires auth if we submitted the job with auth files = files .Select(file => new UploadedFile(file.Name, file.Link + "?access_token=" + AccessToken)) .ToImmutableList(); } metadata["UploadedFiles"] = JsonConvert.SerializeObject(files).Replace("%", "%25"); } catch (Exception ex) { Log.LogWarningFromException(ex); } failedWorkItemObjects.Add(new TaskItem($"{jobName}/{wi}", metadata)); await Task.Delay(DelayBetweenHelixApiCallsInMs); } return(failedWorkItemObjects); }
private static ITaskItem ConvertToLibrary(ITaskItem output) { var fileName = output.ItemSpec; var frameworkNameMoniker = output.GetTargetFrameworkMoniker(); var targetFramework = frameworkNameMoniker.GetShortFrameworkName(); var metadata = output.CloneCustomMetadata(); metadata[Metadata.TargetFramework] = targetFramework; metadata[Metadata.FileTarget] = Path.Combine(targetFramework, Path.GetFileName(fileName)); return(new TaskItem(fileName, metadata)); }
static TaskItem CreateGzipAsset(ITaskItem asset, string gzipSpec) { var result = new TaskItem(gzipSpec, asset.CloneCustomMetadata()); result.SetMetadata("RelatedAsset", asset.ItemSpec); result.SetMetadata("AssetRole", "Alternative"); result.SetMetadata("AssetTraitName", "Content-Encoding"); result.SetMetadata("AssetTraitValue", "gzip"); return(result); }
public void AddMetadata(ITaskItem item, Item itemNode) { var cloned = item.CloneCustomMetadata(); if (cloned is ArrayDictionary <string, string> metadata) { int count = metadata.Count; if (count == 0) { return; } itemNode.EnsureChildrenCapacity(count); var keys = metadata.KeyArray; var values = metadata.ValueArray; for (int i = 0; i < count; i++) { var key = keys[i]; var value = values[i]; var metadataNode = new Metadata { Name = key, Value = value }; // hot path, do not use AddChild // itemNode.AddChild(metadataNode); itemNode.Children.Add(metadataNode); metadataNode.Parent = itemNode; } } else { if (cloned is ICollection collection) { itemNode.EnsureChildrenCapacity(collection.Count); } foreach (DictionaryEntry metadataName in cloned) { var metadataNode = new Metadata { Name = SoftIntern(Convert.ToString(metadataName.Key)), Value = SoftIntern(Convert.ToString(metadataName.Value)) }; itemNode.Children.Add(metadataNode); metadataNode.Parent = itemNode; } } }
private static ITaskItem ConvertToPackageFile(ITaskItem output) { var fileName = output.ItemSpec; var frameworkNameMoniker = output.GetTargetFrameworkMoniker(); var packageDirectory = output.GetPackageDirectory(); var targetFramework = frameworkNameMoniker.GetShortFrameworkName(); var metadata = output.CloneCustomMetadata(); metadata[Metadata.TargetFramework] = targetFramework; metadata[Metadata.PackageDirectory] = packageDirectory.ToString(); metadata[Metadata.FileTarget] = packageDirectory.Combine(targetFramework, Path.GetFileName(fileName)); return new TaskItem(fileName, metadata); }
private async Task <IEnumerable <ITaskItem> > GetFailedWorkItemsAsync(ITaskItem job, CancellationToken cancellationToken) { var jobName = job.GetMetadata("Identity"); Log.LogMessage($"Getting status of job {jobName}"); var status = await HelixApi.RetryAsync( () => HelixApi.Job.PassFailAsync(jobName, cancellationToken), LogExceptionRetry, cancellationToken); if (status.Working > 0) { Log.LogError( FailureCategory.Build, $"This task can only be used on completed jobs. There are {status.Working} of {status.Total} unfinished work items."); return(Array.Empty <ITaskItem>()); } return(await Task.WhenAll(status.Failed.Select(async wi => { // copy all job metadata into the new item var metadata = job.CloneCustomMetadata(); metadata["JobName"] = jobName; metadata["WorkItemName"] = wi; var consoleUri = HelixApi.BaseUri.AbsoluteUri.TrimEnd('/') + $"/api/2019-06-17/jobs/{jobName}/workitems/{Uri.EscapeDataString(wi)}/console"; metadata["ConsoleOutputUri"] = consoleUri; try { var files = await HelixApi.RetryAsync( () => HelixApi.WorkItem.ListFilesAsync(wi, jobName, cancellationToken), LogExceptionRetry, cancellationToken); if (!string.IsNullOrEmpty(AccessToken)) { // Add AccessToken to all file links because the api requires auth if we submitted the job with auth files = files .Select(file => new UploadedFile(file.Name, file.Link + "?access_token=" + AccessToken)) .ToImmutableList(); } metadata["UploadedFiles"] = JsonConvert.SerializeObject(files); } catch (Exception ex) { Log.LogWarningFromException(ex); } return new TaskItem($"{jobName}/{wi}", metadata); }))); }
/// <summary> /// Creates a new ITaskItem with the contents of the old one. /// </summary> private ITaskItem CreateNewTaskItemFrom(ITaskItem copyFrom) { ITaskItem2 copyFromAsITaskItem2 = copyFrom as ITaskItem2; string escapedItemSpec = null; string escapedDefiningProject = null; Dictionary <string, string> escapedMetadata = null; if (copyFromAsITaskItem2 != null) { escapedItemSpec = copyFromAsITaskItem2.EvaluatedIncludeEscaped; escapedDefiningProject = copyFromAsITaskItem2.GetMetadataValueEscaped(FileUtilities.ItemSpecModifiers.DefiningProjectFullPath); IDictionary nonGenericEscapedMetadata = copyFromAsITaskItem2.CloneCustomMetadataEscaped(); if (nonGenericEscapedMetadata is Dictionary <string, string> ) { escapedMetadata = (Dictionary <string, string>)nonGenericEscapedMetadata; } else { escapedMetadata = new Dictionary <string, string>(StringComparer.OrdinalIgnoreCase); foreach (object key in nonGenericEscapedMetadata.Keys) { escapedMetadata[(string)key] = (string)nonGenericEscapedMetadata[key] ?? String.Empty; } } } else { // If we don't have ITaskItem2 to fall back on, we have to make do with the fact that // CloneCustomMetadata, GetMetadata, & ItemSpec returns unescaped values, and // TaskParameterTaskItem's constructor expects escaped values, so escaping them all // is the closest approximation to correct we can get. escapedItemSpec = EscapingUtilities.Escape(copyFrom.ItemSpec); escapedDefiningProject = EscapingUtilities.EscapeWithCaching(copyFrom.GetMetadata(FileUtilities.ItemSpecModifiers.DefiningProjectFullPath)); IDictionary customMetadata = copyFrom.CloneCustomMetadata(); escapedMetadata = new Dictionary <string, string>(StringComparer.OrdinalIgnoreCase); if (customMetadata != null && customMetadata.Count > 0) { foreach (string key in customMetadata.Keys) { escapedMetadata.Add(key, EscapingUtilities.Escape((string)customMetadata[key] ?? String.Empty)); } } } TaskParameterTaskItem taskItem = new TaskParameterTaskItem(escapedItemSpec, escapedDefiningProject, escapedMetadata); return(taskItem); }
private void Write(ITaskItem item) { Write(item.ItemSpec); IDictionary customMetadata = item.CloneCustomMetadata(); Write(customMetadata.Count); foreach (string metadataName in customMetadata.Keys) { Write(metadataName); Write(item.GetMetadata(metadataName)); } }
private static ITaskItem ConvertToPackageFile(ITaskItem output) { var fileName = output.ItemSpec; var frameworkNameMoniker = output.GetTargetFrameworkMoniker(); var packageDirectory = output.GetPackageDirectory(); var targetFramework = frameworkNameMoniker.GetShortFrameworkName(); var metadata = output.CloneCustomMetadata(); metadata[Metadata.TargetFramework] = targetFramework; metadata[Metadata.PackageDirectory] = packageDirectory.ToString(); metadata[Metadata.FileTarget] = packageDirectory.Combine(targetFramework, Path.GetFileName(fileName)); return(new TaskItem(fileName, metadata)); }
private IEnumerable <XElement> CreateMetadataFromItem(ITaskItem item) { if (this.IncludeMetadata) { var metadata = item.CloneCustomMetadata(); return(metadata.Keys .OfType <object> () .Select(key => new XElement(XmlNs + key.ToString(), metadata[key].ToString()))); } return(Enumerable.Empty <XElement> ()); }
private static void CopyMetadata(ProjectItem targetItem, ITaskItem sourceItem) { foreach (ProjectMetadata projectMetadata in targetItem.Metadata.ToArray()) { if (String.IsNullOrEmpty(sourceItem.GetMetadata(projectMetadata.Name))) { targetItem.Metadata.Remove(projectMetadata); } } foreach (DictionaryEntry entry in sourceItem.CloneCustomMetadata()) { targetItem.SetMetadataValue((string)entry.Key, (string)entry.Value); } }
public TaskItem (ITaskItem sourceItem) { if (sourceItem == null) throw new ArgumentNullException ("sourceItem"); var ti2 = sourceItem as ITaskItem2; if (ti2 != null) { escapedItemSpec = ti2.EvaluatedIncludeEscaped; escapedMetadata = ti2.CloneCustomMetadataEscaped (); } else { escapedItemSpec = MSBuildUtils.Escape (sourceItem.ItemSpec); escapedMetadata = sourceItem.CloneCustomMetadata (); foreach (string key in new ArrayList (escapedMetadata.Keys)) escapedMetadata [key] = MSBuildUtils.Escape ((string)escapedMetadata [key]); } }
public static IEnumerable <KeyValuePair <string, string> > EnumerateMetadata(this ITaskItem taskItem) { if (taskItem is IMetadataContainer container) { // This is the common case: most implementations should implement this for quick access return(container.EnumerateMetadata()); } // This runs if ITaskItem is Microsoft.Build.Utilities.TaskItem from Microsoft.Build.Utilities.v4.0.dll // that is loaded from the GAC. IDictionary customMetadata = taskItem.CloneCustomMetadata(); if (customMetadata is IEnumerable <KeyValuePair <string, string> > enumerableMetadata) { return(enumerableMetadata); } // In theory this should never be reachable. var list = new KeyValuePair <string, string> [customMetadata.Count]; int i = 0; foreach (string metadataName in customMetadata.Keys) { string valueOrError; try { valueOrError = taskItem.GetMetadata(metadataName); } // Temporarily try catch all to mitigate frequent NullReferenceExceptions in // the logging code until CopyOnWritePropertyDictionary is replaced with // ImmutableDictionary. Calling into Debug.Fail to crash the process in case // the exception occurres in Debug builds. catch (Exception e) { valueOrError = e.Message; Debug.Fail(e.ToString()); } list[i] = new KeyValuePair <string, string>(metadataName, valueOrError); i += 1; } return(list); }
private static ITaskItem ConvertToPackageFile(ITaskItem output) { var fileName = output.ItemSpec; var targetPath = output.GetMetadata("TargetPath"); targetPath = string.IsNullOrEmpty(targetPath) ? Path.GetFileName(fileName) : targetPath; var frameworkNameMoniker = output.GetTargetFrameworkMoniker(); var packageDirectory = output.GetPackageDirectory(); var targetSubdirectory = output.GetTargetSubdirectory(); var targetFramework = packageDirectory == PackageDirectory.Analyzers ? frameworkNameMoniker.GetAnalyzersFrameworkName() : frameworkNameMoniker.GetShortFrameworkName(); var metadata = output.CloneCustomMetadata(); metadata[Metadata.TargetFramework] = targetFramework; metadata[Metadata.PackageDirectory] = packageDirectory.ToString(); metadata[Metadata.TargetSubdirectory] = targetSubdirectory; metadata[Metadata.FileTarget] = packageDirectory.Combine(targetFramework, targetSubdirectory, targetPath); return new TaskItem(fileName, metadata); }
public void TestCloneCustomMetadata() { item = new TaskItem(); item.SetMetadata("AAA", "111"); item.SetMetadata("aaa", "222"); item.SetMetadata("BBB", "111"); string [] metakeys = new string [] { "aaa", "BBB" }; IDictionary meta = item.CloneCustomMetadata(); Assert.IsTrue(CompareStringCollections(meta.Keys, metakeys), "A1"); metakeys [0] = "aAa"; Assert.IsTrue(CompareStringCollections(meta.Keys, metakeys), "A2"); Assert.AreEqual("222", meta ["aaa"], "A3"); Assert.AreEqual("222", meta ["AAA"], "A4"); Assert.AreEqual("222", meta ["aAa"], "A5"); Assert.AreEqual("111", meta ["BbB"], "A5"); }
public void TestCloneCustomMetadata () { item = new TaskItem (); item.SetMetadata ("AAA", "111"); item.SetMetadata ("aaa", "222"); item.SetMetadata ("BBB", "111"); string [] metakeys = new string [] { "aaa", "BBB" }; IDictionary meta = item.CloneCustomMetadata (); Assert.IsTrue (CompareStringCollections (meta.Keys, metakeys), "A1"); metakeys [0] = "aAa"; Assert.IsTrue (CompareStringCollections (meta.Keys, metakeys), "A2"); Assert.AreEqual ("222", meta ["aaa"], "A3"); Assert.AreEqual ("222", meta ["AAA"], "A4"); Assert.AreEqual ("222", meta ["aAa"], "A5"); Assert.AreEqual ("111", meta ["BbB"], "A5"); }
void AddEvaluatedItem(Project project, bool evaluatedTo, ITaskItem taskitem) { BuildItemGroup big; BuildItem bi = new BuildItem(this); bi.finalItemSpec = taskitem.ItemSpec; foreach (DictionaryEntry de in taskitem.CloneCustomMetadata()) { bi.unevaluatedMetadata.Add((string)de.Key, (string)de.Value); bi.evaluatedMetadata.Add((string)de.Key, (string)de.Value); } project.EvaluatedItemsIgnoringCondition.AddItem(bi); if (evaluatedTo) { project.EvaluatedItems.AddItem(bi); if (!project.EvaluatedItemsByName.ContainsKey(bi.Name)) { big = new BuildItemGroup(null, project, null, true); project.EvaluatedItemsByName.Add(bi.Name, big); } else { big = project.EvaluatedItemsByName [bi.Name]; } big.AddItem(bi); } if (!project.EvaluatedItemsByNameIgnoringCondition.ContainsKey(bi.Name)) { big = new BuildItemGroup(null, project, null, true); project.EvaluatedItemsByNameIgnoringCondition.Add(bi.Name, big); } else { big = project.EvaluatedItemsByNameIgnoringCondition [bi.Name]; } big.AddItem(bi); }
private static ITaskItem ConvertToPackageFile(ITaskItem output) { var fileName = output.ItemSpec; var targetPath = output.GetMetadata("TargetPath"); targetPath = string.IsNullOrEmpty(targetPath) ? Path.GetFileName(fileName) : targetPath; var frameworkNameMoniker = output.GetTargetFrameworkMoniker(); var packageDirectory = output.GetPackageDirectory(); var targetSubdirectory = output.GetTargetSubdirectory(); var targetFramework = packageDirectory == PackageDirectory.Analyzers ? frameworkNameMoniker.GetAnalyzersFrameworkName() : frameworkNameMoniker.GetShortFrameworkName(); var metadata = output.CloneCustomMetadata(); metadata[Metadata.TargetFramework] = targetFramework; metadata[Metadata.PackageDirectory] = packageDirectory.ToString(); metadata[Metadata.TargetSubdirectory] = targetSubdirectory; metadata[Metadata.FileTarget] = packageDirectory.Combine(targetFramework, targetSubdirectory, targetPath); return(new TaskItem(fileName, metadata)); }
/// <summary> /// Parses the <paramref name="taskItem" /> and transforms it to a <see cref="ObjDict" /> /// . Handles string, int and double values only. /// </summary> /// <param name="taskItem"></param> /// <param name="nodeNames"></param> /// <returns></returns> private ObjDict TaskItemToNodeDictionary(ITaskItem taskItem, out string[] nodeNames) { var props = new ObjDict(); nodeNames = taskItem.ItemSpec == null || string.IsNullOrWhiteSpace(taskItem.ItemSpec) ? null : taskItem.ItemSpec .Split('.') .Where(s => string.IsNullOrEmpty(s) == false) .ToArray(); foreach (DictionaryEntry propKeyValue in taskItem.CloneCustomMetadata()) { var propName = (string)propKeyValue.Key; var propValue = (string)propKeyValue.Value; if (propName.StartsWith("\"") && propName.EndsWith("\"")) { props[propName] = propValue; } else if (int.TryParse(propValue, out int propIntValue)) { props[propName] = propIntValue; } else if (double.TryParse(propValue, out double propDoubleValue)) { props[propName] = propDoubleValue; } else { props[propName] = propValue; } } return(props); }
private void Publish(IS3Client client, ITaskItem sourceFolder, string bucket, string destinationFolder, bool publicRead, int timeoutMilliseconds) { var dirInfo = new DirectoryInfo(sourceFolder.GetMetadata("Identity")); var headers = MsBuildHelpers.GetCustomItemMetadata(sourceFolder); var files = dirInfo.GetFiles(); foreach (var f in files) { Logger.LogMessage(MessageImportance.Normal, string.Format("Copying file {0}", f.FullName)); client.PutFileWithHeaders(bucket, CreateRelativePath(destinationFolder, f.Name), f.FullName, headers, publicRead, timeoutMilliseconds); } var dirs = dirInfo.GetDirectories(); foreach (var d in dirs) { Publish(client, new TaskItem(d.FullName, sourceFolder.CloneCustomMetadata()), bucket, CreateRelativePath(destinationFolder, d.Name), publicRead, timeoutMilliseconds); } }
public PropertyValue(ITaskItem propertyValue, Dictionary <string, PropertyInfo> propertyNames) { Value = propertyValue.ItemSpec; var name = propertyValue.GetMetadata(PropertyName); PropertyInfo property; if (!propertyNames.TryGetValue(name, out property)) { throw new Exception($"PropertyValue {Value} contained unknown property name \"{name}\""); } Property = property; imports = propertyValue.GetMetadata(ImportsName); compatibleWith = propertyValue.GetMetadata(CompatibleWithName); var customMetadata = propertyValue.CloneCustomMetadata(); AdditionalProperties = customMetadata.Keys.Cast <string>() .Where(k => !s_excludedMetadata.Contains(k)) .Select(k => new KeyValuePair <string, string>(k, (string)customMetadata[k])) .ToArray(); }
private void Write(ITaskItem item) { Write(item.ItemSpec); IDictionary customMetadata = item.CloneCustomMetadata(); Write(customMetadata.Count); foreach (string metadataName in customMetadata.Keys) { Write(metadataName); string valueOrError; try { valueOrError = item.GetMetadata(metadataName); } catch (InvalidProjectFileException e) { valueOrError = e.Message; } Write(valueOrError); } }
/// <summary> /// This constructor creates a new virtual (non-persisted) item based /// on a ITaskItem object that was emitted by a task. /// </summary> public BuildItem(string itemName, ITaskItem taskItem) { ErrorUtilities.VerifyThrowArgumentNull(taskItem, "taskItem"); string itemInclude = EscapingUtilities.Escape(taskItem.ItemSpec); BuildItemHelper ( null /* this is a virtual item with no backing XML */, itemName, itemInclude, false, /* PERF NOTE: don't waste time creating a new custom metadata cache, * because we're going to clone the given task item's custom metadata */ null /* no definition library */ ); IDictionary rawSourceTable = taskItem.CloneCustomMetadata(); // Go through and escape the metadata as necessary. string[] keys = new string[rawSourceTable.Count]; rawSourceTable.Keys.CopyTo(keys, 0); foreach (string singleMetadataName in keys) { string singleMetadataValue = (string) rawSourceTable[singleMetadataName]; rawSourceTable[singleMetadataName] = EscapingUtilities.Escape(singleMetadataValue); } this.unevaluatedCustomMetadata = new CopyOnWriteHashtable(rawSourceTable, StringComparer.OrdinalIgnoreCase); this.evaluatedCustomMetadata = new CopyOnWriteHashtable(rawSourceTable, StringComparer.OrdinalIgnoreCase); this.isPartOfProjectManifest = false; }
void AddEvaluatedItem (Project project, bool evaluatedTo, ITaskItem taskitem) { if (IsDynamic && evaluatedTo && !KeepDuplicates && ContainsItem (project, taskitem)) return; BuildItemGroup big; BuildItem bi = new BuildItem (this); bi.finalItemSpec = taskitem.ItemSpec; foreach (DictionaryEntry de in taskitem.CloneCustomMetadata ()) { bi.unevaluatedMetadata.Add ((string) de.Key, (string) de.Value); bi.evaluatedMetadata.Add ((string) de.Key, (string) de.Value); } project.EvaluatedItemsIgnoringCondition.AddItem (bi); if (evaluatedTo) { project.EvaluatedItems.AddItem (bi); if (!project.EvaluatedItemsByName.ContainsKey (bi.Name)) { big = new BuildItemGroup (null, project, null, true); project.EvaluatedItemsByName.Add (bi.Name, big); } else { big = project.EvaluatedItemsByName [bi.Name]; } big.AddItem (bi); } if (!project.EvaluatedItemsByNameIgnoringCondition.ContainsKey (bi.Name)) { big = new BuildItemGroup (null, project, null, true); project.EvaluatedItemsByNameIgnoringCondition.Add (bi.Name, big); } else { big = project.EvaluatedItemsByNameIgnoringCondition [bi.Name]; } big.AddItem (bi); if (IsDynamic) AddAndRemoveMetadata (project, bi); }
private IEnumerable<XElement> CreateMetadataFromItem(ITaskItem item) { if (this.IncludeMetadata) { var metadata = item.CloneCustomMetadata(); return metadata.Keys .OfType<object> () .Select (key => new XElement (XmlNs + key.ToString (), metadata[key].ToString ())); } return Enumerable.Empty<XElement> (); }
private string GetAttributeArguments(ITaskItem attributeItem, string namedArgumentString) { // Some attributes only allow positional constructor arguments, or the user may just prefer them. // To set those, use metadata names like "_Parameter1", "_Parameter2" etc. // If a parameter index is skipped, it's an error. IDictionary customMetadata = attributeItem.CloneCustomMetadata(); // Initialize count + 1 to access starting at 1 List<string> orderedParameters = new List<string>(new string[customMetadata.Count + 1]); List<string> namedParameters = new List<string>(); foreach (DictionaryEntry entry in customMetadata) { string name = (string) entry.Key; string value = entry.Value is string ? $@"""{entry.Value}""" : entry.Value.ToString(); if (name.StartsWith("_Parameter", StringComparison.OrdinalIgnoreCase)) { int index; if (!int.TryParse(name.Substring("_Parameter".Length), out index)) { Log.LogErrorWithCodeFromResources("General.InvalidValue", name, "WriteCodeFragment"); return null; } if (index > orderedParameters.Count || index < 1) { Log.LogErrorWithCodeFromResources("WriteCodeFragment.SkippedNumberedParameter", index); return null; } // "_Parameter01" and "_Parameter1" would overwrite each other orderedParameters[index - 1] = value; } else { namedParameters.Add($"{name}{namedArgumentString}{value}"); } } bool encounteredNull = false; for (int i = 0; i < orderedParameters.Count; i++) { if (orderedParameters[i] == null) { // All subsequent args should be null, else a slot was missed encounteredNull = true; continue; } if (encounteredNull) { Log.LogErrorWithCodeFromResources("WriteCodeFragment.SkippedNumberedParameter", i + 1 /* back to 1 based */); return null; } } return string.Join(", ", orderedParameters.Union(namedParameters).Where(p => !string.IsNullOrWhiteSpace(p))); }
/// <summary> /// Asserts the equality (or lack thereof) of two ITaskItems. /// </summary> internal static void AreEqual(ITaskItem x, ITaskItem y) { if (x == null && y == null) { return; } if (x == null || y == null) { Assert.True(false, "The two items are not equal -- one of them is null"); } Assert.Equal(x.ItemSpec, y.ItemSpec); IDictionary metadataFromX = x.CloneCustomMetadata(); IDictionary metadataFromY = y.CloneCustomMetadata(); Assert.Equal(metadataFromX.Count, metadataFromY.Count); foreach (object metadataName in metadataFromX.Keys) { if (!metadataFromY.Contains(metadataName)) { Assert.True(false, string.Format("Only one item contains the '{0}' metadata", metadataName)); } else { Assert.Equal(metadataFromX[metadataName], metadataFromY[metadataName]); } } }
private bool GenerateCodeFile(ITaskItem item) { var codeFile = item.ItemSpec; string[] conditionalConstants; string className; string[] classModifiers; ClassMemberTypes classMemberType; if (GetConditionalConstants(item, out conditionalConstants) && GetClassName(item, out className) && GetClassModifiers(item, out classModifiers) && GetClassMemberType(item, out classMemberType)) { if (File.Exists(codeFile) && !ForceOverwrite) { Log.LogError("Code file \"{0}\" already exist.", codeFile); return false; } using (var writer = File.CreateText(codeFile)) { var dict = item.CloneCustomMetadata(); if (conditionalConstants.Length > 0) writer.WriteLine(string.Format("#if {0}", string.Join(" && ", conditionalConstants))); if (classModifiers.Length > 0) writer.Write(string.Format("{0} ", string.Join(" ", classModifiers))); writer.WriteLine(string.Format("class {0}", className)); writer.WriteLine("{"); foreach (DictionaryEntry e in dict) { var name = e.Key.ToString(); if (name.Contains("-")) continue; WriteMember(writer, classMemberType, name, e.Value.ToString()); } writer.WriteLine("}"); if (conditionalConstants.Length > 0) writer.WriteLine("#endif"); } return true; } return false; }