Load embedded Methods in rails console

Problem
While debugging on the rails console this week, I needed to load some code that we use as embedded methods. Usually I would just copy and paste it from the UI, but since Hammer can load embedded methods recursively now, this does no longer work…

After a day of digging in the code I came up with a solution, which is probably helpful for a bunch of you guys.

Full code: https://gist.github.com/ThomasBuchinger/a34b9c242c01da3315680f5b546b0ee5

Short Description
The code without the fluff boils down to this:

$evm = AeLoader.get_evm()
aem = MiqAeMethod.where(name: 'lib_validation')
data =  MiqAeEngine::MiqAeMethod.send(:bodies_and_line_numbers, $evm, aem)
eval(data[0].join("\n"))
  • Obtain a working MiqAeWorkspace (i.e. $evm)
  • Get the Method from the database (MiqAeMethod), with a given path
  • Use MiqAeEngine::MiqAeMethod to resolve the embedded methods and return the contents as string
  • evaluate the code in the current context

Usage

ae = AeLoader.new($evm) # if you already have a workspace
ae = AeLoader.new  # or let AeLoader create a new workspace 

# :include_embedded_methods returns the content of all embedded methods as one long
# string, ready to be evaluated in the current context
eval(ae.include_embedded_methods('StdLib/Automate/Validation/lib_validation'))

# :include_method will also includes the data of the actual method, not only the embedded ones
eval(ae.include_method('StdLib/Automate/Validation/lib_validation'))

# both methods also accept a MiqAeMethod object, in case the URL translation fails
eval(ae.include_method(MiqAeMethod.where(name: 'lib_validation').first))

This is pretty cool @buc ! I could see us making much of this more accessible from the Rails console directly, so you don’t have to resort to calling .send on various private methods. @mkanoor @tinaafitz Thoughts?

Thanks :slight_smile:

While we are thinking about opening some internals to rails console, maybe other people have some rails console hacks, they want to share?

  • We sometimes set the retry counter of a state machine back to 0
  • One thing we discussed last week was the ability set ae_next_state from rails, allowing us to move the request to an earlier step in the state machine

We came up with one more use-case:

  • Setting StateVars of a workflow from rails.

Great code!

In your code, you have the class method “def self.get_evm…”
This causes error ‘no such method…’ on creating an instance of AeLoader,
because of calling the class method from the instance method.
I make it instance method (without self), then all works ok.
Am I right?

Also, can you provide some examples of how are you using this class, AeLoader on practice?

Hi,
Thanks for notecing the Bug :slight_smile: I am not sure if i got your questions, but i’ll give it a shot

I am mostly using it interactively in rails console if I need to load a bunch of code from the automate domain (e.g. we have out own IPAM Service, which would be a pain to interact with using only RestClient).

What AeLoader does is, resolving the AeMethod path (as it appears in the UI) into the content of those methods and any dependent embedded methods. The crucial thing is, that AeLoader only returns the content of everything as one long string, so you need to evaluate the code using the eval method

ae = AeLoader.new

# Just output a Method from the Automate domain
puts ae.include_method("/Integration/MyCustomIPAM/Methods/ipam_client")

# Using the Method in rails console
eval( ae.include_method("/Integration/MyCustomIPAM/Methods/ipam_client") )

# calling the code
ipam = MyCustomIPAM::Client.new
ipam.new_ip("192.168.1.0")

Hi Thomas,

Thank for your prompt reply.

AeLoader is very cool.

I understand you went deeply in miq code in order to create it.

I start using it for interactive flow as you described.

This gives the way to manually test the code in automation.

I wonder do you have any idea of how to test such code by Rspec or the like?

Also, it is very interesting what is the flow of your development:

That is, do you first write scripts via UI and then test on the server,

or you write scripts on server and then import them (via UI, via rake: import, others ways…)

Sorry for the late reply… I kind of want to keep this a Reference Thread for AeLoader Script and avoid offtopic discussions. I sent you a message with the Reply.

About Aeloader.

Very useful class, really!

I, may be, have found some problem:

The method ‘include_method’ is defined as
“load the method AND embedded methods into the current context”

I noticed that this method actually returns the method content twice!
Why? Because it call the method “include_embedded_methods(aem)”,
which returns content of embedded methods AND content of the method itself.
Then the method ‘include_method’ add method content again!

Am I right?

Yes is does. Never noticed it. Fixed it, thanks