使用 FindMatchingFiles 工作流活动的 MatchPattern 属性

发布于 2024-10-08 21:28:30 字数 376 浏览 10 评论 0原文

我正在使用 TFS 2010 Team Build 自定义构建过程模板的默认工作流程。有一个名为 FindMatchingFiles 的活动允许使用 MatchPattern 属性中定义的模式搜索特定文件。如果我只指定一个文件扩展名,它就有效。示例:

String.Format("{0}\\**\\\*.msi", SourcesDirectory)

但我也想包含 *.exe。尝试以下模式但不起作用:

String.Format("{0}\\**\\\*.(msi|exe)", SourcesDirectory)

任何人都可以告诉我如何纠正它?

I'm customizing the default workflow of build process template using TFS 2010 Team Build. There is an activity named FindMatchingFiles allows to search for specific files with a pattern defined in MatchPattern property. It works if I only specify one file extension. Example:

String.Format("{0}\\**\\\*.msi", SourcesDirectory)

But I would like to include *.exe as well. Trying following pattern but it doesn't work:

String.Format("{0}\\**\\\*.(msi|exe)", SourcesDirectory)

Anyone could show me how to correct it?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

漫漫岁月 2024-10-15 21:28:30

您可以使用 String.Format("{0}\**\*.msi;{0}\**\*.exe", SourcesDirectory)

You can use String.Format("{0}\**\*.msi;{0}\**\*.exe", SourcesDirectory)

人│生佛魔见 2024-10-15 21:28:30

FindMatchingFiles 活动MatchPattern 属性使用

searchPattern 参数支持的语法Directory.GetFiles(String, String) 方法。

这意味着您无法组合多个扩展。您需要调用 FindMatchingFiles 活动两次。然后,您可以在使用时合并这两个调用的结果(即,如果您的结果是 msiFilesexeFiles,则可以使用 msiFiles.Concat(exeFiles) 作为 ForEach 的输入)。

但是,正如您在 @antwoord 的回答 中看到的,该活动实际上似乎接受以分号分隔的模式列表,与Directory.GetFiles不同。

The FindMatchingFiles activity's MatchPattern property uses the

Syntax that is supported by the searchPattern argument of the Directory.GetFiles(String, String) method.

That means that you can't combine multiple extensions. You'll need to call the FindMatchingFiles activity twice. You can then combine the results of those two calls when you use them (i.e. if your results are msiFiles and exeFiles, you can use msiFiles.Concat(exeFiles) as the input to a ForEach).

However, as you can see with @antwoord's answer, the activity does actually seem to accept a semi-colon delimited list of patterns, unlike Directory.GetFiles.

青衫负雪 2024-10-15 21:28:30

FindMatchingFiles 有一些奇怪的搜索模式。这是代码(使用 ILSpy 反编译),因此您可以测试搜索模式,而无需启动新的构建。

它包含位于以下位置 (Z:) 的硬编码根目录

List<string> matchingDirectories = GetMatchingDirectories(@"Z:", matchPattern.Substring(0, num), 0);

代码:

using System;
using System.Collections.Generic;
using System.IO;

namespace DirectoryGetFiles
{

    ////    Use the FindMatchingFiles activity to find files. Specify the search criteria in the MatchPattern (String) property.
    ////    In this property, you can specify an argument that includes the following elements: 
    ////        Syntax that is supported by the searchPattern argument of the Directory GetFiles(String, String) method.
    ////
    ////        ** to specify a recursive search. For example:
    ////            To search the sources directory for text files, you could specify something that resembles the following
    ////            value for the MatchPattern property: String.Format("{0}\**\*.txt", SourcesDirectory).
    ////            
    ////            To search the sources directory for text files in one or more subdirectories that are called txtfiles, 
    ////            you could specify something that resembles the following value for the MatchPattern property: 
    ////            String.Format("{0}\**\txtfiles\*.txt", SourcesDirectory).

    class Program
    {
        static void Main(string[] args)
        {
            string searchPattern = @"_PublishedWebsites\Web\Scripts\jasmine-specs**\*.js";
            var results = Execute(searchPattern);

            foreach (var i in results)
            {
                Console.WriteLine("found: {0}", i);
            }

            Console.WriteLine("Done...");
            Console.ReadLine();
        }

