Jump to content

Storing and using hierarchical data in a plugins configuration xml


ginjaninja

Recommended Posts

ginjaninja

please can anyone advise on the reading and writing of a node of structured data to the config xml in c# plugin environment.

go from 

<?xml version="1.0"?>
<PluginConfiguration xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <EnableCycleImages>true</EnableCycleImages>
  <CycleTagString>cyclepic,recommendation</CycleTagString>
</PluginConfiguration>

to

<?xml version="1.0"?>
<PluginConfiguration xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <EnableCycleImages>true</EnableCycleImages>
  <CycleTagString>cyclepic,recommendation</CycleTagString>
  <baseitems>
    <baseitem id="12345" hash="432423423423" ></baseitem>
    <baseitem id="44324" hash="324324823423" ></baseitem>
  </baseitems>
</PluginConfiguration>

i dont know if i am asking a generic question about c# or about inbuilt methods in emby's BasePluginConfiguration class or something else.

i dont need to provide a user ui in the configuration page, this is just structured data my plugin needs to read and write, not likely to exceed 25 baseitems.

Within a scheduled task i would like to read the baseitems into an object which i can query and manipulate and save back.

Spoiler

query id exists, query hash of id

add baseitem

remove baseitem

update the hash of a baseitem

thank you.

 

 

 

Link to comment
Share on other sites

Cheesegeezer

Hi Ginj, sorry bud, i should be available tomorrow and we can go over this on Teams. I don’t wuite understand what you mean. But we will get to the botto Of it tomorrow bud 👍👍

Link to comment
Share on other sites

The C# xml serializer is limited compared to json, so best bet would be to try to come up with a scheme to flatten it.

Link to comment
Share on other sites

14 hours ago, ginjaninja said:

i dont know if i am asking a generic question about c# or about inbuilt methods in emby's BasePluginConfiguration class or something else.

i dont need to provide a user ui in the configuration page, this is just structured data my plugin needs to read and write, not likely to exceed 25 baseitems.

Within a scheduled task i would like to read the baseitems into an object which i can query and manipulate and save back.

If I didn't misunderstand, this is rather a C# question in fact:

    public class PluginConfiguration : BasePluginConfiguration
    {
        public List<ItemRef> Items { get; set; } = new List<ItemRef>();

        [Serializable]
        public class ItemRef
        {
            public long Id { get; set; }

            public string Hash { get; set; }
        }
    }
Edited by softworkz
Link to comment
Share on other sites

ginjaninja

thanks for advice...I appreciate im making this  harder than it needs to be, but its an interesting point of learning.

i'm hoping i made  progress by using Visual Studios paste xml as classes (with a copy of my config.xml). i can read the configuration into an object of type pluginconfiguration and it looks structured. Time will tell if i can actually make use of it.

image.png.327be9c5fba1b9b48612c55df0fc0fca.png

edit this conversion tool looks better. https://xmltocsharp.azurewebsites.net/

 

Edited by ginjaninja
Link to comment
Share on other sites

That's not a good approach. You only do that when you have no other choice (no schema, no code, just some XML).

But in your case, you should really go the other way round: define your classes in the way you need the data (then you might not even ever need to look at the xml). The primary reason though, is that - as a developer - you care about the classes you work with - that must be your starting point - not some clumsy generated code from a tool.

When you aren't able to create the class definitions yourself (due to lack of C# knowledge), then I'm afraid, but developing an Emby Server plugin would be a too big pair of shoes in that case.

Link to comment
Share on other sites

ginjaninja

Thanks all, I needed a bit of hand holding to get me over the line.

Spoiler


namespace Emby.CycleImages.Configuration
{
    public class PluginConfiguration : BasePluginConfiguration
    {
        //Configuration Properties
        public bool EnableCycleImages { get; set; }
        public string CycleTagString { get; set; }
        public CycleItem[] CycleItems { get; set; }
        public PluginConfiguration()
        {
            //Default values
            EnableCycleImages = true;
            CycleTagString = "cyclepic";
            CycleItems = Array.Empty<CycleItem>();
        }   
    }
    public class CycleItem
    {
        public long Id { get; set; }
        public long Hash { get; set; }
    }
}


 

