【问题标题】:Get all classes in project in Visual Studio Scaffolder在 Visual Studio Scaffolder 中获取项目中的所有类
【发布时间】:2014-08-26 11:34:26
【问题描述】:

我正在为 Visual Studio 构建一个脚手架工具,并且需要提供从某个抽象类派生的类的列表,但仅限于活动项目中的类。我有它的工作,但它需要视觉工作室一点时间来运行代码。

ICodeTypeService codeTypeService = (ICodeTypeService)Context
                    .ServiceProvider.GetService(typeof(ICodeTypeService));

var types = codeTypeService.GetAllCodeTypes(Context.ActiveProject);

foreach (var type in types)
{
    type.
    if (type.Kind == vsCMElement.vsCMElementClass)
    {
        foreach (var d in type.Bases)
        {
            var dClass = d as CodeClass;
            var name = type.Name;
            if (dClass.Name == "MyAbstractClass")
            {
                if (type.Namespace.Name.Contains(Context.ActiveProject.Name))
                {
                    yield return type.Name;
                }
            }

        }
    }
}

所以我必须在命名空间找到匹配的类时检查它,以确保它在我的项目中。这感觉就像我在做很多不必要的工作。这是他们在脚手架模板 Visual Studio 项目中给出的示例:

ICodeTypeService codeTypeService = (ICodeTypeService)Context
                    .ServiceProvider.GetService(typeof(ICodeTypeService));

return codeTypeService
    .GetAllCodeTypes(Context.ActiveProject)
    .Where(codeType => codeType.IsValidWebProjectEntityType())
    .Select(codeType => new ModelType(codeType));

codetypeservice 是正确的方法吗?

编辑 基本上,当它搜索类时,它不仅会在当前活动项目中进行,还会搜索所有引用的项目。这就是为什么我必须检查命名空间,所以我只能从活动项目中获得结果。我认为这就是为什么它会放慢速度的原因,因为引用的项目非常大,所以它做了很多完全不必要的工作......

【问题讨论】:

  • 你能定义“一会儿”吗?你也考虑过罗斯林吗?似乎如果速度是您正在寻找的东西,那将是要走的路。
  • 在我的机器上大约需要 10-15 秒,Visual Studio 在此期间进入“无响应”模式。所以并不可怕,但是......是的。是的,Roslyn 看起来确实是前进的方向,但那是针对 VS2014 的,对吧?
  • 我意识到我并没有很好地解释这个问题......我将在帖子中添加一个编辑
  • 你已经可以使用Roslyn来分析和编写c#了。加上Roslyn 的部分内容已经在 VS2013 中
  • 我明白了,我没有意识到这一点。我将不得不调查一下。谢谢你,你一直很有帮助。最后一件事,你有任何关于 Roslyn 资源的良好链接吗?我发现的最好的似乎是 Roslyn codeplex,上面有一些例子可以让我继续前进。再次干杯

标签: c# visual-studio envdte


【解决方案1】:

我注意到有人赞成这个问题,提醒我发布我如何让它更快地工作。正如 Maslow 所指出的,Roslyn 很酷,但是当我构建这个扩展时,除了预览版之外,Roslyn 不可用,所以基本上没有意义。

我的扩展在GitHub上,这里是相关代码sn-p:https://github.com/Hazzamanic/orchardizer/blob/master/Orchardization/UI/CustomViewModel.cs

但万一 GitHub 死了/有人为我的代码支付了 100 万美元,这里是相关代码...

/// <summary>
/// Recursively gets all the ProjectItem objects in a list of projectitems from a Project
/// </summary>
/// <param name="projectItems">The project items.</param>
/// <returns></returns>
public IEnumerable<ProjectItem> GetProjectItems(EnvDTE.ProjectItems projectItems)
{
    foreach (EnvDTE.ProjectItem item in projectItems)
    {
        yield return item;

        if (item.SubProject != null)
        {
            foreach (EnvDTE.ProjectItem childItem in GetProjectItems(item.SubProject.ProjectItems))
                yield return childItem;
        }
        else
        {
            foreach (EnvDTE.ProjectItem childItem in GetProjectItems(item.ProjectItems))
                yield return childItem;
        }
    }

}

获得所有项目项后,您可以按它们进行过滤。这在相当大的项目中似乎工作得很好,尽管我真的没有任何大规模的项目是公平的。就我而言,我想找到所有具有基类DatMigrationImpl 的类。所以我有这样的代码:

var allClasses = GetProjectItems(Context.ActiveProject.ProjectItems).Where(v => v.Name.Contains(".cs"));
// check for .cs extension on each

foreach (var c in allClasses)
{
    var eles = c.FileCodeModel;
    if (eles == null)
        continue;
    foreach (var ele in eles.CodeElements)
    {
        if (ele is EnvDTE.CodeNamespace)
        {
            var ns = ele as EnvDTE.CodeNamespace;
            // run through classes
            foreach (var property in ns.Members)
            {
                var member = property as CodeType;
                if (member == null)
                    continue;

                foreach (var d in member.Bases)
                {
                    var dClass = d as CodeClass;
                    if (dClass == null)
                        continue;

                    var name = member.Name;
                    if (dClass.Name == "DataMigrationImpl")
                    {
                        yield return new Migration(member);
                    }
                }
            }
        }
    }
}

【讨论】:

    猜你喜欢
    • 2010-10-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-10-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多