Synon 2E Model Files - Underlying Database

New ERD for the underlying database files in Synon 2E


UPDATE: 06/12/2025 - Added a summary link post to aggregate these types of posts.

Way back in 1991 a guy called Steve Hinzmann did a talk at a Synon user group.

I've never met the chap and have no idea where he is now and what he is up to.

However, I did discover his document many years later and it has been invaluable for learning the underlying data model of the 2E product.  This has allowed me to build numerous tools and utilities at various sites and assist other developers with queries based over the 2E model database.  Connect with me (somehow) if you want me to send you a copy of the presentation.

I've shared the document to all and sundry over the years but every time, I say "x page is outdated", it "doesn't cover arrays, triggers" and lots of other features that have made it into the 2E product since version 3.  The fundamentals are solid though!!!

Recently I had a bit of spare time so I decided to document the 2E model (ERD) to assist a colleague whilst they were exposing a data dictionary.  I also built lots of queries to help us ensure our standards were being followed thereby refreshing myself of the nuances within 2E model.

ERD

The document can be downloaded from here.

https://drive.google.com/file/d/0B4YRRM3roIs1QndYQW9ieW0tMGs/view?usp=sharing

This is a fluid document and there may be an error or two.  Let me know and I'll keep this up to date.  Please share if you feel others will get some benefit from it.

Update:AUG 2017

https://drive.google.com/file/d/0B4YRRM3roIs1cF9LTUtSR2dpQVU/view?usp=sharing

Steve's document is a lot more detailed and is a must read for anyone wanting the get to grips with the underlying files etc.  One day I may have a little more time to update this also :-)

Thanks for reading the
Synon 2E and Plex Emporium by Lee Dare (A developer blog)
Lee.

Feeling resourceful...NOT!!!!

Moan about the word RESOURCE in the workplace.

My most hated word in the workplace is NOT f**k, w***er, tosser, b***h or even bad words like the ‘c’ word and I don’t mean Christianity, Catholic or Christmas.  All of these used in context (mainly in the pub after work or moaning about a colleague) are okay at varying levels. :-)

The word I hate the most right now in any workplace is ‘Resource’.

“We don’t have the resource?”
“I need to check my resources schedule.”

The reason I cringe at the usage of such a word is purely because I believe it undervalues the skill an individual brings to an organisation.  If your company describes you and your colleagues as a ‘resource’ then it is probably time to consider a move, career change or at least stand up and say "No!".

Not so long ago we had departments that looked after the staff of an organisation, they were called personnel departments and over the years Americanised/morphed into ‘Human Resources’ or HR.  This was the transition point from a meaningful team member with skills and aptitude to a reference number and a salary ceiling associated to him or her.

If the underlying semantics used in your company is ‘resource’ then you are seen as replaceable, able to be replenished, expendable!!!  Whilst this, to some degree is true, it does strongly undervalue how hard some people ‘resources’ are to replace.

I work in the IT industry as a software engineer principally, and as well as the technical skills (platform, database and languages) required to write code, you also need to have relevant business knowledge for the domain problem involved.  Thinking you can hire someone off the street that will immediately be up to speed for a large system is foolish (at best) or expensive if you are lucky as these people often come at a premium.

Back to that resource word again.....

Looking at what a resource really is we know these as consumable items like coal, sugar, soy, oil, cocoa, wool, metals (like iron, tin and steel) etc.  Many (if not all) of these are traded on exchanges around the world.  This is a perfectly good use of the word 'resource'.

The last time I looked a lump of coal hasn’t coded a single C# function (some might argue that computer aren't far from completing this), a packet of sugar hasn’t written a parsing algorithm and I am not aware of any metals, precious or otherwise, that have written code to manipulate a physics engine for your endless runner game idea.  Outside of the IT industry I haven't seen soy beans provide suicide counselling or oil build a school.

Type ‘Thesaurus Resource’ into google and there are a host of positive (enabling) words that describe resource (the human kind).  Words like ‘Ability’, ‘Capability’, ’Talent’ really stand out.

