Skip to main content

Hi, I have a strange issue in this sampler tool which relates to a python syntax in a private parameter. The CT is based on an old tool that used to be on the hub. I have updated it, but it fails to work if parameters are set from outside the CT. If they are hard coded, then the tool works just fine. Any ideas?

Miika

You may not need to use this custom transformer anymore, the regular Sampler now has a "randomize sampling" option


You may not need to use this custom transformer anymore, the regular Sampler now has a "randomize sampling" option

One critical thing for me that is not in the standard Sampler transformer is the possibility to sample by percentage. That's why I still use this.

 

 


I had a look and I agree that FME behaves weirdly, might be a bug.

The code that crashes is the scripted private parameter "RandomizerPercentagePython" which references:

FME_MacroValuesp'RandomizerPercentage']

When it crashes, the error message shows the following reference, however:

FME_MacroValuese'RandomizedSampler_WORKSPACE_NAME']

So I have the impression that FME tries to do something clever about resolving the published parameter names inside the scripted parameter, but fails.

I'd report this to Safe as a potential bug.


Here's a workaround that confuses FME sufficiently to not mess with the scripted parameter. Modify the script inside the private parameter "RandomizerPercentagePython" as follows:

return (100/float(FME_MacroValues.get('RandomizerPercentage')))

Just be aware that this won't work properly if you have several instances of the RandomizedSampler transformer with different values for RandomizerPercentage.


Hi @miikamakela, I don't know why the published parameter won't be evaluated in a scripted parameter defined in a custom transformer, but it seems to be a de facto limitation in the current FME.

As a workaround, how about this modification?

  • Move the scripted parameter "RandomizePercentagePython" from the custom transformer to the Main.
  • In the Main, link this parameter to the "RandomizePercentage" parameter in the RandomizedSampler.
  • In the custom transformer, link the "RandomizePercentage" parameter to the "Sampling Range" parameter of the Sampler_2.

Here's a workaround that confuses FME sufficiently to not mess with the scripted parameter. Modify the script inside the private parameter "RandomizerPercentagePython" as follows:

return (100/float(FME_MacroValues.get('RandomizerPercentage')))

Just be aware that this won't work properly if you have several instances of the RandomizedSampler transformer with different values for RandomizerPercentage.

Interesting. This scripted parameter also worked fine in the custom transformer.

 

import fme
return (100/float(fme.macroValues>'RandomizerPercentage']))

Interesting. This scripted parameter also worked fine in the custom transformer.

 

import fme
return (100/float(fme.macroValuese'RandomizerPercentage']))
I suspect that FME somehow does a search/replace on scripted parameters inside a custom transformer by looking for "FME_MacroValues ...]".

Here's a workaround that confuses FME sufficiently to not mess with the scripted parameter. Modify the script inside the private parameter "RandomizerPercentagePython" as follows:

return (100/float(FME_MacroValues.get('RandomizerPercentage')))

Just be aware that this won't work properly if you have several instances of the RandomizedSampler transformer with different values for RandomizerPercentage.

@david_r, your expression and mine both seem to refer the value of the "RandomizerPercentage" defined in the Main canvas, rather than the same name parameter definition in the custom transformer. This may not be desired behavior...

The code below seems to work, and it also uses the local instance parameter rather than the global parameter:

import fme
percentage = fme.resolveFMEMacros(FME_MacroValuesa'RandomizerPercentage'])
return 100/float(percentage)

@takashi: The above gets automatically "translated" to the following when FME runs:

  import fme
  percentage = fme.resolveFMEMacros(FME_MacroValues FME_MacroValuesM'RandomizedSampler_WORKSPACE_NAME'] + '_' + 'RandomizerPercentage'])
  return 100/float(percentage)


@david_r, your expression and mine both seem to refer the value of the "RandomizerPercentage" defined in the Main canvas, rather than the same name parameter definition in the custom transformer. This may not be desired behavior...
Yes, you're right. I've posted another solution that fixes this problem.

The code below seems to work, and it also uses the local instance parameter rather than the global parameter:

import fme
percentage = fme.resolveFMEMacros(FME_MacroValuesa'RandomizerPercentage'])
return 100/float(percentage)

@takashi: The above gets automatically "translated" to the following when FME runs:

  import fme
  percentage = fme.resolveFMEMacros(FME_MacroValues FME_MacroValuesM'RandomizedSampler_WORKSPACE_NAME'] + '_' + 'RandomizerPercentage'])
  return 100/float(percentage)

Thanks for sharing the tip, @david_r. Definitely it works as expected.

 

I've never seen a comprehensive documentation on the Python fme module. Could you tell me where you found the description on the fme.resolveFMEMacros function?

 


Thanks for sharing the tip, @david_r. Definitely it works as expected.

 

I've never seen a comprehensive documentation on the Python fme module. Could you tell me where you found the description on the fme.resolveFMEMacros function?

 

It's based on the expand_fme_macros() function that I posted here: https://knowledge.safe.com/idea/23605/python-function-to-extract-absolute-path.html

 

See also the comment from @stephenwu further down.

 

Documentation: http://docs.safe.com/fme/2017.0/html/FME_Desktop_Documentation/FME_Workbench/Configuration/FME_BEGIN_PYTHON.htm
Thanks for sharing the tip, @david_r. Definitely it works as expected.

 

I've never seen a comprehensive documentation on the Python fme module. Could you tell me where you found the description on the fme.resolveFMEMacros function?

 

Just to be clear, it isn't fme.resolveFMEMacros() that "translates" the parameter name to include the instance name, that's FME itself. The function resolveFMEMacros() only de-references the string content "$(RandomizerPercentage)" to it's actual value so that it can be cast as a float.
you guys rock! thanks a lot for your support!


Just to be clear, it isn't fme.resolveFMEMacros() that "translates" the parameter name to include the instance name, that's FME itself. The function resolveFMEMacros() only de-references the string content "$(RandomizerPercentage)" to it's actual value so that it can be cast as a float.
Thanks again. I learned something new today :-)

 

 


Reply