Epicor 10 BPM Custom Code

I need to create a BPM when a sales order line is created/updated.
I need to check the Par table if Part.QuoteRequired_c = true

I can create the Custom Code to give me a message.
But what I would really like to do is have the custom code return a true or false value.

Is this possible using Execute Custom Code?

Erp.Tables.Part Part;
foreach (var ttOrderDtl_iterator in (from ttOrderDtl_Row in ttOrderDtl
                                   where (string.Equals(ttOrderDtl_Row.RowMod, IceRow.ROWSTATE_ADDED, 
                                   StringComparison.OrdinalIgnoreCase) || string.Equals(ttOrderDtl_Row.RowMod, 
                                   IceRow.ROWSTATE_UPDATED, StringComparison.OrdinalIgnoreCase))
                                   select ttOrderDtl_Row))
{
  var ttOrderDtlRow = ttOrderDtl_iterator;
  
 
  Part = (from Part_Row in Db.Part
                      where string.Compare(Part_Row.Company, ttOrderDtlRow.Company, true) == 0
                      && ttOrderDtlRow.PartNum == Part_Row.PartNum && Part_Row.Part.QuoteRequired_c == true
                      select Part_Row).FirstOrDefault();
  

    if(Part == null)
    {   
    return  false;
    }
    else if(Part != null) 
   {
   return true;
   }      
}

The condition widget can do this without code. It’s the “Number of Rows in…” option.

return it to where?

Also can you please format your code / post. Instructions in the FAQ, and the Editor Window

I believe I figured it out, I was putting the custom code in the wrong place

Code used:

Erp.Tables.Part Part;
foreach (var ttOrderDtl_iterator in (from ttOrderDtl_Row in ttOrderDtl
                                   where (string.Equals(ttOrderDtl_Row.RowMod, IceRow.ROWSTATE_ADDED, 
                                   StringComparison.OrdinalIgnoreCase) || string.Equals(ttOrderDtl_Row.RowMod, 
                                   IceRow.ROWSTATE_UPDATED, StringComparison.OrdinalIgnoreCase))
                                   select ttOrderDtl_Row))
{
  var ttOrderDtlRow = ttOrderDtl_iterator;
 
 
  Part = (from Part_Row in Db.Part
                      where string.Compare(Part_Row.Company, ttOrderDtlRow.Company, true) == 0
                      && ttOrderDtlRow.PartNum == Part_Row.PartNum
                      && Part_Row.QuoteRequired_c == true
                      select Part_Row).FirstOrDefault();
                      

    if(Part == null);
     {
      return false;
  }
   
}
return true;

Ok, that’s not it.
The Code is Valid.
I need to return true or false.
Hopefully the picture helps.

What he said

Jason_Woods
Thank you, yes this may work for this example.
However if I can figure this out with code, I can use this in other areas.

What method directive is this on? Please format your code when you post. Also your code can be cleaned up quite a bit. Where did you get this example from?

foreach (var ttOrderDtl_iterator in (from ttOrderDtl_Row in ttOrderDtl
where (string.Equals(ttOrderDtl_Row.RowMod, IceRow.ROWSTATE_ADDED,
StringComparison.OrdinalIgnoreCase) || string.Equals(ttOrderDtl_Row.RowMod,
IceRow.ROWSTATE_UPDATED, StringComparison.OrdinalIgnoreCase))
select ttOrderDtl_Row))
{
}

// Can be condensed to 
foreach (var ttOd in ttOrderDtl.Where(x => x.Added() || x.Updated()))
{
}

Method Directive Erp.SalesOrder.Update
Thanks for the condensed version, I got this code from other bpms written in our system.
wasn’t sure how to format.

I would verify that you are getting rows back as you expect. I’m guessing you’re not getting a part back. You can use publish infomessage in your bpm throughout your code to see at what points you have what data, or you can use the ice log and write event viewer events to the server to review. Step through it and find where the breakdown is.

even more condensing: you can reduce the entire Part Lookup to do an “Any” lookup which returns either a true or false.

bool QuoteRequired = false;
foreach ttODtl in ttOrderDtl.Where(x=>x.Added() || x.Updated()){
    bool PartQuoteRequired = Db.Part.Where(x=>x.Company == ttODtl.Company && x.PartNum == ttODtl.PartNum && x.QuoteRequired).Any();
    if (PartQuoteRequired == true) QuoteRequired = true;

}

His QuoteRequired field is on the Part table otherwise for sure that would be a quick way to do a custom condition. That being said never join TT tables on DB tables, the two individual statements he originally had would be the way to go vs doing a join with a single Any() statement in this case.

@mnewman, This is what @josecgomez is talking about.

Thank you for all the responses.
However I am not a programmer.
I can a hack a little.
So most of what you say, I am not completely understanding.
That being said.
What I am trying to achieve is to do a condition that returns a true or false.
So I can then do other things like e-mail or messages or etc.
I just need to know if its possible to do this, because it seems by dragging the Execute custom code caller does not seem to be able to return a value.

I then tried to use the Condition flow chart.
But the only custom code available condition returns valid or invalid rather than true or false.

Please forgive me for not speaking programmer lingo.

I have provided a picture hoping to help you understand what I am trying to achieve in this example.
At this point I am wondering if its possible, if so how.

I am not sure how to format my code example in this message.

Use that one. Make your query to find the part number of your ttDataset, joined with the Part table on company and then filter the part table to only show parts that your custom field is true on.

(I know, don’t join TT to DB tables… Blah blah blah, yes it’s slow but it works.) Try this out and if the logic works, you can change how to joins are done later.

Banderson
I don’t know of any other way to link the part number on the sales order line (On The Screen) to the part number in the part table and check a field value. other than linking the ttTable to the Part Table

There have been several occasions that the option you have shown above does not work.
I have found if I do it with custom code and have the code create a message it works every time.
However, instead of coding the message and email, I am wondering if I can create custom code that returns true or false to be able to continue using the guid to do these types of things.

Sure, just make a bool var, then you can use that variable in your code.

Banderson
not sure how to do that and make it work…

Make your variable here, then you can set set in custom code.

Then instead of this.

if(Part == null)
{   
return  false;
}
else if(Part != null) 

{
return true;
}

use this

if(Part == null)
{   
MyBoolVar = false;
}
else if(Part != null) 

{
MyBoolVar = true;
}
1 Like

You keep talking about “returning” a value to indicate if a quote is required. What is receiving that result?

You screen shots show that it shows a message (I assume for debugging), and sending an email. Is the desire to send an email when a Part is entered and the QuoteRequired_c is true?

Do you want the action to happen, even if a quote exists? Or just when QuoteRequired_c is true AND no matching quote found?

Don’t forget to check to see if the Part even exists. What should be done if a PartNumber that is not in the system is entered?