        private static IEnumerable<string> Execute(string pattern)
        {
            string text = pattern;
            text = text.Replace(";;", "\0");
            var hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase);
            string[] array = text.Split(new char[]
    {
        ';'
    }, StringSplitOptions.RemoveEmptyEntries);

            for (int i = 0; i < array.Length; i++)
            {
                string text2 = array[i];
                string text3 = text2.Replace("\0", ";");
                if (IsValidPattern(text3))
                {
                    List<string> list = ComputeMatchingPaths(text3);
                    if (list.Count > 0)
                    {
                        using (List<string>.Enumerator enumerator = list.GetEnumerator())
                        {
                            while (enumerator.MoveNext())
                            {
                                string current = enumerator.Current;
                                hashSet.Add(current);
                            }
                            goto IL_15C;
                        }
                    }
                    ////Message = ActivitiesResources.Format("NoMatchesForSearchPattern", new object[]
                }
                else
                {
                    ////       Message = ActivitiesResources.Format("InvalidSearchPattern", new object[]
                }

            IL_15C: ;
            }

            return hashSet;//.OrderBy((string x) => x, FileSpec.TopDownComparer);
        }

        private static bool IsValidPattern(string pattern)
        {
            string text = "**" + Path.DirectorySeparatorChar;
            int num = pattern.IndexOf(text, StringComparison.Ordinal);
            return (num < 0 || (pattern.IndexOf(text, num + text.Length, StringComparison.OrdinalIgnoreCase) <= 0 && pattern.IndexOf(Path.DirectorySeparatorChar, num + text.Length) <= 0)) && pattern[pattern.Length - 1] != Path.DirectorySeparatorChar;
        }

        private static List<string> ComputeMatchingPaths(string matchPattern)
        {
            List<string> list = new List<string>();
            string text = "**" + Path.DirectorySeparatorChar;
            int num = matchPattern.IndexOf(text, 0, StringComparison.OrdinalIgnoreCase);
            if (num >= 0)
            {
                List<string> matchingDirectories = GetMatchingDirectories(@"Z:", matchPattern.Substring(0, num), 0);
                string searchPattern = matchPattern.Substring(num + text.Length);
                using (List<string>.Enumerator enumerator = matchingDirectories.GetEnumerator())
                {
                    while (enumerator.MoveNext())
                    {
                        string current = enumerator.Current;
                        list.AddRange(Directory.GetFiles(current, searchPattern, SearchOption.AllDirectories));
                    }
                    return list;
                }
            }
            int num2 = matchPattern.LastIndexOf(Path.DirectorySeparatorChar);
            if (num2 >= 0)
            {
                List<string> matchingDirectories2 = GetMatchingDirectories(string.Empty, matchPattern.Substring(0, num2 + 1), 0);
                string searchPattern2 = matchPattern.Substring(num2 + 1);
                using (List<string>.Enumerator enumerator2 = matchingDirectories2.GetEnumerator())
                {
                    while (enumerator2.MoveNext())
                    {
                        string current2 = enumerator2.Current;
                        try
                        {
                            list.AddRange(Directory.GetFiles(current2, searchPattern2, SearchOption.TopDirectoryOnly));
                        }
                        catch
                        {
                        }
                    }
                    return list;
                }
            }
            try
            {
                list.AddRange(Directory.GetFiles(Directory.GetCurrentDirectory(), matchPattern, SearchOption.TopDirectoryOnly));
            }
            catch
            {
            }
            return list;
        }

