Jump to content

Organizing your projects on disk


Recommended Posts

I am looking into better ways to organize my project files on disk. The existing setup I have used for many years is not conductive to LVOOP classes or easy code reuse. So, I am looking for some 'best practices' information on how to layout my various project folders and organize the classes and VIs and support files within. I need to get this correct upfront before I start building and committing anything to SCC, as rearranging it later is a pain.

I did some searches for information on this but came up empty. I am hoping someone can post their thoughts or a link to a good article or thread on this subject.

thanks for any help,

-John

Link to comment

I just discussed this with my teammate and we noted some rules we follow.

1) (Really a must): Each class should be in its own directory. (This means LabVIEW will go automatically to the correct directory when you want to save a method for the class.)

2) We use virtual folders in a class to distinguish between scope (Public, Private, Protected; we don't use Community) and purpose (AccessorMethods) but locate all methods directly under the class directory on disk. I don't see any reason to have subfolders under a class on disk.

3) We group closely related items (often these correspond to a UML package) in a virtual folder in a LabVIEW project and a folder on disk. This is especially true if we add the classes to a project library (.lvlib).

4) We do not, however, make the disk folder hierarchy match the class inheritance hierarchy. There is no reason to do this. Moreover, if we change the inheritance structure (e.g., insert a layer, or just remap the inheritance relationships) we do not want to have to move directories on disk (which is a bit more annoying if we have already checked files into source code control).

5) We find project libraries useful (for instance) when we want to copy a set of code and reuse it, but just with a new namespace. There are differing opinions in LAVA threads on putting classes in project libraries, though.

6) We use a template for our components now. We put code we need to customize or add to in the project and in a template directory. Common code is generally in the dependencies and in folders in the user.lib. (It took me a while to learn to realize the advantages of locating items in the user.lib.)

7) Something we have found useful is to put different applications (or other pieces) within a component (for control components, for instance the view may or may not run when the controller is running; having separate applications for the view and controller is, of course, necessary for cRIO applications) into separate projects. This helps us to concentrate on one piece at a time, and means that we can build the different pieces separately. For each component we have a top-level project that includes the subprojects, just for convenience.

8) On that note, I advocate using interfaces appropriately to separate source code dependencies effectively.

My advice here is keep the class structure flattish on disk. Do not be tempted to try and organise your file hiearachy the same as your Project stucture. I know NI recommends doing this, but I think it is more detrimental to project maintenance (especially if used with SCC).

This is especially true since different projects may use sections of the code in different ways.

Nonetheless, our disk locations generally do match the hierarchies in the project on the macro level, and we have found that to be a really good idea. Generally the level on which we apply groupings matches a package (think diagram) in UML. (On that note, I will put in a plug for modeling. I think modeling is essential to end up with an optimal design.)

  • Like 1
Link to comment

What about groups of classes? Like if you made several classes that deal with reading and writing XML. Would you put those into a separate folder under your classes folder in your project?

Yes. We actually have this exact situation, and we set it like this: ..\\user.lib\Common\XML, and under this we have a folder for each class (e.g, XMLGenerator, XMLParser) and one for Typedefs. (We usually put Typedefs in a folder--and often a library--at the appropriate level.)

Edit: Well, I addressed where we put them on disk. I reread your question, and you actually asked about in the project. For XML libraries these would end up in the dependencies in most projects. (We only generally put what is specific to the project in the project directly. Everything else is in the dependencies. This is quite helpful when we are trying to understand a project.)

Hmm... One more thing that I think is important. We set up our directories on our data drive like this ..\\trunk\\src (also bld, errors, platform, test)\Components (also Tools and some others)\<Subsystem>\<Component>. The source for each component is thus is in its own directory, which is essential for the way we work.

Link to comment

Thanks for the reply.

In the case of reusable code, such and the XML libraries, I was planning to have thing in their own project along with their unit tests and keep that physically in a shared code area (not user.lib) along side the projects that use this code. Then, in the main project, I would have virtual folders that point to the folder where the shared XML code is.

I was mainly asking if all the class folders should be at the same physical directory level or if it was an ok practice to nest them (not by inheritance, but by some common area of responsibility, like dealing with XML or a database or an instrument).

I prefer to limit the code in user.lib to reuse code that is very generic, like OpenG type stuff and to install it using packages only.

Also, I prefer to not have anything in the dependencies other than vi.lib, user.lib and OS files (.NET DLLS). I make a virtual folder for everything else called external code or shared code so I can see that when looking at a project. The dependencies are just too out of sight, out of mind for me.

Link to comment

Yes, on everything up to the user.lib. I didn't used to put things in the user.lib, but then we decided to move calling code up or down a directory to group items we decided to group in a subsystem (hence changing the relative path to the common code) and I realized why it was maybe not the best thing that I hadn't taken advantage of a symbolic directory. So, yes, we put our common code in user.lib now. (We actually have a Common folder under user.lib.) Something else may work better for you.

On dependencies: We prefer having only the elements we need to edit in the particular context directly in the project. Other linked items (common code, interfacing code belonging to other contexts) we like to have in the dependencies precisely because they are out of sight unless we need to go look for them. (In some projects we have a thin layer we are editing but there is a lot of linked code in the dependencies that we certainly don't need to edit, or even look at, in that context.) As I said, this approach is helpful for our way of working. There are other development processes, to be sure.

Link to comment

For our re-usable code we like to have a separate project for the "library" where maintainance is performed. These are put in source code control and we never link directly to the VIs in the project area. When use VI Package Manager (VIPM) to build VI packages to place the VI's in a custom location in the user.lib folder. This has worked well for us with multiple developers through two LabVIEW upgrades. We are still working with the community version of VIPM since I can convince the boss man to spring for the pay version(s) that would let us manage distribution easier.

  • Like 2
Link to comment

Wire Warrior - That is exactly how I am setting up my reuse code now. Glad you are having success with it.

Paul - I see why that would be good in your case. My reasoning is I want to have visibility to dependencies to in-house code. I want to hide dependencies to 3rd party (NI, OpenG, general purpose re-use) code. This is because I will need to trigger a build if my in-house code changes so I want everyone to be thinking about that and know where things are used. The other code is not likely to change much so I worry less about that. But this may not be an issue to you or you might have other ways of dealing with it.

As to the re-use code I do put in user.lib via VIPM, I also want that code to be available via the palettes when editing. The re-use code that is more specific to our company's projects is not something I feel the need to have available via the pallet and can store in our separate area on disk. Also, we are calling it directly from that separate area, where as the stuff in user.lib is never edited there but instead its source is kept separate and it is installed to user.lib where it is called from.

I hope that last paragraph made sense! :unsure:

Link to comment

My advice:

Put your .lvproj file in the root of your project folder (this sounds obvious), and has the following advantages:

  • The default built location will be next to your project folder under builds (..\builds\project\buildname)
  • That will most of the time prevent builds to get into your SCC

Ton

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.