using Microsoft.CodeAnalysis; namespace InnovEnergy.Lib.SrcGen; public readonly ref struct Rewriter where TRoot : SyntaxNode where TNode : SyntaxNode { internal readonly TRoot Root; internal readonly IEnumerable Descendants; internal Rewriter(TRoot root, IEnumerable descendants) { Root = root; Descendants = descendants; } public Rewriter Where(Func predicate) { return new Rewriter(Root, Descendants.Where(predicate)); } public Rewriter OfType() where T : TNode { return new Rewriter(Root, Descendants.OfType()); } public Rewriter HasAncestor() where T : SyntaxNode { return new Rewriter(Root, Descendants.Where(d => d.Ancestors().OfType().Any())); } public Rewriter HasParent() where T : SyntaxNode { return new Rewriter(Root, Descendants.Where(d => d.Parent is T)); } public Rewriter SelectNodes(Func> nodes) { return new Rewriter(Root, Descendants.SelectMany(nodes)); } public Rewriter SelectNode(Func node) where T: SyntaxNode { return new Rewriter(Root, Descendants.Select(node)); } public Rewriter GetAncestor() where T : SyntaxNode { return SelectNode(n => n.Ancestors().OfType().First()); } public TRoot Replace(SyntaxNode syntaxNode) { return Root.ReplaceNodes(Descendants, (_, _) => syntaxNode); } public TRoot Replace(Func map) { return Root.ReplaceNodes(Descendants, (_, n) => map(n)); } public TRoot Remove() => Remove(SyntaxRemoveOptions.KeepNoTrivia); public TRoot Remove(SyntaxRemoveOptions options) => Root.RemoveNodes(Descendants, options)!; } public static class Rewrite { public static Rewriter EditNodes(this R root) where R : SyntaxNode { return new Rewriter(root, root.DescendantNodes()); } }