Resource is a throwaway word bandied around by project managers (in my case) and normally talentless 6ft 5” middle managers (if my last company was anything to go by).  Whenever I hear it I cringe and I am trying to correct any company culture I come across to use more eloquent and most importantly inclusive terms.  I was in a meeting only recently where we are described as resources.  Not a good feeling I must say.

So..... 

I’m beating the drum wherever I work to eradicate this cancerous word and to have is replaced by ‘Capability, Capacity, Skills, Staffing or _____________’ whenever it is used in the context of a human.

Moan over.

Thanks for reading the
Synon 2E and Plex Emporium by Lee Dare (A developer blog)
Lee.

CA Plex and Unity - A visual comparison....

CA PLEX IDE vs Unity IDE


I feel like I've been here before.......

I love CA Plex together with 'what it does' and 'how it does it'.  In terms of developer productivity I believe it is only now being matched by modern day development tooling.  Yet CA Plex was born over 20 years ago.  I am also seeing an up-swell once again towards low-code or code generation so who knows what the future entails.

Personally, for me I have always been interested in developing games and I gradually move my focus in this direction.

I've been doing game development as a serious hobby/business and despite trying many different game engines (and I promise I've tried quite a few over the last 20 years) I have settled on Unity from Unity Technologies www.unity.com.  A few other engines I like for smaller projects and rapid prototyping of game ideas but it's Unity for me for implementation.

So to all those CA Plex developers out there who like me enjoy programming games, here are a few visual comparisons that might help to explain why I like the tools.

IDE

This layout looks quite familiar.

Plex (Unity)


Coding

One language.

This is a slight lie as Plex uses a pseudo language known as Action Diagramming and Unity has C# or UnityScript (a derivative of Java), so two languages.  But the philosophy is the same i.e. master a language to solve lots of different programming problems regardless of target platform.

Plex Coding

Unity Coding

Building

Multiple different build targets from the same repository.

I feel that the common ground makes them and me, quite compatible.

Plex Generate & Build


And like Plex you can also play around with the icons for scripts, so now I have the best of both worlds for my projects.

IDE Iconography


If any other Plex or 2Er's out there also dabble in Unity, get in touch.

Thanks for reading the
Synon 2E and Plex Emporium by Lee Dare (A developer blog)
Lee.

Synon 2E Under the covers of the SELRCD function type

SELRCD (Select Record) - Technical deep dive, Synon and the code generated


UPDATE: 06/12/2025 - Linked to a summary post dedicated to deep dive long form posts.

Hi,

This blog touches on the design challenges when using select record (SELRCD) function type and makes some recommendations for best practices.  Disclaimer:  These are from personal experience and may not cover all scenarios.  I would be happy to hear of any ideas/improvements that can be made to this post.

SELRCDs can cause quite a few issues if you are not aware of the quirks of how Synon generates the code.

Let's cut straight to the problem domain at hand.  In my sample model you will see that I have two files declared.  You will see that "Lee's File" Refer to "Lee's Reference File" which will mean that if I have a PMTRCD or EDTFIL etc over Lee's file we will be able to prompt for the reference data.

SELRCD Deep Dive

The functions I have over the reference file are as follows, I have removed the default EDTFIL and renamed the database primitive functions inline with our internal development standards.

SELRCD Deep Dive
 The main file has numerous test functions so I have filtered on Edit file only.

SELRCD Deep Dive

The screens (Edit File and Select Records) in the blog post have been tidied (ever so slightly) to ensure that all the fields fit nicely on the screen.

I have generated up the code for the EDTFIL.

Reviewing the generated code.

By default you will see that Synon has generated code to call the SELRCD function upon prompting the field and Synon has chosen my SELRCD based on the reference file.

You will also notice that the parameters for the SELRCD have been defaulted to fields based on the RCD context of the calling program.  In this instance it was an EDTFIL.

SELRCD Deep Dive

This is pretty standard and works a treat.

Now we will add a few additional SELRCDs, you will see these below.  Note the naming of these was deliberate in order to ensure that they appeared after 'Select Lee's Reference Fi'.