        private static List<string> GetMatchingDirectories(string rootDir, string pattern, int level)
        {
            if (level > 129)
            {
                return new List<string>();
            }
            List<string> list = new List<string>();
            int num = pattern.IndexOf('*');
            if (num >= 0)
            {
                int num2 = pattern.Substring(0, num).LastIndexOf(Path.DirectorySeparatorChar);
                string text = (num2 >= 0) ? Path.Combine(rootDir, pattern.Substring(0, num2 + 1)) : rootDir;
                if (text.Equals(string.Empty))
                {
                    text = Directory.GetCurrentDirectory();
                }
                int num3 = pattern.IndexOf(Path.DirectorySeparatorChar, num);
                if (num3 < 0)
                {
                    num3 = pattern.Length;
                }
                string searchPattern = pattern.Substring(num2 + 1, num3 - num2 - 1);
                try
                {
                    string[] directories = Directory.GetDirectories(text, searchPattern, SearchOption.TopDirectoryOnly);
                    if (num3 < pattern.Length - 1)
                    {
                        string pattern2 = pattern.Substring(num3 + 1);
                        string[] array = directories;
                        for (int i = 0; i < array.Length; i++)
                        {
                            string rootDir2 = array[i];
                            list.AddRange(GetMatchingDirectories(rootDir2, pattern2, level + 1));
                        }
                    }
                    else
                    {
                        list.AddRange(directories);
                    }
                    return list;
                }
                catch
                {
                    return list;
                }
            }
            string text2 = Path.Combine(rootDir, pattern);
            if (text2.Equals(string.Empty))
            {
                list.Add(Directory.GetCurrentDirectory());
            }
            else
            {
                if (Directory.Exists(text2))
                {
                    list.Add(Path.GetFullPath(text2));
                }
            }
            return list;
        }
    }
}

FindMatchingFiles has some strange search pattern. Here is the code (decompiled using ILSpy) so you can test your search patterns without having to kick off a new build.

It contains a hardcoded root dir at the following location (Z:)

List<string> matchingDirectories = GetMatchingDirectories(@"Z:", matchPattern.Substring(0, num), 0);

Code:

using System;
using System.Collections.Generic;
using System.IO;

namespace DirectoryGetFiles
{

    ////    Use the FindMatchingFiles activity to find files. Specify the search criteria in the MatchPattern (String) property.
    ////    In this property, you can specify an argument that includes the following elements: 
    ////        Syntax that is supported by the searchPattern argument of the Directory GetFiles(String, String) method.
    ////
    ////        ** to specify a recursive search. For example:
    ////            To search the sources directory for text files, you could specify something that resembles the following
    ////            value for the MatchPattern property: String.Format("{0}\**\*.txt", SourcesDirectory).
    ////            
    ////            To search the sources directory for text files in one or more subdirectories that are called txtfiles, 
    ////            you could specify something that resembles the following value for the MatchPattern property: 
    ////            String.Format("{0}\**\txtfiles\*.txt", SourcesDirectory).

    class Program
    {
        static void Main(string[] args)
        {
            string searchPattern = @"_PublishedWebsites\Web\Scripts\jasmine-specs**\*.js";
            var results = Execute(searchPattern);

            foreach (var i in results)
            {
                Console.WriteLine("found: {0}", i);
            }

            Console.WriteLine("Done...");
            Console.ReadLine();
        }

        private static IEnumerable<string> Execute(string pattern)
        {
            string text = pattern;
            text = text.Replace(";;", "\0");
            var hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase);
            string[] array = text.Split(new char[]
    {
        ';'
    }, StringSplitOptions.RemoveEmptyEntries);

            for (int i = 0; i < array.Length; i++)
            {
                string text2 = array[i];
                string text3 = text2.Replace("\0", ";");
                if (IsValidPattern(text3))
                {
                    List<string> list = ComputeMatchingPaths(text3);
                    if (list.Count > 0)
                    {
                        using (List<string>.Enumerator enumerator = list.GetEnumerator())
                        {
                            while (enumerator.MoveNext())
                            {
                                string current = enumerator.Current;
                                hashSet.Add(current);
                            }
                            goto IL_15C;
                        }
                    }
                    ////Message = ActivitiesResources.Format("NoMatchesForSearchPattern", new object[]
                }
                else
                {
                    ////       Message = ActivitiesResources.Format("InvalidSearchPattern", new object[]
                }

            IL_15C: ;
            }

            return hashSet;//.OrderBy((string x) => x, FileSpec.TopDownComparer);
        }

