web
You’re offline. This is a read only version of the page.
close
Skip to main content

Notifications

Announcements

No record found.

Community site session details

Community site session details

Session Id :
Finance | Project Operations, Human Resources, ...
Answered

contract object not initialized

(0) ShareShare
ReportReport
Posted on by 65

FRVMSIPspiffOverrideReportController Class:

class FRVMSIPSpiffOverrideReportController extends SrsReportRunController
{
}

protected void preRunModifyContract()
{
    VMSipAllowanceHeader header;

    super();

    if(this.parmArgs() && this.parmArgs().record())
    {
        this.parmReportContract().parmReportName(ssrsReportStr(FRVMSIPSpiffOverrideReport, FRVMSIPSpiffOverrideReport));
        this.parmReportName(ssrsReportStr(FRVMSIPSpiffOverrideReport, FRVMSIPSpiffOverrideReport));
    }
}

public static void main(Args _args)
{
    VMSipAllowanceHeader headerInfo;

    List programIds = new List(Types::String);

    FRVMSIPSpiffOverrideReportContract contract = new FRVMSIPSpiffOverrideReportContract();

    MultiSelectionHelper selectedSpiffs = MultiSelectionHelper::createFromCaller(_args.caller());

    FRVMSIPSpiffOverrideReportController controller = new FRVMSIPSpiffOverrideReportController();

    headerInfo = selectedSpiffs.getFirst();

    if(headerInfo)
    {
        while (headerInfo)
        {
            programIds.addEnd(headerInfo.ProgramId);

            headerInfo = selectedSpiffs.getNext();
        }
    }

    contract.parmProgramIds(programIds);

    controller.parmArgs(_args);

    controller.parmReportName(ssrsReportStr(FRVMSIPSpiffOverrideReport, FRVMSIPSpiffOverrideReport));

    controller.parmShowDialog(false);

    controller.startOperation();
}

FRVMSIPSpiffOverrideReportDP Class:

[
    SysEntryPointAttribute(false)
]
public void processReport()
{
    gVMSpiffOverrideReportTmp.clear();

    contract = this.parmDataContract() as FRVMSIPSpiffOverrideReportContract;
    
    _programIds = contract.parmProgramIds();

    if(_programIds != null)
    {
         programIdsListIterator = _programIds.getEnumerator();

         while(programIdsListIterator.moveNext())
        {
            programId = programIdsListIterator.current();

            while select allowanceHeader where programId == allowanceHeader.ProgramId
                join allowanceLine where allowanceHeader.RecId == allowanceLine.RecId
                join salesLine where allowanceLine.SalesLine == salesLine.RecId
                join spiffOverride where spiffOverride.AllowanceHeader == allowanceHeader.RecId
                join custTable where CustTable.RecId == allowanceLine.CustTable
                join inventTable where InventTable.RecId == spiffOverride.InventTable
                join spiffChassis where spiffChassis.AllowanceHeader == allowanceHeader.RecId
                join inventSite where inventSite.SiteId == allowanceHeader.InventSiteId
                join siteMapping where (siteMapping.SiteId == inventSite.SiteId && siteMapping.user == curUserId()) ||
                (siteMapping.user == curUserId())

            gVMSpiffOverrideReportTmp.ProgramIds = allowanceHeader.ProgramId;

            gVMSpiffOverrideReportTmp.SiteId = allowanceHeader.InventSiteId;

            gVMSpiffOverrideReportTmp.VMShortVIN = allowanceLine.frShortVIN;

            gVMSpiffOverrideReportTmp.VMVINNumber = allowanceLine.VINInfo;

            gVMSpiffOverrideReportTmp.Active = spiffOverride.frActive;

            gVMSpiffOverrideReportTmp.Amount = spiffOverride.Amount;

            gVMSpiffOverrideReportTmp.CustGroup = custTable.CustGroup;

            gVMSpiffOverrideReportTmp.CustomerDescription = spiffOverride.dispCustName(spiffOverride);

            gVMSpiffOverrideReportTmp.SalesGroup = CustTable.SalesGroup;

            gVMSpiffOverrideReportTmp.ItemNumber = inventTable.RecId;

            gVMSpiffOverrideReportTmp.ItemDescription = spiffOverride.dispItemDescription(spiffOverride);

            gVMSpiffOverrideReportTmp.OverrideNote = spiffOverride.frSipOverrideNote;

            gVMSpiffOverrideReportTmp.PaymentDate = spiffOverride.frDispTransDate();

            gVMSpiffOverrideReportTmp.ValidFrom = spiffOverride.ValidFrom;

            gVMSpiffOverrideReportTmp.ValidTo = spiffOverride.ValidTo;

            gVMSpiffOverrideReportTmp.insert();
        }
    }
}

The error occurs when I reach this line in the processReport method of my DP:

_programIds = contract.parmProgramIds();

Do I need a parmContract method to hold the contract instead of just the new statement in the controller class?

