C# Code in BPM Expression

I have created a Data Directive BPM on the PartTran Table Using the InTransaction process that simply sets the field to my name. All I did in the expression was to put in “Trygve” That works fine.

Now that I have found the way to update I want to do is set the field to a resource ID but don’t know how to write the expression.

If I take the information in the PartTran record and tie the Company, JobNum, Assembly Seq fields to the JobOpDtl table I then can get the ResourceID from the JobOpDtl and use that to update.

Any help appreciated as we are changing a process tomorrow and need to get this working to be able to have the value for printing labels.

In a data directive, you only have easy access to the table you are working with. If you want to get info from other tables, you will need to use a Linq expression. Do some searching on the forum and you can find some examples, however this isn’t a beginner level code solution.

PartTran is probably one of the tables you shouldnt put a DD on, or write to.

1 Like

@tthayer - It sounds like you might want to be adding the ResourceID to the material transaction for that JobOpSeq - eg set the value to determine which resource received the material.

If that is the case, may I suggest that you instead use a method directive on the issue material transaction. You have access to all the data you need in one step (I believe), or because it’s a method directive, you can call the BO to look up the resource on the JobOpDtl. Plus, you can also catch any material returns as well.

1 Like

Mike,

It is true I am looking for the ResourceID in the JobOpDtl table. I am needing this when a record is added to PartTran so I can use that value to determine where to print a label as there are many printers to print to. I am not against using the method directive but do not know how to Call the BO to look up the ResourceID on the JobOpDtl table.

Example of an Expression returning t/f because of Any() from OrderHed.

4 Likes

which transaction is doing this - Material Issue? Job Receipt to Inv? I would still use the Method Directive for these rather than a DD on PartTran.

In the Method Directive you could use the BO widget to call the BO, or you could use the custom code widget, or you could use @hkeric.wci’s method above.

This is a great help for me to see an example. Now if I just had an example that returned a value instead of True/False.

(from oh in Db.OrderHed.With(LockHint.NoLock) where oh.Company == ttInvcHeadRow.Company && oh.OrderNum == ttInvcHeadRow.OrderNum && oh.idxConsInv_c == true select oh.OrderNum).DefaultIfEmpty("").First()

Another thing you can do is create a variable and then set it to a variable and use it throughout your workflow by referencing the variable.

2 Likes

What I ended up with was writing custom code on the Data Directive for PartTran in the In Transaction section. Works wonderful now !!!

Erp.Tables.JobOpDtl JobOpDtl;

foreach(var ttPartTran_iterator in (from ttPartTran_Row in ttPartTran

                                    where ttPartTran_Row.TranType == "“MFG-STK"”

                                    select ttPartTran_Row))

{

  var ttPartTranRow = ttPartTran_iterator;

  if(ttPartTranRow != null)

  {

     JobOpDtl = (from JobOpDtl_Row in Db.JobOpDtl

                                       where JobOpDtl_Row.Company == ttPartTranRow.Company Company

                                       && JobOpDtl_Row.JobNum == ttPartTranRow.JobNum

                                       && JobOpDtl_Row.AssemblySeq == ttPartTranRow.AssemblySeq

                                       select JobOpDtl_Row).FirstOrDefault();

    {

      if(JobOpDtl != null)

      {

        ttPartTranRow["“ShortChar01"”] = JobOpDtl.ResourceGrpID;

      }

    }

  }

}

Opportunities for Improvement:

Do Not do SELECT * - ask for what you need

// Specifying the columns you want avoids select *
JobOpDtl = (from JobOpDtl_Row in Db.JobOpDtl
     where JobOpDtl_Row.Company == ttPartTranRow.Company 
      && JobOpDtl_Row.JobNum == ttPartTranRow.JobNum
      && JobOpDtl_Row.AssemblySeq == ttPartTranRow.AssemblySeq
      select new { JobOpDtl_Row.ResourceGrpID, Anothercolumn }).FirstOrDefault();

If you only need 1 column you can just return it

string resGroupID = (from JobOpDtl_Row in Db.JobOpDtl
     where JobOpDtl_Row.Company == ttPartTranRow.Company 
      && JobOpDtl_Row.JobNum == ttPartTranRow.JobNum
      && JobOpDtl_Row.AssemblySeq == ttPartTranRow.AssemblySeq
      select JobOpDtl_Row.ResourceGrpID).DefaultIfEmpty("").First();

Looking over your query it could trigger several times you should specify when by using ttPartTran_Row.Added() or Updated():

foreach(var ttPartTran_iterator in (from ttPartTran_Row in ttPartTran
                      where ttPartTran_Row.Added() 
                      && ttPartTran_Row.TranType == "MFG-STK"
                      select ttPartTran_Row))
3 Likes