        private static bool IsValidPattern(string pattern)
        {
            string text = "**" + Path.DirectorySeparatorChar;
            int num = pattern.IndexOf(text, StringComparison.Ordinal);
            return (num < 0 || (pattern.IndexOf(text, num + text.Length, StringComparison.OrdinalIgnoreCase) <= 0 && pattern.IndexOf(Path.DirectorySeparatorChar, num + text.Length) <= 0)) && pattern[pattern.Length - 1] != Path.DirectorySeparatorChar;
        }

        private static List<string> ComputeMatchingPaths(string matchPattern)
        {
            List<string> list = new List<string>();
            string text = "**" + Path.DirectorySeparatorChar;
            int num = matchPattern.IndexOf(text, 0, StringComparison.OrdinalIgnoreCase);
            if (num >= 0)
            {
                List<string> matchingDirectories = GetMatchingDirectories(@"Z:", matchPattern.Substring(0, num), 0);
                string searchPattern = matchPattern.Substring(num + text.Length);
                using (List<string>.Enumerator enumerator = matchingDirectories.GetEnumerator())
                {
                    while (enumerator.MoveNext())
                    {
                        string current = enumerator.Current;
                        list.AddRange(Directory.GetFiles(current, searchPattern, SearchOption.AllDirectories));
                    }
                    return list;
                }
            }
            int num2 = matchPattern.LastIndexOf(Path.DirectorySeparatorChar);
            if (num2 >= 0)
            {
                List<string> matchingDirectories2 = GetMatchingDirectories(string.Empty, matchPattern.Substring(0, num2 + 1), 0);
                string searchPattern2 = matchPattern.Substring(num2 + 1);
                using (List<string>.Enumerator enumerator2 = matchingDirectories2.GetEnumerator())
                {
                    while (enumerator2.MoveNext())
                    {
                        string current2 = enumerator2.Current;
                        try
                        {
                            list.AddRange(Directory.GetFiles(current2, searchPattern2, SearchOption.TopDirectoryOnly));
                        }
                        catch
                        {
                        }
                    }
                    return list;
                }
            }
            try
            {
                list.AddRange(Directory.GetFiles(Directory.GetCurrentDirectory(), matchPattern, SearchOption.TopDirectoryOnly));
            }
            catch
            {
            }
            return list;
        }

        private static List<string> GetMatchingDirectories(string rootDir, string pattern, int level)
        {
            if (level > 129)
            {
                return new List<string>();
            }
            List<string> list = new List<string>();
            int num = pattern.IndexOf('*');
            if (num >= 0)
            {
                int num2 = pattern.Substring(0, num).LastIndexOf(Path.DirectorySeparatorChar);
                string text = (num2 >= 0) ? Path.Combine(rootDir, pattern.Substring(0, num2 + 1)) : rootDir;
                if (text.Equals(string.Empty))
                {
                    text = Directory.GetCurrentDirectory();
                }
                int num3 = pattern.IndexOf(Path.DirectorySeparatorChar, num);
                if (num3 < 0)
                {
                    num3 = pattern.Length;
                }
                string searchPattern = pattern.Substring(num2 + 1, num3 - num2 - 1);
                try
                {
                    string[] directories = Directory.GetDirectories(text, searchPattern, SearchOption.TopDirectoryOnly);
                    if (num3 < pattern.Length - 1)
                    {
                        string pattern2 = pattern.Substring(num3 + 1);
                        string[] array = directories;
                        for (int i = 0; i < array.Length; i++)
                        {
                            string rootDir2 = array[i];
                            list.AddRange(GetMatchingDirectories(rootDir2, pattern2, level + 1));
                        }
                    }
                    else
                    {
                        list.AddRange(directories);
                    }
                    return list;
                }
                catch
                {
                    return list;
                }
            }
            string text2 = Path.Combine(rootDir, pattern);
            if (text2.Equals(string.Empty))
            {
                list.Add(Directory.GetCurrentDirectory());
            }
            else
            {
                if (Directory.Exists(text2))
                {
                    list.Add(Path.GetFullPath(text2));
                }
            }
            return list;
        }
    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文