Spoiler


<?xml version="1.0"?>
<PluginConfiguration xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <EnableCycleImages>true</EnableCycleImages>
  <CycleTagString>cyclepic</CycleTagString>
  <CycleItems>
    <CycleItem>
      <Id>234324</Id>
      <Hash>75834758347</Hash>
    </CycleItem>
    <CycleItem>
      <Id>2444</Id>
      <Hash>75834</Hash>
    </CycleItem>
  </CycleItems>
</PluginConfiguration>

 

Link to comment
Share on other sites

Doesn't the plugin class have a Configuration object that serializes what's in the XML on load. 

That class also has an Update method, and Get method as well.

Is it that you aren't sure what the XML is going to have a head of time?

 

I always start by building the  PluginConfiguration : BasePluginConfiguration class.

That class will serialize everything to the XML when given to the UpdatePluginConfiguration method.

 

Just wondering why are you serializing the config on your own?

 

 

Link to comment
Share on other sites

34 minutes ago, softworkz said:

Looks good!

Oh - sorry, no: You need to add a [Serializable] attribute to the CycleItem class!

Link to comment
Share on other sites

4 minutes ago, chef said:

always start by building the  PluginConfiguration : BasePluginConfiguration class.

That class will serialize everything to the XML when given to the UpdatePluginConfiguration method.

That's what he's doing.

He was asking how to have a list of items in the configuration class, that's all.

Link to comment
Share on other sites

Cheesegeezer

Not sure if i should reply… but basepluginconfiguration takes care of the xml serialisation. Which pluginconfiguration inherits. Its not something we have to worry about. Trust me.

i got The red head warrior sorted earlier and now he’s off to the races.

he needed an array in pluginconfiguration which then uses another class to populate the array.

terminology is the barrier here thats all.

👍👍

 

Link to comment
Share on other sites

2 minutes ago, Cheesegeezer said:

basepluginconfiguration takes care of the xml serialisation

Essentially BasePluginCongiguration does nothing at all. It's just an empty class with the [Serializable] attribute applied - because that attribute is required to be serializable to xml (which is done by IConfigurationManager, not the base class.

Emby cannot add that attribute for any other classes which are part of the configuration, that's why you need to do that yourself.

Link to comment
Share on other sites

Cheesegeezer
Just now, softworkz said:

Essentially BasePluginCongiguration does nothing at all. It's just an empty class with the [Serializable] attribute applied - because that attribute is required to be serializable to xml (which is done by IConfigurationManager, not the base class.

Emby cannot add that attribute for any other classes which are part of the configuration, that's why you need to do that yourself.

Thanks for agreeing 

Link to comment
Share on other sites

Cheesegeezer

Just to clarify, as long as your Lists, Arrays and direct properties are under the pluginconfiguration class, emby takes care of it. 
 

your lists and Arrays can then be accessed via their own class to populate the properties, and in code you always have to access and update via Plugin.Instance.Configuration and you are all good. 
 

anything outside of that then yes… extra work is involved.

Link to comment
Share on other sites

3 minutes ago, Cheesegeezer said:

Just to clarify, as long as your Lists, Arrays and direct properties are under the pluginconfiguration class, emby takes care of it. 
 

your lists and Arrays can then be accessed via their own class to populate the properties, and in code you always have to access and update via Plugin.Instance.Configuration and you are all good. 
 

anything outside of that then yes… extra work is involved.

The attributes are always required.

Link to comment
Share on other sites

Cheesegeezer
47 minutes ago, softworkz said:

The attributes are always required.

Please expand because they never have been. Is this a 4.8 thing?

can you show an example?

ps I’m having the last word hehehe 😂 😛 

Edited by Cheesegeezer
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...