Jump to content

Saving LVClass data to an ini file


Recommended Posts

I am using it to test a proof-of-concept of saving LVClass data in an ini file.

Two points for consideration:

  1. You should verify that this type of access works in a built executable.
  2. Classes are versioned and have automatic mutation applied when you unflatten old data. This won't work if you attempt to load data from the INI solution unless you do something like the OpenG variant config VIs do, where the values are loaded by name, so whatever exists in the file is loaded from the file and whatever isn't in the file gets the current value. This works reasonably well, but it should be pointed out that the built in mutation is supposed to be smarter and recognize things like renames as well.

Link to comment

I'll expand a little on what I'm doing since there were some requests. I use the MGI Read/Write Anything VIs to save data, but the Read/Write Anything VIs currently save LVClass data as flattened data in a Hex string. The LVClasses represent instruments that are used in tests. I've had lots of problems with changing the data inside the class and then having the unflatten fail because the saved data can't be mutated to the new class version. I know that LVClasses are supposed to handle this, so I don't know if I'm doing something strange or if there is another problem, but the first time it happened I just recreated all the instruments, and I assumed it was a fluke. It has since happened enough other times that I felt I needed to address the problem. In fact, I think I am just now realizing the problem; the file that contains the flattened class data is on a shared network drive. There are typically multiple computers reading the instruments, and its possible they run different versions of the software, so that if the new version reads the old LVClass flattened data and then saves it as a new version, then when the old version trys to read the data it will fail because it doesn't understand the new data. I should verify that this is what is happening.

However, it is not practical to force every lab computer to update at the same time, so I'm still interested in saving the LVClass data in an ini format. I realize I would lose the mutation handling capabilities of LVClasses, but it is worth the trade if I can have old versions of the application able to mostly read the new versions of the LVClass data, which I think will work fine if the data is saved as text fields.

Currently, I have added a "Write to INI" and a "Read from INI" dynamic dispatch VI to each LVClass in the instrument hierarchy. This gives me the behavior that I want, but it took several hours and I have to remember to update these methods every time I change the data of the LVClass.

For all the other LVClasses I've written I haven't needed or wanted to arbitrarily save all the class data. This is the first use case where I've wanted this ability. My use case may be strange because all my LVClasses contain data that I want to be persistent and accessible from multiple versions of the built executable. It may be time for me to learn the LVClass mutation rules. I would welcome any comments about the wisdom or foolishness of wanting to save LVClasses into an ini file.

Link to comment

I'll expand a little on what I'm doing since there were some requests. I use the MGI Read/Write Anything VIs to save data, but the Read/Write Anything VIs currently save LVClass data as flattened data in a Hex string. The LVClasses represent instruments that are used in tests. I've had lots of problems with changing the data inside the class and then having the unflatten fail because the saved data can't be mutated to the new class version. I know that LVClasses are supposed to handle this, so I don't know if I'm doing something strange or if there is another problem, but the first time it happened I just recreated all the instruments, and I assumed it was a fluke. It has since happened enough other times that I felt I needed to address the problem. In fact, I think I am just now realizing the problem; the file that contains the flattened class data is on a shared network drive. There are typically multiple computers reading the instruments, and its possible they run different versions of the software, so that if the new version reads the old LVClass flattened data and then saves it as a new version, then when the old version trys to read the data it will fail because it doesn't understand the new data. I should verify that this is what is happening.

However, it is not practical to force every lab computer to update at the same time, so I'm still interested in saving the LVClass data in an ini format. I realize I would lose the mutation handling capabilities of LVClasses, but it is worth the trade if I can have old versions of the application able to mostly read the new versions of the LVClass data, which I think will work fine if the data is saved as text fields.

Currently, I have added a "Write to INI" and a "Read from INI" dynamic dispatch VI to each LVClass in the instrument hierarchy. This gives me the behavior that I want, but it took several hours and I have to remember to update these methods every time I change the data of the LVClass.

