project QadFinancials > class BMultiCyProcessor > method ProcessRequestAsyncProcess

Description

Runs a single business function over all entities in a single entity group. Each call will use the same parameter set.


Parameters


ocNextCompanyCodeoutputcharacterCode of the next entity to be processed.
oiNumberOfProcessedCompaniesoutputintegerNumber of processed Entities.
olEofoutputlogical
oiReturnStatusoutputintegerReturn status of the method.


Internal usage


unused


program code (program1/bmulticyprocessor.p)

/* Current entity errorr handling */
assign viCurrentEntityReturnStatus = 0.


/* ================================================================= */
/* Default values for output parameters                              */
/* ================================================================= */
assign ocNextCompanyCode            = "":U
       oiNumberOfProcessedCompanies = 0
       olEof                        = false.
       
/* ================================================================= */
/* Get the next Entity that was not processed yet                    */
/* Processing is starting with Current entity                        */
/* ================================================================= */
find first tAsyncProcessCompanies where
           tAsyncProcessCompanies.tlIsProcessed <> true and
           tAsyncProcessCompanies.tcCompanyCode = vcAsyncCurrentCompanyCode
           no-error.
if not available tAsyncProcessCompanies
then find first tAsyncProcessCompanies where
                tAsyncProcessCompanies.tlIsProcessed <> true
                no-error.
     
if not available tAsyncProcessCompanies
then do:
    assign oiNumberOfProcessedCompanies = viNumberOfCompaniesInCyGroup
           olEof                        = true.
    return.
end.    
       