SELRCD Deep Dive

In terms of impact analysis you will notice that the SELRCD is showing no usages although we have generated code above that proves the object is called.

SELRCD Deep Dive

This is due to implicit code generation that is automatically added if the field is a result of a foreign key constraint AND is input capable AND a select record exists on the reference file.  If you deleted the SELRCD at this stage and generated the code again the prompt and call logic will not be generated.  Give it a try!


Above is a screen image of the default Synon setup.  Notice the two subfile options at the bottom of the screen.  S allows you to select the SELRCD that should be used, T clears this value and leaves the generator to choose the default SELRCD.

SELRCD Deep Dive

After taking the S option and selecting my SELRCD from the reference file you will see that this is indicated above.  Because we have made an explicit reference to the SELRCD in the device design it will now appear as a usage within Synon.

SELRCD Deep Dive

You will see below that the generated code is as before which is great :-)

SELRCD Deep Dive

In order to help with the blog narrative, please now deselect the SELRCD by taking the subfile option T for default behaviour.   This will clear the reference to the dedicated SELRCD.

SELRCD Deep Dive

Now we will create another SELRCD (again deliberately named).  You will see that it sits above the current (default) select record for the EDTFIL.

SELRCD Deep Dive

If we generate the EDTFIL again we will see that the outcome is no longer the same. The generator now puts a call into the higher ordered SELRCD on the reference file.  We didn't intend for this to happen and a developer doing a regeneration could easily pick this up without knowing.  Quite dangerous....

SELRCD Deep Dive

In this instance, as the keys on the SELRCD are identical there is NOT too much to worry about.  However, in the real world 2nd and subsequent SELRCD functions will typically be over an alternate access path with a different key structure or may have additional parameters or specialist action diagram functionality which may not be the preferred default behaviour.

In order to demonstrate this let's add some fields to the model which we will then associate with a new SELRCD function.

SELRCD Deep Dive

Create yet another SELRCD function over the referenced file.  Note again I have named it deliberately so it appears at the top of a refreshed EDIT FUNCTIONS panel.

SELRCD Deep Dive

I have extended the parameters for this SELRCD to add our five new fields.

SELRCD Deep Dive

Let's generate up the EDTFIL once again and look at the generated code.

Ouch!!  Houston we have a problem.

You will see below that all of the new parameters have been defaulted to CON.  This is because the fields were not found in context for the relationship. i.e. in this case, not part of the RCD context. And because this is a warning message only it may go unnoticed.  Preferably Synon should mark these as errors and only allow the correct context ones to generate correctly i.e RCD example above.

Also we have now picked up yet another SELRCD.  One can conclude that anytime a new SELRCD is added and it appears higher up in the EDIT FUNCTION panel the next time a referencing function is generated it will generate code to call the new SELRCD and not the previous one.  Imagine a highly reference file and the chaos this could bring.

SELRCD Deep Dive

We can do somehing to help here.  Whilst we cannot get at the parameters at the point the implicit call to the SELRCD is made, we can put these fields in the context and populate them accordingly.

Add the fields to the 'Subfile Record' format RCD.  You will notice I set these to hidden.

SELRCD Deep Dive

Then in the action diagram you can set these values using a standard *MOVE built-in function.


SELRCD Deep Dive

Generate the function once more and the generated code now shows the moved and also defaults to the RCD context meaning that you no the parameters are populated with your values and NOT CON blank or Zero.

SELRCD Deep Dive

SELRCD Deep Dive

But I remind you at this stage that these were warnings in the code only.  How many people check the generated source for warnings.  I don't, do you?

Another way to do this is to switch off default processing and take control of the prompting yourself in the action diagram coding.  Back in the EDTFIL function again set the relation checking to 'USER'.



SELRCD Deep Dive

Note: This switches off all referential integrity checking so in the real world you'll also need to add action diagram code for the OPTIONAL/MANDATORY as well as foreign key constraints.  For the purposes of this blog I am only focused on the prompting and calling of the select record.

