Many thanks for JFC-Unit. It helps us a lot in automating our tests in a big project (postal automation).
Here a modified class that might interest you.
A few more classes will follow.
JLabelFinderTagHandler.java can block the program flow as long as
- a label is enabled
- a label is disabled
Benifit
Example:
Sometimes you get a status label in a GUI saying something like "Please wait. Loading data..".
The robot should wait until this message has vanished.
The javadoc explains the usage.
If you think this modification is usefull for you or other users please intergrate it into the official version.
It would be very helpfull because we won't have any trouble if you come out with the next version of JFC-Unit.
The changes are documented/explained in the javadoc of the source code.
Here a brief description on how we used JFC-Unit.
- Huge mail distribution center (J2EE architecture)
- Performance and functional tests.
- Many different Java-GUIs where tested (all commanded by JFC-Unit robots)
- Many parallel working robots of the same type
- The robots have to react according to the feedback of the GUI. (A robot has to cope with different scenarios.)
- The robots take their data from XML files (as input for GUIs)
- Error and status messages are written back into these files.
- The files are move from one robot to another
- (The sytem is very dynamical and the robots have to cope with it.)
May be it encourages others to use JFC-Unit as well.
Thanks a lot.
Tom Wiedenhoeft
P.S. Please note to modify the files XMLConstants.java as shown below.
/**
* This is a extension of the findTagHandler element. Where the
* finder specified is JLabelFinder.
*
* <h3>Description</h3>
* <p>
* This creates a FrameFinder and executes the find.
* </p>
* <h3>Finder tag name</h3>
* <p>
* JLabelFinder
* </p>
* <h3>Parameters</h3>
* <table border="1" cellpadding="2" cellspacing="0">
* <tr>
* <td valign="top"><b>Attribute</b></td>
* <td valign="top"><b>Description</b></td>
* <td align="center" valign="top"><b>Required</b></td>
* <td valign="top"><b>Default</b></td>
* <td valign="top"><b>Values</b></td>
* </tr>
* <tr>
* <td valign="top">finder</td>
* <td valign="top">For this element the type must be set to JLabelFinder</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">N/A</td>
* </tr>
* <tr>
* <td valign="top">id</td>
* <td valign="top">Id for the object found.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">String</td>
* </tr>
* <tr>
* <td valign="top">refid</td>
* <td valign="top">Id for the object found.</td>
* <td valign="top" align="center">No</td>
* <td valign="top">Search in all windows</td>
* <td valign="top">Panel to be searched</td>
* </tr>
* <tr>
* <td valign="top">index</td>
* <td valign="top">The index of the element to select from the combo box.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">Zero based index of list items.</td>
* </tr>
* <tr>
* <td valign="top">label</td>
* <td valign="top">The text of the label to be found.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">None</td>
* <td valign="top">Regular expression defining the label.</td>
* </tr>
* <tr>
* <td valign="top">caseindependent</td>
* <td valign="top">Ignore the case if true</td>
* <td valign="top" align="center">No</td>
* <td valign="top">false</td>
* <td valign="top">true/false</td>
* </tr>
* <tr>
* <td valign="top">waitForDisabled</td>
* <td valign="top">Blocks the flow until the label is disabled
* But not longer then the time given. WATCH this:
* If the JLabel is not disabled after the time
* you gave as attribute value the reference to the
* JLabel will be null ("id").</td>
* <td valign="top" align="center">No</td>
* <td valign="top">10000</td>
* <td valign="top">long value in milliseconds</td>
* </tr>
* <tr>
* <td valign="top">waitForEnabled</td>
* <td valign="top">Blocks the flow until the label is enabled
* But not longer then the time given. WATCH this:
* If the JLabel is not enabled after the time
* you gave as attribute value the reference to the
* JLabel will be null ("id").</td>
* <td valign="top" align="center">No</td>
* <td valign="top">10000</td>
* <td valign="top">long value in milliseconds</td>
* </tr>
* </table>
* <h3>Example</h3>
* <blockquote><pre>
* <find
* finder="JLabelFinder"
* id="MyLabel"
* label="^My label$"
* index="0"
* />
* </pre></blockquote>
* <p>
* The above finds the first label with
* a text "My label"
* </p>
* <h3>Example</h3>
* <blockquote><pre>
* <find
* finder="JLabelFinder"
* id="MyLabel"
* label="^My label$"
* index="0"
* waitForEnabled="5000"
* />
* </pre></blockquote>
* <p>
* The above finds the first label with
* a text "My label". If the JLabel is enabled
* the programm flow is not blocked. If the label is not
* enabled the programm flow is blocked but only up to 5 seconds.
* </p>
* @see junit.extensions.jfcunit.finder.JLabelFinder
* @author Kevin Wilson
* @author <a href="mailto:vraravam@thoughtworks.com">Vijay Aravamudhan : ThoughtWorks Inc.</a>
* @author tom@smart-tail.com (Tom Wiedenhoeft, DV-Ratio acting under contract with Siemens L&A PA)
*/
public class JLabelFinderTagHandler extends BaseFindTagHandler {
/**
* Constructor for FindTagHandler.
*
* @param element The element to be processed
* @param testCase The IXMLTestCase that uses this element
*/
public JLabelFinderTagHandler(final Element element,
final IXMLTestCase testCase) {
super(element, testCase);
}
/**
* Get the value of the waitForEnabled attribute.
* @return String value of the waitForEnabled attribute.
*/
public String getWaitForEnabled() {
return getString(WAIT_FOR_ENABLED);
}
/**
* Get the value of the waitForDisabled attribute.
* @return String value of the waitForDisabled attribute.
*/
public String getWaitForDisabled() {
return getString(WAIT_FOR_DISABLED);
}
/**
* @see junit.extensions.xml.elements.AbstractTagHandler#validateElement()
*/
public void validateElement() throws XMLException {
// do the default validations from the super class
super.validateElement();
String timeEnabled = this.getWaitForEnabled();
String timeDisabled = this.getWaitForDisabled();
if(timeEnabled != null && timeDisabled != null)
{
throw new XMLException(
"Its not allowed to give both attributes "
+ WAIT_FOR_ENABLED + " and " + WAIT_FOR_DISABLED + ".",
null,
getElement(),
getTest().getPropertyCache());
}
}
/**
* Blocks the flow if the attibutes waitForDisabled or
* waitForEnabled are given.
*/
private void waitForEnablingDisabling()
{
// Was the component found?
String id = this.getString(ID);
Object o = getXMLTestCase().getProperty(id);
if(o == null)
{
// The component was not found. Do not block any longer.
return;
}
long startTime = System.currentTimeMillis();
JLabel jLabel = (JLabel) o;
if(timeEnabled != null)
{
if("".equals(timeEnabled))
{
timeEnabled = "10000";
}
long blockTime = 0;
try {
blockTime = Long.parseLong(timeEnabled);
} catch(NumberFormatException e) {
throw new XMLException(
"Failed to parse attribute value for "
+ WAIT_FOR_ENABLED + ". Must be long value.",
e,
getElement(),
getTest().getPropertyCache());
}
while(! jLabel.isEnabled())
{
long lapTime = System.currentTimeMillis() - startTime;
if(lapTime < blockTime)
{
continue;
}
else
{
// The JLabel is still not enabled. Set the property to null.
getXMLTestCase().addProperty(id, null);
return;
}
}
}
else if(timeDisabled != null)
{
if("".equals(timeDisabled))
{
timeDisabled = "10000";
}
long blockTime = 0;
try {
blockTime = Long.parseLong(timeDisabled);
} catch(NumberFormatException e) {
throw new XMLException(
"Failed to parse attribute value for "
+ WAIT_FOR_DISABLED + ". Must be long value.",
e,
getElement(),
getTest().getPropertyCache());
}
while(jLabel.isEnabled())
{
long lapTime = System.currentTimeMillis() - startTime;
if(lapTime < blockTime)
{
continue;
}
else
{
// The JLabel is still not enabled. Set the property to null.
getXMLTestCase().addProperty(id, null);
return;
}
}
}
By the way, we implemented all tests with XML files (no tests in java source). At the beginning we where not decided. But the TagHandlers provide sufficient program flow for us.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
Hallo!
Many thanks for JFC-Unit. It helps us a lot in automating our tests in a big project (postal automation).
Here a modified class that might interest you.
A few more classes will follow.
JLabelFinderTagHandler.java can block the program flow as long as
- a label is enabled
- a label is disabled
Benifit
Example:
Sometimes you get a status label in a GUI saying something like "Please wait. Loading data..".
The robot should wait until this message has vanished.
The javadoc explains the usage.
If you think this modification is usefull for you or other users please intergrate it into the official version.
It would be very helpfull because we won't have any trouble if you come out with the next version of JFC-Unit.
The changes are documented/explained in the javadoc of the source code.
Here a brief description on how we used JFC-Unit.
- Huge mail distribution center (J2EE architecture)
- Performance and functional tests.
- Many different Java-GUIs where tested (all commanded by JFC-Unit robots)
- Many parallel working robots of the same type
- The robots have to react according to the feedback of the GUI. (A robot has to cope with different scenarios.)
- The robots take their data from XML files (as input for GUIs)
- Error and status messages are written back into these files.
- The files are move from one robot to another
- (The sytem is very dynamical and the robots have to cope with it.)
May be it encourages others to use JFC-Unit as well.
Thanks a lot.
Tom Wiedenhoeft
P.S. Please note to modify the files XMLConstants.java as shown below.
---schnipp -- JLabelFinderTagHandler.java ---
package junit.extensions.jfcunit.finder;
import java.awt.Component;
import javax.swing.JLabel;
import junit.extensions.xml.IXMLTestCase;
import junit.extensions.xml.XMLException;
import org.w3c.dom.Element;
/**
* This is a extension of the findTagHandler element. Where the
* finder specified is JLabelFinder.
*
* <h3>Description</h3>
* <p>
* This creates a FrameFinder and executes the find.
* </p>
* <h3>Finder tag name</h3>
* <p>
* JLabelFinder
* </p>
* <h3>Parameters</h3>
* <table border="1" cellpadding="2" cellspacing="0">
* <tr>
* <td valign="top"><b>Attribute</b></td>
* <td valign="top"><b>Description</b></td>
* <td align="center" valign="top"><b>Required</b></td>
* <td valign="top"><b>Default</b></td>
* <td valign="top"><b>Values</b></td>
* </tr>
* <tr>
* <td valign="top">finder</td>
* <td valign="top">For this element the type must be set to JLabelFinder</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">N/A</td>
* </tr>
* <tr>
* <td valign="top">id</td>
* <td valign="top">Id for the object found.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">String</td>
* </tr>
* <tr>
* <td valign="top">refid</td>
* <td valign="top">Id for the object found.</td>
* <td valign="top" align="center">No</td>
* <td valign="top">Search in all windows</td>
* <td valign="top">Panel to be searched</td>
* </tr>
* <tr>
* <td valign="top">index</td>
* <td valign="top">The index of the element to select from the combo box.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">N/A</td>
* <td valign="top">Zero based index of list items.</td>
* </tr>
* <tr>
* <td valign="top">label</td>
* <td valign="top">The text of the label to be found.</td>
* <td valign="top" align="center">Yes</td>
* <td valign="top">None</td>
* <td valign="top">Regular expression defining the label.</td>
* </tr>
* <tr>
* <td valign="top">caseindependent</td>
* <td valign="top">Ignore the case if true</td>
* <td valign="top" align="center">No</td>
* <td valign="top">false</td>
* <td valign="top">true/false</td>
* </tr>
* <tr>
* <td valign="top">waitForDisabled</td>
* <td valign="top">Blocks the flow until the label is disabled
* But not longer then the time given. WATCH this:
* If the JLabel is not disabled after the time
* you gave as attribute value the reference to the
* JLabel will be null ("id").</td>
* <td valign="top" align="center">No</td>
* <td valign="top">10000</td>
* <td valign="top">long value in milliseconds</td>
* </tr>
* <tr>
* <td valign="top">waitForEnabled</td>
* <td valign="top">Blocks the flow until the label is enabled
* But not longer then the time given. WATCH this:
* If the JLabel is not enabled after the time
* you gave as attribute value the reference to the
* JLabel will be null ("id").</td>
* <td valign="top" align="center">No</td>
* <td valign="top">10000</td>
* <td valign="top">long value in milliseconds</td>
* </tr>
* </table>
* <h3>Example</h3>
* <blockquote><pre>
* <find
* finder="JLabelFinder"
* id="MyLabel"
* label="^My label$"
* index="0"
* />
* </pre></blockquote>
* <p>
* The above finds the first label with
* a text "My label"
* </p>
* <h3>Example</h3>
* <blockquote><pre>
* <find
* finder="JLabelFinder"
* id="MyLabel"
* label="^My label$"
* index="0"
* waitForEnabled="5000"
* />
* </pre></blockquote>
* <p>
* The above finds the first label with
* a text "My label". If the JLabel is enabled
* the programm flow is not blocked. If the label is not
* enabled the programm flow is blocked but only up to 5 seconds.
* </p>
* @see junit.extensions.jfcunit.finder.JLabelFinder
* @author Kevin Wilson
* @author <a href="mailto:vraravam@thoughtworks.com">Vijay Aravamudhan : ThoughtWorks Inc.</a>
* @author tom@smart-tail.com (Tom Wiedenhoeft, DV-Ratio acting under contract with Siemens L&A PA)
*/
public class JLabelFinderTagHandler extends BaseFindTagHandler {
/**
* Constructor for FindTagHandler.
*
* @param element The element to be processed
* @param testCase The IXMLTestCase that uses this element
*/
public JLabelFinderTagHandler(final Element element,
final IXMLTestCase testCase) {
super(element, testCase);
}
/**
* Get the value of the waitForEnabled attribute.
* @return String value of the waitForEnabled attribute.
*/
public String getWaitForEnabled() {
return getString(WAIT_FOR_ENABLED);
}
/**
* Get the value of the waitForDisabled attribute.
* @return String value of the waitForDisabled attribute.
*/
public String getWaitForDisabled() {
return getString(WAIT_FOR_DISABLED);
}
/**
* @see junit.extensions.xml.elements.AbstractTagHandler#processElement()
*/
public void processElement() throws XMLException {
validateElement();
String label = getLabel();
boolean caseIndependent = getCaseIndependent();
find(new JLabelFinder(label, caseIndependent));
this.waitForEnablingDisabling();
}
/**
* @see junit.extensions.xml.elements.AbstractTagHandler#validateElement()
*/
public void validateElement() throws XMLException {
// do the default validations from the super class
super.validateElement();
// reqd attribute: label
checkRequiredAttribute(LABEL);
String timeEnabled = this.getWaitForEnabled();
String timeDisabled = this.getWaitForDisabled();
if(timeEnabled != null && timeDisabled != null)
{
throw new XMLException(
"Its not allowed to give both attributes "
+ WAIT_FOR_ENABLED + " and " + WAIT_FOR_DISABLED + ".",
null,
getElement(),
getTest().getPropertyCache());
}
}
/**
* Blocks the flow if the attibutes waitForDisabled or
* waitForEnabled are given.
*/
private void waitForEnablingDisabling()
{
// Was the component found?
String id = this.getString(ID);
Object o = getXMLTestCase().getProperty(id);
if(o == null)
{
// The component was not found. Do not block any longer.
return;
}
long startTime = System.currentTimeMillis();
JLabel jLabel = (JLabel) o;
String timeEnabled = this.getWaitForEnabled();
String timeDisabled = this.getWaitForDisabled();
if(timeEnabled != null)
{
if("".equals(timeEnabled))
{
timeEnabled = "10000";
}
long blockTime = 0;
try {
blockTime = Long.parseLong(timeEnabled);
} catch(NumberFormatException e) {
throw new XMLException(
"Failed to parse attribute value for "
+ WAIT_FOR_ENABLED + ". Must be long value.",
e,
getElement(),
getTest().getPropertyCache());
}
while(! jLabel.isEnabled())
{
long lapTime = System.currentTimeMillis() - startTime;
if(lapTime < blockTime)
{
continue;
}
else
{
// The JLabel is still not enabled. Set the property to null.
getXMLTestCase().addProperty(id, null);
return;
}
}
}
else if(timeDisabled != null)
{
if("".equals(timeDisabled))
{
timeDisabled = "10000";
}
long blockTime = 0;
try {
blockTime = Long.parseLong(timeDisabled);
} catch(NumberFormatException e) {
throw new XMLException(
"Failed to parse attribute value for "
+ WAIT_FOR_DISABLED + ". Must be long value.",
e,
getElement(),
getTest().getPropertyCache());
}
while(jLabel.isEnabled())
{
long lapTime = System.currentTimeMillis() - startTime;
if(lapTime < blockTime)
{
continue;
}
else
{
// The JLabel is still not enabled. Set the property to null.
getXMLTestCase().addProperty(id, null);
return;
}
}
}
}
}
---schnapp -- JLabelFinderTagHandler.java ---
Please add in XMLConstants.java
---schnipp -- XMLConstants.java ---
/** waitForEnabled */
String WAIT_FOR_ENABLED = "waitForEnabled";
/** waitForDisabled */
String WAIT_FOR_DISABLED = "waitForDisabled";
---schnapp -- XMLConstants.java ---
By the way, we implemented all tests with XML files (no tests in java source). At the beginning we where not decided. But the TagHandlers provide sufficient program flow for us.
Good Idea, a RFE would be a great place to log such issues. Then the request will not get lost in the forums.
Yes, I will do it next week.
Tom