For all the other LVClasses I've written I haven't needed or wanted to arbitrarily save all the class data. This is the first use case where I've wanted this ability. My use case may be strange because all my LVClasses contain data that I want to be persistent and accessible from multiple versions of the built executable. It may be time for me to learn the LVClass mutation rules. I would welcome any comments about the wisdom or foolishness of wanting to save LVClasses into an ini file.

Hi Shawn, if NI were to release such an API that would be very cool.

XML is great and easy to flatten/unflatten to, but if the spec requires ini's then you need to handle it yourself, I would love to see this in the palette (and handle mutations etc...)!

So I am interested in what you are doing.

Here are some things I have tried as well:

Like you I started out using MGI VIs to read write cluster to ini. These are much faster than the OpenG ones (which are only APIs I know to do this).

The speed diffs comes (from the best of my knowledge) from the fact that the MGI VIs save the data as a string, whereas OpenG uses the key-value paradigm and the Config File API.

The problem with MGI is that you cannot use them for Inherited Classes and make use of reuse - writing the string deletes the previous string.

So you cannot store parent and child data in the same section.

OpenG overcomes this issue as the parent keys will persist, (as long as you choose different data member names you won't lose or overwrite any data) so your child data can be added under the same section.

All you have to do is call the parent read/write method. Sweet.

As I like LVOOP, my data clusters are small.

When you read and write small data clusters, as opposed to cluster in cluster with arrays etc...the speed diff gets muted, so OpenG wins hands down for me.

Now with a little bit of work, and a great post by Jim, you can easily add forward and backwards capability to your classes read/write methods.

I normally like to store all the section of the ini in one Settings File that has all persistent data.

So I have a File IO manager that is reusable and handles the general tasks - such as the file versioning in the header.

Here is a screenshot from an early implementation:

The File IO Manager is inherited from (for that Settings File Type) and just calls the Read methods of its data members.

post-10325-014533100 1284762339_thumb.pn

If you want to take abstraction a step further you can delegate your read write methods to a Class that does just file io.

I have looked at using Community scope to expose the Cluster to a Friend Class.

Either this Class does the ini file io and/or you can inherit from it with the other implementations (jki xml, custom etc...).

Because you are passing the cluster and due to datatyping you have to have a Friends File IO Class for each Class

Therefore, I could inherit from a single base class ini for file io using a Variant Interface (I am looking into that at the moment).

I am thinking I could typecast it back if I need to break it out for any reason.

Any feedback would be great.

Also I can post code example if required.

Francois - are you happy this conversation stays on this thread, or would you prefer it moved?

Link to comment

Currently, I have added a "Write to INI" and a "Read from INI" dynamic dispatch VI to each LVClass in the instrument hierarchy.

Do you mind if I ask what's included in your instrument hierarchy? I ask only because I have found that creating an inheritance tree of instruments restricts their reusability. (I'll spare the thread the long explanation of why that is. PM me or start a new thread if you're interested.)

I would welcome any comments about the wisdom or foolishness of wanting to save LVClasses into an ini file.

Do you want users to be able to see and edit the class details? If so, ini files are as good as anything. If not, saving to a binary format would probably be wiser. (Users have an annoying habit of messing with things that are better left alone.)

If you want to take abstraction a step further you can delegate your read write methods to a Class that does just file io.

I have looked at using Community scope to expose the Cluster to a Friend Class.

This is exactly what the Interface Framework does. (How rude of me to mention another repository package on Francois' thread!) In the back of my head sits the idea of making an IPersistable interface for the Interface Framework. Persisting objects to disk is one of those requirements that is just begging for native interfaces. When class mutation works, it works well. When it breaks, it breaks hard. I haven't had to persist object data in my apps very often (uh... ever?) so I haven't got around to doing it yet, but I'm sure it could be done.

You'll still have to write and update the mutation code every time the class changes. Interfaces give you a common api for dealing with all persistable objects so your application level code doesn't have to change.

[Edit - Sorry Francois]

Link to comment

Do you want users to be able to see and edit the class details? If so, ini files are as good as anything. If not, saving to a binary format would probably be wiser. (Users have an annoying habit of messing with things that are better left alone.)

Or you can put a checksum in your file. Change a bit and they're screwed... (That should teach them some manners...) :ph34r:

Link to comment

I haven't had to persist object data in my apps very often (uh... ever?) so I haven't got around to doing it yet, but I'm sure it could be done.

How do you normally (/like to) store your application's configuration (settings) data?

For me: Like MGI's example I like to keep the data in the Object and read and write the "Object" rather than passing the data out to some other structure. This means I do not have to expose 'private' data through less protected APIs, whilst making use of cluster to ini functions and not having to expose that cluster as well (except to File IO Friend Class).

Link to comment

How do you normally (/like to) store your application's configuration (settings) data?

Huh? Config data? I don't understand the question... ;)

I write test tools for internal product development teams. Application fit and finish--like storing default values and other user customizable information--is pretty low on the priority list. Flexibility is the name of the game here. Most of my requests are something like, "I want to combine the wireless protocol sniffer from the Foo tool and the robot controller from the Bar tool to create test cases for a new product." It's really bad mojo if product development is held up because the test tools aren't ready, so I sit down with the test engineer and "reset their expectations" by filtering out the features that improve usability and focus on collecting the data they need. Once we get all the data collection systems nailed down, then I'll go back and work on making it easier to use, faster, more automated, etc. Lots of times I simply don't have much time to work on that, or the test engineer decides fit and finish isn't worth the hit to their budget. (For some reason they think all the stuff they ask for can be implemented with just a couple clicks...)

We've had an ongoing large project for the last year and a half that uses text config files, but it was implemented before I got here and it's not object-based. If I ever need/get to implement a config file, creating an AppConfig class is certainly the way I'd do it.

Link to comment
Do you want users to be able to see and edit the class details? If so, ini files are as good as anything. If not, saving to a binary format would probably be wiser. (Users have an annoying habit of messing with things that are better left alone.)

Or you can put a checksum in your file. Change a bit and they're screwed... (That should teach them some manners...) :ph34r:

I have had some customers who just want to 'see' the data, others like to (or are happy to) use it as an API into the system.

Application fit and finish--like storing default values and other user customizable information--is pretty low on the priority list.

I thought this would be a bit more of a higher priority in most cases (not higher than than the test rig working obviously)

e.g. From my experience only, customer loses their app custom settings on startup = annoyed customer.

So its normally a req.

Link to comment

The speed diffs comes (from the best of my knowledge) from the fact that the MGI VIs save the data as a string, whereas OpenG uses the key-value paradigm and the Config File API.

That's correct, the delay actually comes from the NI VIs. You can see this here. The attachment is no longer there, but you can see the numbers.

The problem with MGI is that you cannot use them for Inherited Classes and make use of reuse - writing the string deletes the previous string.

You seem to be fine with the OpenG VIs, but you could probably also modify the MGI VIs so that you can easily save to the same file.

Link to comment
You seem to be fine with the OpenG VIs, but you could probably also modify the MGI VIs so that you can easily save to the same file.

Nice link.

I wonder if the MGI people have a solution for inherited class? (and whether they post here?)

Managing multiple Section names for inherited classes was too hard for me, I much prefer OpenG VIs.

Link to comment

I thought this would be a bit more of a higher priority in most cases (not higher than than the test rig working obviously)

I've never worked for a systems integrator, but I understand why fit and finish is a very high priority for them and their customers. Not only does the fit and finish directly influence the company's reputation, but support isn't always immediately available and likely costs the customer more money. In the past I've built manufaturing test equipment and fit and finish was important since downtime was costly. In my current position with strictly internal customers... not so much. They want fit and finish and we give it to them when we can, it's just not always possible given schedule constraints.

Link to comment

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.