7 Replies Latest reply on Feb 22, 2016 5:34 AM by adinn

    BMUnit against a remote JVM

    ibrencic

      Hi,

       

      I would like to test an application that is already running in another JVM with BMUnit. I see that it is possible to specify a host:port in the @BMUnitConfig annotation, but I dont understand the details. Using the command line it is possible to install the Byteman agent with the bminstall command to another JVM, and after that it is possible to load rules with bmsubmit. This is exactly what I want to do from a JUnit test: install the agent to a remote JVM, load rules to it, and run tests against it. Is this possible?

       

      Thanks,

      Ivan

        • 1. Re: BMUnit against a remote JVM
          adinn

          Hi Ivan,

          Ivan Brencsics wrote:

           

          I would like to test an application that is already running in another JVM with BMUnit. I see that it is possible to specify a host:port in the @BMUnitConfig annotation, but I dont understand the details. Using the command line it is possible to install the Byteman agent with the bminstall command to another JVM, and after that it is possible to load rules with bmsubmit. This is exactly what I want to do from a JUnit test: install the agent to a remote JVM, load rules to it, and run tests against it. Is this possible?

           

          Yes, it is possible to do what you want. You need to do two things:

           

          • tell BMUnit not to load the agent into the JVM which is running the unit tests
          • ensure BMUnit submits rule load and unload requests to the other JVM

           

          Depending upon how you have started the other JVM step 2 may well be unnecessary.

           

          The first step can be achieved by configuring attribute inhibitAgentLoad=true in the @BMUnitConfig annotation on your unit test class. Alternatively, you can ensure that the JVM running the unit tests is started with -Dorg.jboss.byteman.contrib.bmunit.agent.inhibit on the java command line.

           

          If you have installed the agent into the other JVM without configuring the agent hostname and port options then you don't need to do anything else.The BMUnit code in the JVM running the unit tests will attempt to upload and unload your Byteman rules to the agent listener using address localhost and port 9091. Similarly, the agent listener in the other JVM will be listening on address localhost port 9091.

           

          Of course, the advice above assumes that the two JVMs are both running on the same machine. If not then you need to configure the network name or IP address for the other JVM's host in the @BMUnitConfig annotation and install the agent using that same hostname. Depending on your firewall settings you may also need to specify a different port. If you need help for this sort of setup on how to configure the @BMUnitConfig annotation or pass the hostname and port when installing the agent let me know and I'll help you to get it working.

           

          regards,

           

           

          Andrew Dinn

          • 2. Re: BMUnit against a remote JVM
            ibrencic

            Hi Andrew,

             

            Thanks for the quick answer. By using the inhibitAgentLoad option as you recommended, I managed to make my tests up and running. I am starting up the "remote" JVM with the -javaagent option, and BMUnit successfully loads the rules to it.

             

            You mentioned that there is also the possibility to load the agent to the remote JVM from BMUnit. How exactly should that be done?

             

            Thanks,

            Ivan

            • 3. Re: BMUnit against a remote JVM
              adinn

              Ivan Brencsics wrote:

               

              Hi Andrew,

               

              Thanks for the quick answer. By using the inhibitAgentLoad option as you recommended, I managed to make my tests up and running. I am starting up the "remote" JVM with the -javaagent option, and BMUnit successfully loads the rules to it.

               

              Excellent. I'm very glad you have got it working.

              Ivan Brencsics wrote:

               

              You mentioned that there is also the possibility to load the agent to the remote JVM from BMUnit. How exactly should that be done?

               

              Did I? Oops, that's not what I thought I said :-) At present there is no way to tell BMUNit to install the agent into some other JVM. All you can do is either install it in the JVM running the Unit tests or inhibit installation as I explained in the last post.

               

              Are you thinking of this maybe:

               

              . . . you need to configure the network name or IP address for the other JVM's host in the @BMUnitConfig annotation and install the agent using that same hostname

               

              If so then I obviously didn't make it very clear what I meant. I was referring to the case where the two JVMs were on different machines. All I meant was the following

               

              If you want to run the Byteman agent in the other JVM on host foobar.my.org listening on port 36001 then you need to start it using a java command looking like this

               

              java -javagent:/path/to/byteman.jar=listener:true,hostname:foobar.my.org,port:36001 . . .
              
              

               

              and you need to edit BMUnitConfig for the tests like this

               

              @BMUnitConfig(
                  hostname="foobar.my.org",
                  port=36001,
                  inhibitAgentLoad=true)
              class MyTestClass {
                  . . .
              
              

               

              This is just to make sure that the agent listener and the BMUNit submit client both use the same hostname and port when opening, respectively, their server socket and client socket. Obviously, you need to have domain info set up to be able to resolve the name ot an IP address (you should be able to put the IP address in as a string) and you need to ensure that it is safe for the agent listener to open a server socket on the associated network (using a firewall or whatever else is appropriate).

              .

              • 4. Re: BMUnit against a remote JVM
                ibrencic

                What is was looking for is the MBUnit alternative of the mbinstall. If I understand it right, with mbinstall one can install the agent to an already running JVM. I was thinking whether MBUnit can achieve the same: there is an already running target JVM containing no agent, then I start my BMUnit test that 1) installs the agent, 2) loads the rules, and 3) runs the tests. Is this possible? In fact this is not very important, it is not a problem at all to start the target JVM with the agent, I am just trying to explore all the features of ByteMan.

                • 5. Re: BMUnit against a remote JVM
                  adinn

                  Hi Ivan,

                  Ivan Brencsics wrote:

                   

                  What is was looking for is the MBUnit alternative of the mbinstall. If I understand it right, with mbinstall one can install the agent to an already running JVM. I was thinking whether MBUnit can achieve the same: there is an already running target JVM containing no agent, then I start my BMUnit test that 1) installs the agent, 2) loads the rules, and 3) runs the tests. Is this possible? In fact this is not very important, it is not a problem at all to start the target JVM with the agent, I am just trying to explore all the features of ByteMan.

                   

                  Yes, it would be possible to upload he agent to a remote JVM but that is not currently implemented.

                   

                  BMUnit uses class Install to do the agent load (the same class as is used by the install script). It passes the current process id (pid) to Install to specify which  JVM to load the agent into. The code could easily be rewritten so that you could specify the pid of a remote process from the command line e.g. by setting a System property. Of course, it would not be possible to use the BMUnitConfig annotation to specify the remote pid since you won't know the pid until the other JVM was running.

                  • 6. Re: BMUnit against a remote JVM
                    ibrencic

                    Yes, true, I forgot about it that the PID cant be hardcoded in the unit tests. Thanks Andrew for the clarifications.

                    • 7. Re: BMUnit against a remote JVM
                      adinn

                      Hi Ivan

                      Ivan Brencsics wrote:

                       

                      Yes, true, I forgot about it that the PID cant be hardcoded in the unit tests. Thanks Andrew for the clarifications.

                       

                      No problem. Thank you for using Byteman and don't hesitate to ask for help or advice if you have any problems getting your tests to work the way you want.

                       

                      regards,

                       

                       

                      Andrew Dinn