Search code examples
c#mongodbintellisensecode-completion

How can I define available values for code completion of a string property in C# in a way that MongoDB.BsonSerializer will understand?


The main purpose is to show intellisense when setting the property. It would be great if I could do it via an attribute like the image below.

The property should remain a string(not enum or struct) so that Mongo's BsonSerializer can serialize it properly. Here is an example of what it might look like:

enter image description here

To help other developers on the team know possible (but not exlusive) values they can use for the Type field Code Completion should display values that can be used as shown below:

enter image description here


Solution

  • (Edited) I was able to solve this by creating my own type

    public class SkinType:StringType<SkinType>
    {
        public SkinType(string value)
        {
            Value = value;
        }
        public SkinType()
        {
    
        }
        public static implicit operator string(SkinType d)
        {
            return d.Value;
    
        }
        public static implicit operator SkinType(string d)
        {
            return  new SkinType(d);
        }
    
        public const string StringValue = nameof(StringValue);
        public const string Color = nameof(Color);
    }
    

    Now I get intellisense for my Type property and Mongo knows how to serialize it.

    Here is how I use it:

        public class Skin : ServiceMongoIdentity
    {
    
         //removed some properties for brevity.
        [BsonIgnoreIfDefault]
        [BsonDefaultValue(SkinType.StringValue)]
        public SkinType Type { get; set; } = SkinType.StringValue;
    
    }
    

    Here is how the StringType base class is defined. I had to make Value public because Generics cannot have constructors with parameters

     public abstract  class StringType<T> where T :StringType<T>,new()
    {
        [ReadOnly(true)]
        public string Value;
        public T FromString(string d)
        {
            return  new T
            {
                Value = d
            };
    
        }
        public override bool Equals(object obj)
        {
            return obj?.ToString() == Value;
    
        }
    
        public override int GetHashCode()
        {
    
            return Value.GetHashCode();
        }
    
        public override string ToString()
        {
    
            return Value;
        }
    
    }