比如说我有一个 yaml 文件

immutable_class: Foo
  A: int
  B: string

根据想象的 MSBUILD 规则将生成
partial class Foo {

    public int A { set ; private get; }
    public string B { set; private get; }

    private Foo(){}

    public static Foo Default = new Foo();

    public Foo SetA(int value){
        var r = (Foo) this.Clone();
        r.A = value;
        return r;
    }

    public Foo SetB(string value){
        var r = (Foo) this.Clone();
        r.B = value;
        return r;
    }
}

现在在我的源代码中的某个地方我将拥有
Foo foo = Foo.Default;
foo = foo
    .SetA(1)
    .SetB("Hello");

var tmp = foo.B;

我现在告诉 resharper 我希望重构 rename B 插件将识别此属性的来源是生成类的 DSL,并相应地重构该 DSL。假设一旦我被正确的信息触发,我就有了自己实际重构 DSL 的工具。

Resharper API 是否足够开放来做这种事情?

最佳答案

ReSharper API 或多或少允许您执行此操作,但实现起来并非微不足道。

您需要为 yaml 文件实现文件支持。一旦有了抽象语法树,就可以在 C# 文件中的 B 节点和 yaml 文件中的 B 节点之间创建一个引用。重命名时,ReSharper 将能够跟踪引用,并将引用文本从“B”重命名为任何内容。

(通过能够编辑生成的类和从中生成的数据,增加了额外的复杂性。例如,如果您重命名 Foo.B ,这将更新 yaml 文件中的 B,但是如何更新 Foo.SetB 方法?我想你可以通过实现从 yaml BFoo.SetB 方法的引用来做到这一点,并且在重命名 B 时它会重命名 SetB 。但是,如果重命名 Foo.SetB 怎么办?我不确定如何处理。您还需要找到一种知道 yaml 文件旨在生成 C# 文件的方法)

在 ReSharper 中提供文件支持并非易事,但它是对文件内容进行所有操作(导航、使用、重构、编辑等)的基础。它没有在 devguide 中正确记录,但有一些例子:

  • ForTea - 为 .tt 文件提供语言支持,带有手工制作的解析器
  • NTriples - RDF 三元组文件的语言支持,使用 SDK 的专有解析器格式
  • AngularJs plugin - 嵌入在 HTML 文件中的 AngularJS 表达式中的语言支持。修改现有的 JS 语言解析器以支持 Angular 所需的子集。
  • 关于c# - 我可以编写一个 resharper 插件来重构生成 c# 代码的自定义 DSL,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/23596318/

    10-11 09:19
    查看更多