You can then monitor for prompting on your field and call ANY SELRCD function you think is appropriate.

SELRCD Deep Dive

With this method you get a nice parameter interface for the SELRCD and more importantly it is obvious to another developer that you are initialising the fields for an explicitly called SELRCD rather than an implicitly called on.  Some comments might be useful if you choose the other method.

SELRCD Deep Dive

This highlights the many options you have for calling a SELRCD and should help you decide what is best for your model, team etc.

Once last issue with SELRCDs.  I mentioned earlier that Synon (by default) will chose the highest SELRCD based on the referenced file.  Due to no usages showing it is possible that code will be generated to call an object that hasn't been created or has been removed by a developer thinking it is not used.  This will mean you'll get a 'resolve to object' call error which isn't a good look.

SELRCD Deep Dive

Best tip is to generate up a standard SELRCD for each reference file and implement it at the time the file is created.  If you decide that a file doesn't need prompting, then remove ALL SELRCDs from the file so this code doesn't get generate implicitly.  As you can see from above the code will get generated if the function exists regardless of whether the object exists or not.

Best Practices Summary

  1. Come up with a naming convention for the default SELRCD so that it is first in the list on the EDIT FUNCTIONS panel.  We use '*SLT xxxxxxxxxxxxxxx'.
  2. Always ensure you generate up and implement ALL SELRCD functions.
  3. Always keep the default SELRCD keys the same at the RTV access path.
  4. Always name 2nd and subsequent SELRCD so they appear lower in the EDIT FUNCTIONS panel.
  5. It is recommended you set explicitly the SELRCD you want to call either by the 'S' option or via action diagram coding.
  6. Never delete any SELRCD objects without checking the generated source files or by exploring all file references.

Thanks for reading the
Synon 2E and Plex Emporium by Lee Dare (A developer blog)
Lee.

Synon 2E CHGOBJ and easy file maintenance

CHGOBJ Synon 2E - A better way


UPDATE: 06/12/2025 - Linked to a summary post dedicated to deep dive long form posts.

Today I want to write about a neat little method of setting up CHGOBJ DBF internal functions to assist with long term file maintenance.  I have touched on this before in my standards posts but decided that as I keep seeing people do this incorrectly (wherever I work) that it deserved a blog post of its own.

Imagine a nice simple file being added to your data model.  I have added one below.

CHGOBJ Synon 2E

As you can see above it has one key and a few neatly named attributes.

CHGOBJ Synon 2E

The file was a reference file but for cleanliness I have removed the default edit file and select record functions.  Also in our shop we have a standard of preceding the primitive DBF functions with an asterisk so I have done this also.

The parameter structure for the CHGOBJ is as expected for a full record CHGOBJ.  Nothing spectacular here.  This thankfully is default 2E behaviour.

CHGOBJ Synon 2E


In order to show the proposed methods I want you to use, we need to imagine how we are going to modify the data in this file.  Typically we won't change the entire record with the exception being an EDTFIL/EDTTRN which will as default use the full record update or if you have created a W/W + PMTRCD maintenance suite which is quite common. type function .  

In the real world we update a total amount, a status, or more typically a subset of relevant data.  To do this we often create individual CHGOBJ's named something like 'Change Account Status' or 'Update Address Only'. 

Below I have created two separate CHGOBJ's to update the status field on this file.  I have imaginatively named as below.

CHGOBJ Synon 2E

Method 1 is (as defaulted) passing the entire file structure as RCD.  The parameters at the detail level are setup as follows.  Note that I have set the parameters we are not updating as NEITHER and turned off the MAP role  Nothing gets me more irritated in Synon coding than leftover MAP roles...

CHGOBJ Synon 2E

Method 2 has the data passed differently.  I am using two parameter blocks.  The first one for the keys or key in our case.  The second line for the data attributes where I have set the status filed we wish to update as input.  Again I switched off that darn MAP role.

CHGOBJ Synon 2E

CHGOBJ Synon 2E

CHGOBJ Synon 2E

