ABL2DB and Scoping

Posted by Thomas Mercer-Hursh on 02-Jul-2015 16:51

I have recently been exploring the use of Proparse to track the scope of various object types (buffers, variables, etc.).  I thought this might also give me the resolution on calls to sub-compile units, but it looks now like that is going to require a different effort.  But, in the mean time, this means I have to decide what to do with this information.

In the current version of ABL2DB I am tracking shared objects - browse, buffer, dataset, frame, menu, query, stream, temp-table, variable, and work-table.  In a SharedObject table I link a compile unit where it appears to the object and identify whether it is new or not.  In a separate table for each object type, I indicate whether it is global, since not all shared objects can be global.  In some cases these other tables contain additional information.

Now, I did shared objects because they are of particular interest in refactoring because they couple compile units. I.e., a variable UserName defined as new shared in one compile unit and just shared in another is a dependency link between those compile units.  Of course, the same shared variable name may be defined in other compile units and not indicate a dependency because they are not part of the same group of code. I use the name Functional Group to refer to all of the code which can be reached from some main compile unit which is run by a menu selection or batch function.  So, usually one will analyze shared object use within a Functional Group.

Non-shared objects are typically going to be of interest only within a single compile unit (with some possible exceptions like TTs passed by reference and the like).  One notable exception to this might be things defined LIKE a database object where one might want to see all the instances if one was contemplating a DB change.

So, the question is, should I capture every instance of one of these objects in every compile unit according to the scope in which it is defined or is this level of detail something you are going to go to the code for?   Or, would you only want the LIKEs?

There are some interesting database design issues here and I would be interested if anyone had any input.  For example, I currently have
CompileUnit
    V
SharedObject (Name, Type, IsNew, SharingQualifier)
    V
SharedVariable (IsGlobal, DataType, LikePhrase, AssignedTo, AssignedFrom, Variable/Property)

Now, a regular Variable has these same properties with the exception of IsGlobal and it is going to be linked to a Block, not the whole CompileUnit, so does SharedVariable become Variable, and IsGlobal move to an association table?  I.e.,

CompileUnit
    V
SharedObject (Name, Type, IsNew, SharingQualifier)
    V
SharedVariable (IsGlobal)
    V
Variable (DataType, LikePhrase, AssignedTo, AssignedFrom, Variable/Property)

and

CompileUnit
    V
Block
    V
Variable (DataType, LikePhrase, AssignedTo, AssignedFrom, Variable/Property)

And, if so, are shared variables included in this second association and is there a flag or link to indicate that.  I guess that since SharedVariable would have a link to Variable that if one started with a Variable and there was a SharedVariable link, then one would know it was Shared.

Note, however, that the name is not in the second set, so it would seem that I would have to move Name into every specific SharedX, even though all SharedX have a name. 

All Replies

Posted by Thomas Mercer-Hursh on 04-Jul-2015 13:14

Given the non-existent response to this post, I suppose no one is actually interested, but I realized the next morning that there was actually an error in the original because I had left out a link table between Block and Variable.  After some further consideration, what I am now doing is:

CompileUnit<-SharedObject<-SharedVariable->Variable

for the shared variables where the Name is moved into Variable and SharedVariable is merely a link between SharedObject and Variable. For other variables I have:

CompileUnit<-Block<-ScopedVariable->Variable

Where ScopedVariable is likewise just a link.  Block includes MainBlock which is the CompileUnit as a whole.  SharedVariables of course must be scoped to MainBlock.

I have mixed feelings at this point about providing a link for SharedVariables through ScopedVariable, i.e., ScopedVariable would have all variables whether shared or not.  My inclination at this is to include them.  There is no need for a IsShared flag in Variable since this is indicated by the existence of the SharedVariable record.

One naming dilemma I am having is that this means I have three tables for each object type

Variable

ScopedVariable

SharedVariable

For Browse and Buffer this was fine, but when I got to Dataset the dictionary wouldn't let me create a table called Dataset.  So, I am now, reluctantly, creating ADataset, ABuffer, ABrowse, etc.  This has the advantage of grouping all the tables together, but I dislike the way it sounds.

Posted by Garry Hall on 05-Jul-2015 21:16

Thanks for contributing your ideas to the community.

This thread is closed