From 45cf2fbcc593c53e5dc8c9046488d21919bbeb76 Mon Sep 17 00:00:00 2001 From: craiggwilson Date: Sun, 24 Oct 2010 00:37:00 -0500 Subject: [PATCH] added convention profile and element name conventions --- Bson/Bson.csproj | 346 +++++++++--------- Bson/DefaultSerializer/BsonClassMap.cs | 24 +- .../Conventions/ConventionProfile.cs | 25 ++ .../Conventions/ElementNameConventions.cs | 30 ++ BsonUnitTests/BsonUnitTests.csproj | 259 ++++++------- .../ElementNameConventionsTests.cs | 54 +++ 6 files changed, 430 insertions(+), 308 deletions(-) create mode 100644 Bson/DefaultSerializer/Conventions/ConventionProfile.cs create mode 100644 Bson/DefaultSerializer/Conventions/ElementNameConventions.cs create mode 100644 BsonUnitTests/DefaultSerializer/Conventions/ElementNameConventionsTests.cs diff --git a/Bson/Bson.csproj b/Bson/Bson.csproj index b2c9037909..f1599b30b4 100644 --- a/Bson/Bson.csproj +++ b/Bson/Bson.csproj @@ -1,179 +1,181 @@ - - - - Debug - AnyCPU - 9.0.30729 - 2.0 - {0E9A3A2A-49CD-4F6C-847C-DC79B4B65CE6} - Library - Properties - MongoDB.Bson - MongoDB.Bson - v3.5 - 512 - - - 3.5 - - publish\ - true - Disk - false - Foreground - 7 - Days - false - false - true - 0 - 1.0.0.%2a - false - false - true - - - true - full - false - bin\Debug\ - DEBUG;TRACE - prompt - 4 - AllRules.ruleset - - - pdbonly - true - bin\Release\ - TRACE - prompt - 4 - AllRules.ruleset - - - - - 3.5 - - - 3.0 - - - 3.5 - - - 3.5 - - - - - 3.0 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - False - .NET Framework 3.5 SP1 Client Profile - false - - - False - .NET Framework 3.5 SP1 - true - - - False - Windows Installer 3.1 - true - - - + + + + Debug + AnyCPU + 9.0.30729 + 2.0 + {0E9A3A2A-49CD-4F6C-847C-DC79B4B65CE6} + Library + Properties + MongoDB.Bson + MongoDB.Bson + v3.5 + 512 + + + 3.5 + + publish\ + true + Disk + false + Foreground + 7 + Days + false + false + true + 0 + 1.0.0.%2a + false + false + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + AllRules.ruleset + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + AllRules.ruleset + + + + + 3.5 + + + 3.0 + + + 3.5 + + + 3.5 + + + + + 3.0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + False + .NET Framework 3.5 SP1 Client Profile + false + + + False + .NET Framework 3.5 SP1 + true + + + False + Windows Installer 3.1 + true + + + + --> \ No newline at end of file diff --git a/Bson/DefaultSerializer/BsonClassMap.cs b/Bson/DefaultSerializer/BsonClassMap.cs index c8593e9735..285c437dd5 100644 --- a/Bson/DefaultSerializer/BsonClassMap.cs +++ b/Bson/DefaultSerializer/BsonClassMap.cs @@ -23,12 +23,14 @@ using System.Text; using System.Text.RegularExpressions; using MongoDB.Bson.IO; -using MongoDB.Bson.Serialization; +using MongoDB.Bson.Serialization; +using MongoDB.Bson.DefaultSerializer.Conventions; namespace MongoDB.Bson.DefaultSerializer { public abstract class BsonClassMap { #region private static fields - private static object staticLock = new object(); + private static object staticLock = new object(); + private static ConventionProfile defaultProfile = ConventionProfile.Default; private static Dictionary classMaps = new Dictionary(); private static Dictionary> discriminatedTypes = new Dictionary>(); #endregion @@ -267,7 +269,9 @@ namespace MongoDB.Bson.DefaultSerializer { public void AutoMap() { foreach (BsonKnownTypeAttribute knownTypeAttribute in classType.GetCustomAttributes(typeof(BsonKnownTypeAttribute), false)) { BsonClassMap.LookupClassMap(knownTypeAttribute.KnownType); // will AutoMap KnownType if necessary - } + } + + var conventions = GetConventionProfile(classType); var discriminatorAttribute = (BsonDiscriminatorAttribute) classType.GetCustomAttributes(typeof(BsonDiscriminatorAttribute), false).FirstOrDefault(); if (discriminatorAttribute != null) { @@ -302,9 +306,9 @@ namespace MongoDB.Bson.DefaultSerializer { new Type[] { typeof(PropertyInfo), typeof(string) }, null // modifiers ); - var mapPropertyInfo = mapPropertyDefinition.MakeGenericMethod(propertyInfo.PropertyType); - - var elementName = propertyInfo.Name; + var mapPropertyInfo = mapPropertyDefinition.MakeGenericMethod(propertyInfo.PropertyType); + + var elementName = conventions.ElementNameConvention.GetElementName(propertyInfo); var order = int.MaxValue; IBsonIdGenerator idGenerator = null; @@ -414,7 +418,13 @@ namespace MongoDB.Bson.DefaultSerializer { } #endregion - #region private methods + #region private methods + private ConventionProfile GetConventionProfile( + Type type + ) { + return defaultProfile; + } + private bool IsAnonymousType( Type type ) { diff --git a/Bson/DefaultSerializer/Conventions/ConventionProfile.cs b/Bson/DefaultSerializer/Conventions/ConventionProfile.cs new file mode 100644 index 0000000000..28e5abde8c --- /dev/null +++ b/Bson/DefaultSerializer/Conventions/ConventionProfile.cs @@ -0,0 +1,25 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; + +namespace MongoDB.Bson.DefaultSerializer.Conventions +{ + public sealed class ConventionProfile { + public static ConventionProfile Default { get; set; } + + public IElementNameConvention ElementNameConvention { get; private set; } + + static ConventionProfile() + { + Default = new ConventionProfile() + .SetElementNameConvention(new MemberNameElementNameConvention()); + } + + public ConventionProfile SetElementNameConvention(IElementNameConvention convention) + { + ElementNameConvention = convention; + return this; + } + } +} \ No newline at end of file diff --git a/Bson/DefaultSerializer/Conventions/ElementNameConventions.cs b/Bson/DefaultSerializer/Conventions/ElementNameConventions.cs new file mode 100644 index 0000000000..52eee1169a --- /dev/null +++ b/Bson/DefaultSerializer/Conventions/ElementNameConventions.cs @@ -0,0 +1,30 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Reflection; + +namespace MongoDB.Bson.DefaultSerializer.Conventions +{ + public interface IElementNameConvention { + string GetElementName(MemberInfo member); + } + + public class MemberNameElementNameConvention : IElementNameConvention { + public string GetElementName( + MemberInfo member + ) { + return member.Name; + } + } + + public class CamelCaseElementNameConvention : IElementNameConvention { + public string GetElementName( + MemberInfo member + ) { + string name = member.Name; + return Char.ToLowerInvariant(name[0]) + name.Substring(1); + } + } + +} diff --git a/BsonUnitTests/BsonUnitTests.csproj b/BsonUnitTests/BsonUnitTests.csproj index 3ffcecd81d..a762cb7e54 100644 --- a/BsonUnitTests/BsonUnitTests.csproj +++ b/BsonUnitTests/BsonUnitTests.csproj @@ -1,136 +1,137 @@ - - - - Debug - AnyCPU - 9.0.30729 - 2.0 - {10A5FAC2-E26F-4726-B888-26D5B849F805} - Library - Properties - MongoDB.BsonUnitTests - MongoDB.BsonUnitTests - v3.5 - 512 - - - 3.5 - - publish\ - true - Disk - false - Foreground - 7 - Days - false - false - true - 0 - 1.0.0.%2a - false - false - true - - - true - full - false - bin\Debug\ - DEBUG;TRACE - prompt - 4 - AllRules.ruleset - - - pdbonly - true - bin\Release\ - TRACE - prompt - 4 - AllRules.ruleset - - - - False - ..\dependencies\NUnit\lib\nunit.framework.dll - - - - 3.5 - - - 3.0 - - - 3.5 - - - 3.5 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - {0E9A3A2A-49CD-4F6C-847C-DC79B4B65CE6} - Bson - - - - - False - .NET Framework 3.5 SP1 Client Profile - false - - - False - .NET Framework 3.5 SP1 - true - - - False - Windows Installer 3.1 - true - - - + + + + Debug + AnyCPU + 9.0.30729 + 2.0 + {10A5FAC2-E26F-4726-B888-26D5B849F805} + Library + Properties + MongoDB.BsonUnitTests + MongoDB.BsonUnitTests + v3.5 + 512 + + + 3.5 + + publish\ + true + Disk + false + Foreground + 7 + Days + false + false + true + 0 + 1.0.0.%2a + false + false + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + AllRules.ruleset + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + AllRules.ruleset + + + + False + ..\dependencies\NUnit\lib\nunit.framework.dll + + + + 3.5 + + + 3.0 + + + 3.5 + + + 3.5 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {0E9A3A2A-49CD-4F6C-847C-DC79B4B65CE6} + Bson + + + + + False + .NET Framework 3.5 SP1 Client Profile + false + + + False + .NET Framework 3.5 SP1 + true + + + False + Windows Installer 3.1 + true + + + + --> \ No newline at end of file diff --git a/BsonUnitTests/DefaultSerializer/Conventions/ElementNameConventionsTests.cs b/BsonUnitTests/DefaultSerializer/Conventions/ElementNameConventionsTests.cs new file mode 100644 index 0000000000..5d39f980d6 --- /dev/null +++ b/BsonUnitTests/DefaultSerializer/Conventions/ElementNameConventionsTests.cs @@ -0,0 +1,54 @@ +/* Copyright 2010 10gen Inc. +* +* Licensed under the Apache License, Version 2.0 (the "License"); +* you may not use this file except in compliance with the License. +* You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using NUnit.Framework; + +using MongoDB.Bson.DefaultSerializer.Conventions; + +namespace MongoDB.BsonUnitTests.DefaultSerializer.Conventions +{ + [TestFixture] + public class ElementNameConventionsTests { + private class TestClass { + public string FirstName { get; set; } + public int Age { get; set; } + public string _DumbName { get; set; } + public string lowerCase { get; set; } + } + + [Test] + public void TestMemberNameElementNameConvention() { + var convention = new MemberNameElementNameConvention(); + Assert.AreEqual("FirstName", convention.GetElementName(typeof(TestClass).GetProperty("FirstName"))); + Assert.AreEqual("Age", convention.GetElementName(typeof(TestClass).GetProperty("Age"))); + Assert.AreEqual("_DumbName", convention.GetElementName(typeof(TestClass).GetProperty("_DumbName"))); + Assert.AreEqual("lowerCase", convention.GetElementName(typeof(TestClass).GetProperty("lowerCase"))); + } + + [Test] + public void TestCamelCaseElementNameConvention() { + var convention = new CamelCaseElementNameConvention(); + Assert.AreEqual("firstName", convention.GetElementName(typeof(TestClass).GetProperty("FirstName"))); + Assert.AreEqual("age", convention.GetElementName(typeof(TestClass).GetProperty("Age"))); + Assert.AreEqual("_DumbName", convention.GetElementName(typeof(TestClass).GetProperty("_DumbName"))); + Assert.AreEqual("lowerCase", convention.GetElementName(typeof(TestClass).GetProperty("lowerCase"))); + } + } +}