Writing your own tests: Sample 2

The following source code is an example of a test that checks queue names against a defined naming convention. If any queues are found with names that do not meet the defined naming convention, the details are displayed in the Test Results view.

/*                                                    
 * Licensed Materials - Property of IBM
 *  
 * 5724-H72, 5655-L82, 5724-L26, 5655R3600
 * 
 * (c) Copyright IBM Corp. 2005, 2020
 * 
 * disclosure restricted by GSA ADP Schedule Contract with IBM Corp.
 */
package com.ibm.mq.explorer.tests.sample;

/**
 * A sample test used to check Queue Names against naming conventions. Queue names are checked if
 * they begin with any of a set range of prefixes, defined in this class. Any names which do not
 * start with one of the prefixes are output in an error.
 *
 * This example uses the PCF classes provide by the MS0B SupportPac. Download the SupportPac from
 * the IBM website, then include the jar file in the build path for the project.
 */
public class WMQQueueNames extends WMQTest {

  /** Maintain a count of how many queue managers we are waiting for replies from. */
  private static int numberOfQmgrs = 0;

  /** Stores the accepted queue name prefixes. */
  private static final String[] ACCEPTED_Q_PREFIXES = {"SALES_", "MARKETING_", "SHIPPING_", //$NON-NLS-1$//$NON-NLS-2$ //$NON-NLS-3$
      "INCOMING_", "OUTGOING_"}; //$NON-NLS-1$//$NON-NLS-2$

  /** Stores the user preference for whether system queues should be included. */
  boolean includeSystemObjs = false;

  /**
   * Starts the test.
   * 
   * 
   * @param callback handle to the test engine running the test
   * @param guimonitor a handle to the object monitoring the test, provided to allow the test to
   * periodically check if the user has tried to cancel the test running and provide additional user
   * feedback
   * @param contextObjects context MQExtObjects passed to the test engine
   * @param treenodeId the treenodeid used to launch the tests
   */
  public void runTest(WMQTestEngine callback, IProgressMonitor guimonitor,
      MQExtObject[] contextObjects, TreeNode treenodeId) {

    // start with the default implementation. this will store a handle
    //  to the test engine that will be needed when we want to submit
    //  any results at the end of the test
    super.runTest(callback, guimonitor, contextObjects, treenodeId);

    // prepare space to store any results we might want to return
    ArrayList testResults = new ArrayList();

    // get from Preferences whether we should include system queues
    includeSystemObjs = PreferenceStoreManager.getIncludeSysObjsPreference();

    // get a list of queue managers from the Explorer
    ArrayList allQmgrs = new ArrayList();

    for (int k = 0; k < contextObjects.length; k++) {
      if (contextObjects[k] instanceof MQQmgrExtObject) {
        // Object is a queue manager, add to list
        allQmgrs.add(contextObjects[k]);
      }
    }

    // how many queue managers are there?
    numberOfQmgrs = allQmgrs.size();

    // use the number of queue managers as a guide to track progress
    guimonitor.beginTask(getTestName(), numberOfQmgrs);

    // for each queue manager, submit a query
    for (int i = 0; i < numberOfQmgrs; i++) {

      // get next queue manager
      MQQmgrExtObject nextQueueManager = (MQQmgrExtObject) allQmgrs.get(i);

      // only submit queries to connected queue managers
      if (nextQueueManager.isConnected()) {

        // get the name of the queue manager, for use in GUI
        String qmgrName = nextQueueManager.getName();

        // get a handle to a Java object representing the queue manager
        MQQueueManager qmgr = nextQueueManager.getMQQueueManager();

        try {
          // get a PCF message agent to handle sending PCF inquiry to
          PCFMessageAgent agent = new PCFMessageAgent(qmgr);

          // use PCF to submit an 'inquire queue names' query
          PCFMessage response = submitQueueNamesQuery(qmgrName, agent);

          // did we get a response to the query?
          if (response != null) {
            // get the queue names out of the reply
            String[] qnames = (String[]) response.getParameterValue(CMQCFC.MQCACF_Q_NAMES);

            // check each name
            for (int j = 0; j < qnames.length; j++) {
              boolean qnameOkay = checkQueueName(qnames[j]);

              if (!qnameOkay) {
                // if a problem was found with the name, we generate an
                //  error message, and add it to the collection to be
                //  returned
                testResults.add(generateTestResult(qnames[j], qmgrName));
              }
            }
          }
        }
        catch (MQException e) {
          // record error details
          e.printStackTrace();
        }
      }

      // finished examining a queue manager
      guimonitor.worked(1);
    }

    // return any results that this test has generated
    WMQTestResult[] finalresults = (WMQTestResult[]) testResults
        .toArray(new WMQTestResult[testResults.size()]);
    testComplete(finalresults);
  }

  /**
   * Used internally to submit a INQUIRE_Q_NAMES query using PCF to the given queue manager.
   * 
   * 
   * @param qmgrName name of the queue manager to submit the query to
   * @param agent
   * @return the PCF response from the queue manager
   */
  private PCFMessage submitQueueNamesQuery(String qmgrName, PCFMessageAgent agent) {

    // build the pcf message
    PCFMessage inquireQNames = new PCFMessage(CMQCFC.MQCMD_INQUIRE_Q_NAMES);
    inquireQNames.addParameter(CMQC.MQCA_Q_NAME, "*"); //$NON-NLS-1$

    try {
      // send the message
      PCFMessage[] responseMsgs = agent.send(inquireQNames);

      // check if results received successfully
      if (responseMsgs[0].getCompCode() == 0) {
        return responseMsgs[0];
      }
    }
    catch (IOException e) {
      // record error details
      e.printStackTrace();

    }
    catch (MQException e) {
      // record error details
      e.printStackTrace();
    }

    // for some reason, we don't have a response, so return null
    return null;
  }

  /**
   * Used internally to check the given queue name against the collection of acceptable prefixes.
   * 
   * 
   * @param queueName queue name to check
   * @return true if the queue name is okay, false otherwise
   */
  private boolean checkQueueName(String queueName) {

    // if this is a system object (i.e. it has a name which begins with
    //   "SYSTEM.") we check the
    if ((queueName.startsWith("SYSTEM.")) || (queueName.startsWith("AMQ."))) { //$NON-NLS-1$//$NON-NLS-2$
      if (!includeSystemObjs) {
        // user has requested that we do not include system
        //  objects in the test, so we return true to
        //  avoid any problems being reported for this queue
        return true;
      }
    }

    // PCF response will white-pad the queue name, so we trim it now
    queueName = queueName.trim();

    // check the queue name against each of the acceptable prefixes
    //  in turn, returning true immediately if it is
    for (int i = 0; i < ACCEPTED_Q_PREFIXES.length; i++) {
      if (queueName.startsWith(ACCEPTED_Q_PREFIXES[i]))
        return true;
    }

    // we have checked against all accepted prefixes, without
    //  finding a match
    return false;
  }

  /**
   * Used internally to generate a test result for the given queue name.
   *
   * 
   * @param queueName queue name which doesn't meet requirements
   * @param qmgrName name of queue manager which hosts the queue
   * @return the generated test result
   */
  private WMQTestResult generateTestResult(String queueName, String qmgrName) {
    String res = "Queue (" + queueName.trim() + ") does not begin with a known prefix"; //$NON-NLS-1$//$NON-NLS-2$

    return new WMQTestResult(IMarker.SEVERITY_ERROR, res, qmgrName, getTestSubCategory());
  }
}