Microsoft Dynamics 365 Blog

Issue:

When registering time via manufacturing execution/time registration for a job, different time entries (start and end time sum up to 0.01) are calculated on the route card journal when the “Lock employee”-parameter is enabled.

 

How does the “Lock employee”-parameter work?

The cause behind this issue can be found when looking into how the “Lock employee”-parameter works. Development provided the following full investigation information and concluded that a correction to this is not feasible, as any correction to the current code would make this parameter function in the same way for both options enabled’ and “Disabled”.

 

It was found that if the parameter “Lock employee” is enabled, then we get the stated issue, whereas if it is disabled, we will get the expected results.

 

Technical description:

“Lock employee” is disabled

Path: Human Resources

Time and Attendance > Set up > Terminals > Configure registration forms

 

 

If “Lock employee” is disabled when we start the jobs/stops, the code will fall into \Classes\JmgRegistrationForm\approveMarked which is called from \Classes\JmgRegistrationForm\beginMarkedJobs i.e

boolean approveMarked(boolean_skipPreApprove = false)

{

   

——————————————————————-       

jmgRegistrationSetup = form.getRegistrationSetup();

        if
(jmgRegistrationSetup.LockEmployee   == NoYes::Yes)

        {

            commitOk
= localCurrentBundle.makeRegistrations(JmgProfileSeconds::getSysDate(),
JmgProfileSeconds::getSysTime());

        }

        else

        {

            commitOk = localCurrentBundle.makeRegistrations();

        }

    return false;

}

 

Here, “Lock employee” is disabled so the code will fall into the else part and in here, there is no parameter passed for time. In this case, time and date will be taken from the user start job time/end job time  i.e \Classes\JmgJobBundle\makeRegistrations i.e public boolean makeRegistrations(JmgDate _registrationDate = registrationDate, JmgTime _registrationTime = registrationTime)

