2016-08-18 1 views
1

기존 프로젝트를 1.10.0 Mongo 드라이버에서 2.2.4로 업그레이드하고 MongoDB.Bson.BsonDocument에서 상속받은 클래스에서 예기치 않은 동작이 발생했습니다. 원래 개발자 BsonDocumentWithNullsnullBsonNull.Value로 변환하는 것이 목적 인 BsonDocument을 확장했습니다.ToString이 BsonDocument 하위 클래스에서 예상대로 작동하지 않습니다.

단위 테스트에서 Assert.AreEqual(new BsonDocument("foo", "bar"), new BsonDocumentWithNulls("foo", "baz"));은 실패해야하지만 오류 메시지는 BsonDocumentWithNulls 개체의 값을 인식하지 못합니다. 특히 오류 메시지는 Assert.AreEqual failed. Expected:<{ "foo" : "bar" }>. Actual:<[{ }]>.입니다. ToString과 관련이 있지만 수정 방법을 모르겠습니다.

Mongo 드라이버 1.10.0에서는 작동하지만 버전 2.2.4에서는 작동하지 않는 BsonDocumentWithNulls 구현입니다.

public sealed class BsonDocumentWithNulls : BsonDocument 
    { 
     public BsonDocumentWithNulls() 
     { } 

     public BsonDocumentWithNulls(string key, BsonValue value) 
     { 
      if (value == null) 
       Add(key, BsonNull.Value); 
      else 
       Add(key, value); 
     } 

     public BsonDocumentWithNulls(IDictionary<string, object> dictionary) 
     { 
      foreach (var keyValue in dictionary) 
      { 
       if (keyValue.Value == null) 
        Add(keyValue.Key, BsonNull.Value); 
       else 
        Add(keyValue.Key, BsonValue.Create(keyValue.Value)); 
      } 
     } 
    } 

내가 단위 테스트에 다음 어설를 만들 수있는 혼란을 추가하고 모든 값이 실제로 메모리에 저장되는 날을 알려줍니다, 작동합니다.

BsonDocument expected = new BsonDocument("foo", "bar"); 
BsonDocumentWithNulls actual = new BsonDocumentWithNulls("foo", "bar"); 

Assert.AreEqual(expected["foo"], actual["foo"]); 
Assert.AreEqual(expected.GetElement("foo"), actual.GetElement("foo")); 
Assert.AreEqual(expected, actual); 
//And just for sanity 
Assert.AreEqual("bar", actual["foo"]); 

문제를 해결하고 다양한 구현으로 ToString을 재정의하려고했습니다.

public override string ToString() 
{ 
    return base.ToString(); 
} 

public override string ToString() 
{ 
    BsonDocument doc = this.AsBsonDocument; 
    return doc.ToString(); 
} 

내 순진하고 창조적 인 시도 중 하나이지만, 창의적이거나 순진한 경우 판사가 될 것입니다.

public override string ToString() 
{ 
    string retVal = string.Empty; 

    foreach(var val in this.Elements) 
    { 
     retVal += string.Format("{2}, \"{0}\" : \"{1}\" {3}", val.Name, val.Value, "{", "}"); 
    } 
    return retVal; 
} 

답변

0

이 답변보다 해킹의 더하지만 내가 가지고 있던 문제를 통해 저를 얻었다과 BsonDocumentWithNulls 만 constuctors를 구현 한 이후 상당히 쉬운 일이 주변에 있었다.

public sealed class BsonDocumentWithNulls : BsonDocument 
    { 
     public BsonDocument doc { get; set; } 

     public BsonDocumentWithNulls() 
     { 
      doc = new BsonDocument(); 
     } 

     public BsonDocumentWithNulls(string key, BsonValue value) 
     { 
      doc = new BsonDocument(); 
      if (value == null) 
       doc.Add(key, BsonNull.Value); 
      else 
       doc.Add(key, value); 
     } 

     public BsonDocumentWithNulls(IDictionary<string, object> dictionary) 
     { 
      doc = new BsonDocument(); 
      foreach (var keyValue in dictionary) 
      { 
       if (keyValue.Value == null) 
        doc.Add(keyValue.Key, BsonNull.Value); 
       else 
        doc.Add(keyValue.Key, BsonValue.Create(keyValue.Value)); 
      } 
     } 

     public override string ToString() 
     { 
      return doc.ToString(); 
     } 

     public BsonDocument ToBsonDocument() 
     { 
      return doc; 
     } 
    } 

이 클래스의 가장 일반적인 사용은

var doc = new BsonDocumentWithNulls { 
    {"key1" : 1 }, 
    {"key2" : "val2" } 
}; 

같은이 단지에 압정 정말 쉽게이었다. ToBsonDocument()

var doc = new BsonDocumentWithNulls { 
    {"key1" : 1 }, 
    {"key2" : "val2" } 
}.ToBsonDocument();