Both these CHGOBJ's (Method 1 and Method 2) now have the same interface as far as calling programs are concerned.  i.e. two fields.  The key 'MSF My Key' and the fields we want to update i.e. the status field 'MSF Attribute 03 (STS)'.

There is one caveat though.  Method 2 won't work. 

Not yet anyway.  Let me explain why...

There is action diagram code inside all CHGOBJ's that implies the function moves the data passed in via the parameters (PAR) to the database record (DB1) just prior to update.  You can see this in the picture below.

CHGOBJ Synon 2E

However, the Synon generator has been written (by design/bug/undocumented feature) to only move fields passed in the first parameter block.

Yes.  Shortsighted I know but it is a known limitation.  Go ahead try it for yourself.

This means that in this instance it will only move the values passed in the highlighted row below.  In our example for Method 2 this would be the key only.

CHGOBJ Synon 2E

The way we get around this is to do the move ourselves in the user point immediately after the badly generated code.

CHGOBJ Synon 2E

This now moves the attributes into the DB1 context from PAR.

Job done.  This function will perform valiantly and won't let you down.  However, at this stage there is no advantage doing the CHGOBJ this way.  Why would you separate the parameters and add extra complexity forcing developers to add the *MOVE ALL if the two functions are now (functionally) identical?

If your shop has standards then it's likely you've learned the hard way.  Remember the average application spends 90% of its functioning life in maintenance, and therefore, it is these activities that cost the real pounds/dollars and take the time to implement.

Change is inevitable and most files will require some form of change during their lives and the most common type of change for a file is adding new fields. This is where method 2 outshines method 1.


Let's make some basic adjustments to the file.  In the example below we are adding three extra fields which have been appropriately named.

CHGOBJ Synon 2E

So how has this impacted our functions that we have created in the blog post?  The standard CHGOBJ (the *CHG) for the entire record has the three additional parameters automatically added.  We just need to visit its usages and set the values accordingly.

CHGOBJ Synon 2E

CHGOBJ Synon 2E

Our two examples (Method 1 and Method 2) fair quite differently.  Let's discuss these below.

First;y, I will quickly remind you that the two methods for the CHGOBJs were only updating a subset of fields of this file rather than the entire record, in our case the status field 'MSF Attribute 03 (STS)'.

Method 1 has had the extra fields added automatically which is not ideal or what we want.  We now need set these to NEITHER.  Forget this at you peril.  Note: I also removed the MAP!

CHGOBJ Synon 2E

Method 2 however, keeps the existing input parameter structure.  There are no changes to be made other than regeneration due to the changed file.

CHGOBJ Synon 2E

So on the surface it would appear that method 2 is best for CHGOBJ's where a subset of data is changed.

At this point I would recommend you utilise *Template if you haven't already looked at them.  I even have templates for a standard RTVOBJ so I don't forget the *MOVE ALL for CON and DB1.

Below is an example of how I implemented method 2.

Function name.

CHGOBJ Synon 2E

Parameter block.

CHGOBJ Synon 2E

Detail for parameter block 1 .

CHGOBJ Synon 2E

Detail for parameter block 2.

CHGOBJ Synon 2E

Add the AD code for the move all.

CHGOBJ Synon 2E

That's the template completed.   Use Shift F9 to create the function from the EDIT FUNCTIONS screen.  Select the template type and then name it appropriately.

CHGOBJ Synon 2E

Set the parameters you want to include in the CHGOBJ.

CHGOBJ Synon 2E

Switch off the map and you are up and running. 

CHGOBJ Synon 2E

The Action Diagram code has automatically been added to your new function as long as you put the *MOVE ALL in the *Template.

In Summary.

It hasn't got to be a one size fits all approach.  There is no harm in choosing a hybrid approach, so.
  • Use Method 1 for full record updates.
  • Use Method 2 for subset or single field updates.
  • Consider using templates to enforce your standards and to reduce any mistakes or omissions.

Thanks for reading the
Synon 2E and Plex Emporium by Lee Dare (A developer blog)
Lee.