I have the same question (0)
  • Suggested answer
    GirishS Profile Picture
    27,827 Moderator on at

    Hi JGjinx,

    You need to make use of the parmDataContract method to get instance of contract class.

    contract = this.parmDataContract() as contractClassName.

    Thanks,

    Girish S

  • JGjinx321 Profile Picture
    65 on at

    So from my knowledge, we first go to the contract class >  then controller class.

    I initialize FRVMSIPContract in main method of controller class.

    After finishing my controller main method loop, I then call your statement contract = this.parmDataContract() as FRVMSIPSpiffOverrideContract???

    From there, in my DP.ProcessReport I can then call that instance of the contract class and get the controller main method loop values I wanted to bring to DP?

    Would that call be the same statement used to store contract class value? Or is it another statement to retrieve information???

    Sorry if it's a lot of questions.

    Still just trying to get my understanding down correctly.

  • GirishS Profile Picture
    27,827 Moderator on at

    You know need to call the specific class. It will be done automatically by standard. Report will start from -

    Controller class - Controller class will contain the basic information about report dialog caption - Name of the report design.

    UI builder class - This class is mainly used to represent the dialog shown to the user in more representative way - Adding lookup to the control etc.

    Contract class -This class will have parm methods and values given from the dialog box is assigned to parm methods.

    Data provider class (DP) - This is the class which container business logic for the report - Get the contract class instance using contract = this.parmDataContract() as FRVMSIPSpiffOverrideContract.

    Now using that contract buffer, you can get the values given in the report dialog and based on that filter you can write code to insert record into temp table.

    Refer to the below link.

    https://community.dynamics.com/ax/b/dynamics101trainingcenterax/posts/developing-a-ssrs-report-using-the-report-data-provider-in-microsoft-dynamics-ax-2012

    Thanks,

    Girish S.

  • JGjinx321 Profile Picture
    65 on at

    Thank you! :)

  • JGjinx321 Profile Picture
    65 on at

    Hi Girish, I've added a few things to my code that I will update in the original post.

    (The parm method you mentioned as well as tmpTable.clear())

    I've added your statement. When I run through the debugger the method seems to try and pull a parm'd contract from the method. But the value returned back is null.

    It's like it still doesn't recognize that previous contract class instance I created in my controller when assigning values to a parameter.

    Do you know why this is?

    I see in the tutorial the process for this is the same. So I can't think of much myself besides the fact for my contract class I'm extending SysOperationInitializable.

    For my data class I'm extending SrsReportDataProviderPreProcess.

  • Verified answer
    GirishS Profile Picture
    27,827 Moderator on at

    I think you missed the line of code pass to contract values to parmRdpContract method of controller class. Refer to the main method of controller class.

    public static void main(Args _args)
    {
        VMSipAllowanceHeader headerInfo;
    
        List programIds = new List(Types::String);
    
        FRVMSIPSpiffOverrideReportContract contract = new FRVMSIPSpiffOverrideReportContract();
    
        MultiSelectionHelper selectedSpiffs = MultiSelectionHelper::createFromCaller(_args.caller());
    
        FRVMSIPSpiffOverrideReportController controller = new FRVMSIPSpiffOverrideReportController();
    
        headerInfo = selectedSpiffs.getFirst();
    
        if(headerInfo)
        {
            while (headerInfo)
            {
                programIds.addEnd(headerInfo.ProgramId);
    
                headerInfo = selectedSpiffs.getNext();
            }
        }
    
        contract.parmProgramIds(programIds);
    
        controller.parmArgs(_args);
    
        controller.parmReportName(ssrsReportStr(FRVMSIPSpiffOverrideReport, FRVMSIPSpiffOverrideReport));
    
        controller.parmShowDialog(false);
        //this is the line added to pass contract values.
        controller.parmReportContract().parmRdpContract(contract);
        
        controller.startOperation();
    }

    Also don't forget to decorate the DP class with dc class using the attribute.

    [
      SRSReportParameterAttribute(classStr(FRVMSIPSpiffOverrideReportContract))
    ]
    public class YourRDPClassName extends SrsReportDataProviderPreProcess
    {
        
    }

    Thanks,

    Girish S.

  • JGjinx321 Profile Picture
    65 on at

    Thanks!

Under review

Thank you for your reply! To ensure a great experience for everyone, your content is awaiting approval by our Community Managers. Please check back later.

Helpful resources

Quick Links

Responsible AI policies

As AI tools become more common, we’re introducing a Responsible AI Use…

Neeraj Kumar – Community Spotlight

We are honored to recognize Neeraj Kumar as our Community Spotlight honoree for…

Leaderboard > Finance | Project Operations, Human Resources, AX, GP, SL

#1
Martin Dráb Profile Picture

Martin Dráb 565 Most Valuable Professional

#2
André Arnaud de Calavon Profile Picture

André Arnaud de Cal... 450 Super User 2025 Season 2

#3
Sohaib Cheema Profile Picture

Sohaib Cheema 250 User Group Leader

Last 30 days Overall leaderboard

Product updates

Dynamics 365 release plans