考慮下面的類文件中的「MyClass.cs」添加自定義屬性,使用羅斯林
using System;
public class MyClass : Entity<long>
{
public long Id
{
get;
set;
}
[Required]
public string Name
{
get;
set;
}
public string Slug
{
get;
set;
}
public DateTime CreatedOn
{
get;
private set;
}
public DateTime UpdatedOn
{
get;
private set;
}
/* ... */
}
目前,我手動創建數據合同類尋找如下:
[DataContract(Namespace = "http://example.com/", Name = "MyClass")]
public sealed class MyClass
{
[DataMember(EmitDefaultValue = false, Name = "Id")]
public long Id
{
get;
set;
}
[DataMember(EmitDefaultValue = false, Name = "Name", IsRequired = true)]
public string Name
{
get;
set;
}
[DataMember(EmitDefaultValue = false, Name = "Slug")]
public string Slug
{
get;
set;
}
[DataMember(EmitDefaultValue = false, Name = "CreatedOn")]
public DateTime CreatedOn
{
get;
set;
}
[DataMember(EmitDefaultValue = false, Name = "UpdatedOn")]
public DateTime UpdatedOn
{
get;
set;
}
}
我d喜歡使用Roslyn重寫「MyClass.cs」,所以它看起來像我手工創建的類。目前,我有以下幾點:
using System;
using System.IO;
using Roslyn.Compilers.CSharp;
internal class Program
{
private static void Main()
{
var reader = new StreamReader(@"..\..\MyClass.cs");
var source = reader.ReadToEnd();
var tree = SyntaxTree.ParseCompilationUnit(source);
var rewriter = new MyRewriter();
var newRoot = rewriter.Visit(tree.Root);
Console.WriteLine(newRoot.Format());
}
}
public class MyRewriter : SyntaxRewriter
{
protected override SyntaxNode VisitClassDeclaration(ClassDeclarationSyntax node)
{
var declaration = (TypeDeclarationSyntax) base.VisitClassDeclaration(node);
return ((ClassDeclarationSyntax) declaration).Update(
declaration.Attributes,
Syntax.TokenList(Syntax.Token(SyntaxKind.PublicKeyword), Syntax.Token(SyntaxKind.SealedKeyword)),
declaration.Keyword,
declaration.Identifier,
declaration.TypeParameterListOpt,
null,
declaration.ConstraintClauses,
declaration.OpenBraceToken,
declaration.Members,
declaration.CloseBraceToken,
declaration.SemicolonTokenOpt);
}
protected override SyntaxNode VisitPropertyDeclaration(PropertyDeclarationSyntax node)
{
var typeSyntax = node.Type;
if (node.Identifier.ValueText == "Id")
{
typeSyntax = Syntax.IdentifierName("string");
}
var newProperty = Syntax.PropertyDeclaration(
modifiers: Syntax.TokenList(Syntax.Token(SyntaxKind.PublicKeyword)),
type: typeSyntax,
identifier: node.Identifier,
accessorList: Syntax.AccessorList(
accessors: Syntax.List(
Syntax.AccessorDeclaration(SyntaxKind.GetAccessorDeclaration,
semicolonTokenOpt: Syntax.Token(SyntaxKind.SemicolonToken)),
Syntax.AccessorDeclaration(SyntaxKind.SetAccessorDeclaration,
semicolonTokenOpt: Syntax.Token(SyntaxKind.SemicolonToken))
)
)
);
return newProperty;
}
}
我一直試圖找到一種方法來添加數據成員和DataContract自定義屬性MyClass的,但一直未果。如何添加自定義屬性?
我的閱讀方式[這](http://social.msdn.microsoft.com/Forums/en- US/roslyn/thread/f5adeaf0-49d0-42dc-861b-0f6ffd731825)MSDN線程,我會說Roslyn不支持自定義屬性。你有沒有看到其他方面的信息? – 2012-02-09 03:24:39
Roslyn確實在語法級別支持屬性,而不是語義 – 2012-02-09 03:47:49
有一個AttributeDeclarationSyntax類,類和屬性都有一個屬性成員,但我找不到如何構造它的示例。您也可以使用SyntaxRewiter重寫屬性。這裏是一個[示例](http://www.mindscapehq.com/blog/index.php/2011/10/20/in-bed-with-roslyn/)如何使用它。所以我會認爲它的支持,但我可能是錯的。 – bloudraak 2012-02-09 04:34:20