/* ================================================================= */
/* Do Processing in the entity                                       */
/* ================================================================= */       
empty temp-table tFcMessages.

    
CYBLOCK:
do on error undo, throw:
    /* ================================================================= */
    /* Start a new session that can be switched to the needed company.   */
    /* This session will be deleted when this method ends.               */
    /* ================================================================= */
    if viSessionID = 0
    then do:
        <I-57 {bFcStartAndOpenInstance
             &CLASS                = "Session"}>
        
        <M-48 run ApplicationLogin
           (input  vcGlobalSessionId (icGlobalSessionId), 
            input  tAsyncProcessCompanies.tcCompanyCode (icCompanyCode), 
            input  '':U (icExtra), 
            input  false (ilReturnTimeStamps), 
            output vcDummy1 (ocReportTimeStamp), 
            output vcDummy2 (ocSystCacheDateTime), 
            output vcDummy3 (ocSystDateTime), 
            output viFcReturnSuper (oiReturnStatus)) in Session>
        
        if viFcReturnSuper < 0 or viFcReturnSuper > 0 and viCurrentEntityReturnStatus = 0 then assign viCurrentEntityReturnStatus = viFcReturnSuper.
        if viFcReturnSuper <  0 then return. /* error on starting session is fatal */
    end. /* viSessionID = 0 */
    else do:
        if not valid-handle(vhSessionInst)
        then do:
            <I-33 {bFcOpenInstance
                 &CLASS           = "Session"}>
        end.
    
        <M-74 run SwitchCompany
           (input  tAsyncProcessCompanies.tcCompanyCode (icCompanyCode), 
            input  0 (iiCompanyId), 
            output viFcReturnSuper (oiReturnStatus)) in Session>
        
        if viFcReturnSuper < 0 or viFcReturnSuper > 0 and viCurrentEntityReturnStatus = 0 then assign viCurrentEntityReturnStatus = viFcReturnSuper.
        if viFcReturnSuper <  0 then leave CYBLOCK. /* error on switching session current company is not fatal, just log and go to next company */
    end. /* viSessionID <> 0 */
    
        
    /* ================================================================= */
    /* Run the requested business component and then run the business    */
    /* method itself (with a fixed parameter set).                       */
    /* ================================================================= */
    <M-88 run BusinessClassActions
       (input  vcAsyncBusinessClassShortName (icClassShortname), 
        input  'START+OPEN' (icAction), 
        input  no (ilSubtransaction), 
        input-output viBCompOC (biClassOpenCount), 
        input-output vhBCompInst (bhClassInstanceHandle), 
        input-output viBCompID (biClassInstanceId), 
        input  '' (icDraftReference), 
        input  '' (icUserDefinedContext), 
        output viFcReturnSuper (oiReturnStatus)) in BMultiCyProcessor>
    
    if viFcReturnSuper < 0 or viFcReturnSuper > 0 and viCurrentEntityReturnStatus = 0 then assign viCurrentEntityReturnStatus = viFcReturnSuper.
    if viFcReturnSuper <  0 then leave CYBLOCK.
    
    /* Create dataset with the data for the processing */
    assign vlInstaceDatasetCreated = false.
    if valid-handle(vhAsyncInstanceData)
    then assign vhInstanceDataset = vhAsyncInstanceData.
    else do:
        assign vlInstaceDatasetCreated = true.
    
        create dataset vhInstanceDataset in widget-pool "non-persistent".
    
        <M-31 run ConvertTempTableToLongChar
           (input  tAsyncInstanceDataSerialized (t_sAsyncInstanceDataSerialized), 
            output vpAsyncInstanceData (opLongText), 
            output viFcReturnSuper (oiReturnStatus)) in BMultiCyProcessor>
        if viFcReturnSuper < 0 or viFcReturnSuper > 0 and viCurrentEntityReturnStatus = 0 then assign viCurrentEntityReturnStatus = viFcReturnSuper.
        if viFcReturnSuper <  0 then leave CYBLOCK.   
        
        
        vhInstanceDataset:read-xml("LONGCHAR":U, vpAsyncInstanceData, "EMPTY":U, "":U, ?, ?, ?).
    end. /* else do if valid-handle(vhAsyncInstanceData) */ 
    
    /* Run the method */
    run value (vcAsyncMethodName) in vhBCompInst
       (input vcAsyncActivityCode,
        input dataset-handle vhInstanceDataset,
        input vcAsyncUnmanagedData,
        output vcOutputUnmanagedData,
        output viFcReturnSuper) no-error.
    
    if error-status:num-messages > 0
    then do:
        vcDummy1 = "".
        do viFcCount1 = 1 to error-status:num-messages:
            vcDummy1 = vcDummy1 + error-status:get-message(viFcCount1) + chr(10).
        end.
        if error-status:num-messages = 1
        and error-status:get-number(1) = 6456
        then vcDummy2 = trim(#T-18'Internal error: Business component &1 does not contain a definition for &2.':255(104852940)T-18#).
        else if error-status:num-messages = 1
             and error-status:get-number(1) = 3230
             then vcDummy2 = trim(#T-45'Internal error: &1.&2 is not implemented correctly.':255(578680440)T-45#).
             else vcDummy2 = trim(#T-6'Internal error: Failed to run &1.&2.':255(252068056)T-6#).
        viFcReturnSuper = -3.
        
        assign vcDummy2 = substitute(vcDummy2, vcAsyncBusinessClassShortName, vcAsyncMethodName).
        
        <M-91 run SetMessage
           (input  vcDummy2 (icMessage), 
            input  '':U (icArguments), 
            input  '':U (icFieldName), 
            input  '':U (icFieldValue), 
            input  'E':U (icType), 
            input  3 (iiSeverity), 
            input  '':U (icRowid), 
            input  'qadfin-458419':U (icFcMsgNumber), 
            input  '':U (icFcExplanation), 
            input  '':U (icFcIdentification), 
            input  vcDummy1 (icFcContext), 
            output viDummy (oiReturnStatus)) in BMultiCyProcessor>
    end. /* error-status:num-messages > 0 */
    
    if viFcReturnSuper < 0 or viFcReturnSuper > 0 and viCurrentEntityReturnStatus = 0 then assign viCurrentEntityReturnStatus = viFcReturnSuper.
    if viFcReturnSuper <  0 then leave CYBLOCK.
    
    
    /* ===================================================================== */
    /* Remember return status from the execution in the entity, user is      */
    /* logged in                                                             */
    /* ===================================================================== */
    if tAsyncProcessCompanies.tcCompanyCode = vcAsyncCurrentCompanyCode
    then assign viAsyncCurrentCompReturnStatus = viCurrentEntityReturnStatus.
    
    
    /* ===================================================================== */
    /* Overtake return unmanaged output data                                 */
    /* ===================================================================== */
    if vcOutputUnmanagedData <> ? and
       vcOutputUnmanagedData <> "":U
    then assign vcAsyncOutputUnmanagedData = vcAsyncOutputUnmanagedData
                                           + (if vcAsyncOutputUnmanagedData = "":U
                                              then "":U
                                              else chr(2))
                                           + vcOutputUnmanagedData.
    
    finally:
        /* Stop instance of started component */
        <M-77 run BusinessClassActions
           (input  vcAsyncBusinessClassShortName (icClassShortname), 
            input  'CLOSE+STOP' (icAction), 
            input  no (ilSubtransaction), 
            input-output viBCompOC (biClassOpenCount), 
            input-output vhBCompInst (bhClassInstanceHandle), 
            input-output viBCompID (biClassInstanceId), 
            input  '' (icDraftReference), 
            input  '' (icUserDefinedContext), 
            output viFcReturnSuper (oiReturnStatus)) in BMultiCyProcessor>
            
        /* Clear out all used memory */
        if vlInstaceDatasetCreated
        then delete object vhInstanceDataset no-error.
            
        /* ===================================================================== */
        /* Collect all warnings and errors from the business method execution.   */
        /* ===================================================================== */
        if viCurrentEntityReturnStatus <> 0
        then do:
            /* Create Error/Warning message by entity */
            assign vcMessage = if viCurrentEntityReturnStatus < 0
                               then #T-20'Operation failed for entity &1.':255(660100836)T-20#
                               else #T-51'Operation completed with warnings for entity &1.':255(575820651)T-51#
                   vcMessage = substitute(vcMessage, tAsyncProcessCompanies.tcCompanyCode)
                   vcContext = "":U.
                   
            for each tFcMessages:
                assign vcContext = substitute("&1&2&3=&4":U, 
                                              vcContext, 
                                              if vcContext = "":U then "":U else chr(2),
                                              tFcMessages.tcFcMsgNumber,
                                              tFcMessages.tcFcMessage).
            end.        
            
            <M-92 run SetMessage
               (input  vcMessage (icMessage), 
                input  '':U (icArguments), 
                input  '':U (icFieldName), 
                input  '':U (icFieldValue), 
                input  if viCurrentEntityReturnStatus < 0 then 'E':U else 'W':U (icType), 
                input  3 (iiSeverity), 
                input  '':U (icRowid), 
                input  'qadfin-448501':U (icFcMsgNumber), 
                input  '':U (icFcExplanation), 
                input  '':U (icFcIdentification), 
                input  vcContext (icFcContext), 
                output viFcReturnSuper (oiReturnStatus)) in BMultiCyProcessor>
            
            /* Store all error messages to backup temp table - because of order, we have to take first the message created above */
            for each tFcMessages where
                     tFcMessages.tcFcMsgNumber = "qadfin-448501":U:
                create tProcessErrors.
                buffer-copy tFcMessages to tProcessErrors.
                delete tFcMessages.
            end.
            
            for each tFcMessages:
                create tProcessErrors.
                buffer-copy tFcMessages to tProcessErrors
                    assign tProcessErrors.tcFcMessage = substitute(" &1 &2 - &3":U, #T-97'Entity':20(210)T-97#, tAsyncProcessCompanies.tcCompanyCode, tFcMessages.tcFcMessage).
                delete tFcMessages.
            end.
        end. /* if oiReturnStatus <> 0 */
        
        /* Keep overall error status of execution */
        if viCurrentEntityReturnStatus < 0 or viCurrentEntityReturnStatus > 0 and viAsyncReturnStatus = 0 then assign viAsyncReturnStatus = viCurrentEntityReturnStatus.
            
        /* Mark the company as processed, even there were errors. This is to prevent double execution */
        if available tAsyncProcessCompanies
        then assign tAsyncProcessCompanies.tlIsProcessed = true.
        
        /* Increase internal counter with number of processed companies */
        assign viNumberOfCompaniesProcessed = viNumberOfCompaniesProcessed + 1
               oiNumberOfProcessedCompanies = viNumberOfCompaniesProcessed.
        
        /* Get the next company to be processed */
        if available tAsyncProcessCompanies
        then do:
            find first tAsyncProcessCompanies where
                       tAsyncProcessCompanies.tlIsProcessed <> true
                       no-error.
     
            if available tAsyncProcessCompanies
            then assign ocNextCompanyCode = tAsyncProcessCompanies.tcCompanyCode.
            else assign olEof = true.
        end.
    end finally.
end.    /* CYBLOCK */