{

   
—————————————————————————

 

    registrationDate = _registrationDate;

    registrationTime = _registrationTime;

 

    this.checkRegistrationTime();

    this.checkPilot();

 

    ret = this.requestStartupInfo();

    if (ret)

    {

        ret = this.requestFeedback(NoYes::Yes);

    }

 

    if (ret)

    {

        try

        {

        
   ttsbegin;

           
showMessage = false;

 

            switch
(bundleType)

            {

               
case JmgJobBundleType::IPC:

                   
this.makeRegistrationsIPC();

                   
break;

               
case JmgJobBundleType::Prod:

                   
this.makeRegistrationsProd();

                   
break;

               
case JmgJobBundleType::Proj:

                   
this.makeRegistrationsProj();

                   
break;

               
——————————————————–

                   
break;

               
default:

                   
break;

            }

           
this.postProductionJournals();

 

           
this.postTime();

           
ttscommit;

           

    }

——————————————————

}

 

After the code calculates the start/end job time, it will fall into this.makeRegistrationsProd() before it falls into \Classes\JmgJobBundle\postTime which is called from \Classes\JmgJobBundle\makeRegistrations. Subsequently, the code will fall into  \Classes\JmgPostStandardSystem\postTime which is called from \Classes\JmgJobBundle\postTime

Finally the start times/end times are correctly updated.

 

public void postTime()

{

   
———————————————————————

    for (i = 1; i <= jobs.lastIndex(); i++)

    {   

               
prodJournalRoute.FromTime = jmgStampTransMap.StartTime;

               
prodJournalRoute.ToTime = jmgStampTransMap.StopTime;

               
—————————————————————————

}

So we at the end get the expected results.

                                                                                                                             

“Lock employee” is enabled

 

Path: Human Resources

Time and Attendance >Set up -> Terminals > Configure registration forms

 

If “Lock employee” is enabled when the jobs/stops are started, the code will fall into \Classes\JmgRegistrationForm\approveMarked which is called from \Classes\JmgRegistrationForm\beginMarkedJobs i.e

              

boolean approveMarked(boolean _skipPreApprove = false)

{

 

——————————————————————-       

jmgRegistrationSetup = form.getRegistrationSetup();

        if
(jmgRegistrationSetup.LockEmployee   == NoYes::Yes)

        {

            commitOk = localCurrentBundle.makeRegistrations(JmgProfileSeconds::getSysDate(),
JmgProfileSeconds::getSysTime());

        }

        else

        {

            commitOk = localCurrentBundle.makeRegistrations();

        }

       

    return false;

}

 

Here, “Lock employee” is enabled and as per the logic above, the code will fall into the “if” part and there, the parameter JmgProfileSeconds::getSysTime()) is passed so that even when we have a stop job after a time lapse, the system will default to getSysTime() for both the start job time and end job time. After this, the code will continue into \Classes\JmgJobBundle\makeRegistrations i.e

 

public boolean makeRegistrations(JmgDate _registrationDate = registrationDate, JmgTime _registrationTime = registrationTime)

{

    —————————————————————————

 

    registrationDate = _registrationDate;

    registrationTime = _registrationTime;

 

    this.checkRegistrationTime();

    this.checkPilot();

 

    ret = this.requestStartupInfo();

    if (ret)

    {

        ret = this.requestFeedback(NoYes::Yes);

    }

 

    if (ret)

    {

        try

        {

           
ttsbegin;

           
showMessage = false;

 

            switch (bundleType)

            {

        
       case JmgJobBundleType::IPC:

                   
this.makeRegistrationsIPC();

                   
break;

               
case JmgJobBundleType::Prod:

                   
this.makeRegistrationsProd();

                   
break;

               
case JmgJobBundleType::Proj:

                   
this.makeRegistrationsProj();

                   
break;

               
——————————————————–

                   
break;

               
default:

                   
break;

            }

           
this.postProductionJournals();

 

           
this.postTime();

           
ttscommit;

           

    }

——————————————————

}

 

The code will then have updated the start/end job time with i.e the system time. Then the code will fall into this.makeRegistrationsProd() before falling into \Classes\JmgJobBundle\postTime which is called from \Classes\JmgJobBundle\makeRegistrations and after, code will fall into \Classes\JmgPostStandardSystem\postTime which is called from \Classes\JmgJobBundle\postTime.

Finally, start time/end times are updated with the same time.

 

public void postTime()

{

   
———————————————————————

    for (i = 1; i <= jobs.lastIndex(); i++)

    {      

           
prodJournalRoute.FromTime = jmgStampTransMap.StartTime;

               
prodJournalRoute.ToTime = jmgStampTransMap.StopTime;

               
—————————————————————————

}

 

In the end, we are indeed getting the wrong times calculated when the “Lock employee”-parameter is enabled.

 

Workaround: 

If the parameter “Lock employee” is disabled, we will get the correct behaviour.

 

In this particular case, we are unfortunately not able to deliver any fix since if we make the change required (which is to remove the parameters (commitOk = localCurrentBundle.makeRegistrations(JmgProfileSeconds::getSysDate(), JmgProfileSeconds::getSysTime())) in \Classes\JmgRegistrationForm\approveMarked                                                          

boolean approveMarked(boolean_skipPreApprove = false)

{

   

——————————————————————-
       

jmgRegistrationSetup = form.getRegistrationSetup();

        if
(jmgRegistrationSetup.LockEmployee   == NoYes::Yes)

        {

            commitOk = localCurrentBundle.makeRegistrations(JmgProfileSeconds::getSysDate(), JmgProfileSeconds::getSysTime());

        }

        else

        {

            commitOk = localCurrentBundle.makeRegistrations();

        }       

    return false;

}

Then both options for the “Lock employee”-parameter (disabled and enabled) would trigger the same behaviour.

We're always looking for feedback and would like to hear from you. Please head to the Dynamics 365 Community to start a discussion, ask questions, and tell us what you think!