Using PropertyList for value types

Ted
Ted
Vote:
 

Testing the BETA-tagged PropertyList to create a content property for a list of strings.

In essence, I'd like to be able to specify content properties like the following:

public virtual List MetaKeywords { get; set; }

I'm interested in creating a property type to support this, and my first stab at it looks something like:

[PropertyDefinitionTypePlugIn(Description = "A property for list of strings", DisplayName = "String List")]
    public class PropertyStringList : PropertyList
    {
        public override PropertyData ParseToObject(string value)
        {
            ParseToSelf(value);
            return this;
        }

        protected override string ParseItem(string value)
        {
            return value;
        }

        public override void ParseToSelf(string value)
        {
            List.Clear();

            if (string.IsNullOrWhiteSpace(value))
            {
                return;
            }

            List = value.Split(',')
                        .Select(s => s.Trim())
                        .ToList();
        }

        public override string ToString()
        {
            return string.Join(",", List);
        }

        // Default backing type for all List properties
        public override Type PropertyValueType => typeof(List);
    }

I haven't used CollectionEditorDescriptor as it seems to only support complex types, but I think the StringEditorDescriptor should work as a plain string editor should work fine based on how the property type serializes/deserializes its data.

When editing data through the UI, no breakpoints are hit in the property type implementation, but I get an error saying a string cannot be converted to List, which makes sense if a direct cast is made. But I was under the impression this should be handled by the backing property type?

Or perhaps I'm just way off. :)

#142060
Nov 29, 2015 11:48
Ted
Vote:
 

Just for the sake of it, I tried the CollectionEditorDescriptor like...

[EditorDescriptor(EditorDescriptorType = typeof(CollectionEditorDescriptor<PropertyStringListItem>))]

...with a PropertyStringListItem like...

    public class PropertyStringListItem
    {
        public string Value { get; set; }

        public override string ToString()
        {
            return Value ?? "";
        }
    }

...simply to try out the editor. The actual property is still a List<string>.

This yields a different error message saying:

"Error reading string. Unexpected token: StartObject. Path '[0]', line 1, position 2."

Still no breakpoints hit in the property type.

I'm sure I'm missing something fundamental, I just can't get any traction in troubleshooting it. :)

Since PropertyList inherits PropertyJson I'm thinking the error might stem from JSON serialization somewhere?

Edit: I should point out that changing the property type to inherit PropertyList<PropertyStringListItem> (with some additional changes made to the implementation) yields the same result, i.e. the error message above.

#142061
Edited, Nov 29, 2015 12:17
Vote:
 

Ted,
First I must admit that I haven't tried connecting any standard editor descriptor to a PropertyList implementation, but I might be able to clarify a few things about the PropertyList and PropertyJson implementation.

Your PropertyStringList implementation looks mostly fine but for the PropertyValueType implementation that returns List<string> as the value type. The PropertyList<T> uses it's own internal list implementation to be able to do change tracking (if item type implements IModifiedTrackable) and read-only management (if item implements IReadOnly). It will return IEnumerable<T> as the value type, but it will also map to ICollection<T> and IList<T> if that suits better. This could potentially be the source of your issues, but I haven't verified it.
If you want, you can also remove your ParseToSelf and ToString methods as they are just re-implementing what's already in the base class.

The other potential cause of issue is that the StringEditorDescriptor is likely to try to assign the property Value as a string. The PropertyList<T> will only accept the proper value type as it's Value and not any serialized version. I can understand the confusion around this and I believe it primarily comes from some of the things we have done to try to make it work nicely with the difference quirk of our inheritage in this area. You could look at it as if the PropertyList (and PropertyJson) is working with three different formats.

  • List format (IList<T>) - This will be used by most code and by anything that does standardized access to properties using PropertyData and it's Value property.
  • JSON - This format will be used when saving the value to the database. Today there is an internal construct that we are calling PropertyValueConverters that takes care of this conversion on the DataAccess level. If needed we may expose this in the future.
  • String serialized format - This is used when calling the ToString, ParseToSelf and ParseToObejct methods which is primarily utilized by the Default value handling, but also by Export and Import to some extent. The default format of this in PropertyList is a comma separated string, but as there has been a lot of debate around this, it may be something we will revise before coming out of BETA.

So while maybe not solving your problem, it might clarify some of the issues that you are seeing.

#142062
Nov 29, 2015 23:18
Ted
Vote:
 

Thanks for valuable info, Henrik!

#142068
Nov 30, 2015 11:09
This topic was created over six months ago and has been resolved. If you have a similar question, please create a new topic and refer to this one.