Archive for March, 2007

Webcast: Qt Application Testing Made Easy

Thursday, March 8th, 2007

Together with our partner Trolltech we will conduct a webcast where we will show how to use Squish to create and run automated tests on Qt applications. This is a real live webcast where you will be able to ask questions, etc.

Also we will run a special license price offer for webcast attendees.

So if you are considering to use Squish for Qt register now and take advantage of this opportunity: http://www.trolltech.com/campaign/squishwebcasts

C++ Prototype Wrapper

Tuesday, March 6th, 2007

Imagine this: You have an existing class hierarchy, for instance a ‘Node’ class from which ‘StringNode’, ‘NumberNode’ and ‘BooleanNode’ classes derive. Now, you want to implement a nicely generic and easily extensible way to create an object of one of the three concrete classes depending on a value (for instance, a string) you get. How to do this nicely in C++?

I had a problem like this, and a core part of the problem is that the existing class hierarchy had nothing like a ‘clone()’ function or so (a ‘virtual constructor’ for the cool kids on the block). I solved this by writing a generic prototype template class:

class NodePrototypeWrapper
{
public:
    virtual Node *clone() const = 0;
};  

template <class Product>
class GenericNodePrototypeWrapper : public NodePrototypeWrapper
{
public:
    virtual Node *clone() const {
        return new Product( 0 );
    }
};  

class NodeFactory
{
public:
    static NodeFactory &self() {
        if ( !s_instance ) {
            s_instance = new NodeFactory;
        }
        return *s_instance;
    }  

    ~NodeFactory() {
        QMap<QString, NodePrototypeWrapper *>::Iterator it, end = m_prototypes.end();
        for ( it = m_prototypes.begin(); it != end; ++it ) {
            delete *it;
        }
    }  

    QStringList availableNodes() const { return m_prototypes.keys(); }  

    Node *createNode( const QString &name ) const {
        return m_prototypes[ name ]->clone();
    }  

    template <class NodeType>
    void registerNodeType() {
        m_prototypes[ NodeType( 0 ).descriptiveName() ] = new GenericNodePrototypeWrapper<NodeType>;
    }  

private:
    NodeFactory() {}
    NodeFactory( const NodeFactory &rhs ); // disabled
    NodeFactory &operator=( const NodeFactory &rhs ); // disabled
    static NodeFactory *s_instance;  

    QMap<QString, NodePrototypeWrapper *> m_prototypes;
};

So what I can do now is e.g.:

NodeFactory::self().registerNodeType<StringNode>();
NodeFactory::self().registerNodeType<NumberNode>();
NodeFactory::self().registerNodeType<BooleanNode>();

This would probably make a nice macro, too. REGISTER_NODE_TYPE or so. Anyway, lateron I can create nodes using

Node *n = NodeFactory::self().createNode( someString );

In my particular case, I’m using the availableNodes() function of the NodeFactory to get a list of strings which I can show in the GUI, so that the user can select some node to create. I then pass the same string to the createNode() function and voila, it works nicely!

In this trivial example a simple ‘if..else’ might have been easier (but even then, you would have to maintain the code which builds the GUI menu for selecting what node to create, too!) but in my case I have a few dozen node types, and this little trick makes things much easier. :-)

Pain with browser compatibility

Monday, March 5th, 2007

One improvement in Squish for Web 3.2 is the Spy object picker and screenshot comparisons. One issue common to both features is to find out the absolute (to the screen) position and size of a given DOM element. This is necessary to draw a highlighting rectangle around the element (for the object picker) and to take a screenshot of a specific element.

Of course there is no cross-browser way to do this calculation. That’s why in Squish/Web versions prior to 3.1 the object picker used a bad hack to highlight elements (changing its background color) and screenshots could only be taken from the whole browser window.

For Squish for Web 3.2 we finally implemented the necessary function to calculate the DOM element’s coordinates. But it really was a pain. There is no API which you can reliably use. It works differently in all browsers (I wasn’t too surprised by that). But also the used DOM APIs returned behaved differently in Firefox depending on the platform.

So our getElementRect() function really does a lot of checking and magic but finally it works for all browsers. So in Squish 3.2 the object picker will be much more useful (since we also display the name of the object when you hover over it now, as we always did in other Squish editions already) and screenshots can be used now for real.

I’d just wish that the browsers wouldn’t be so different. But I guess many share my pain with this :-)

Clever Web Object Identification

Friday, March 2nd, 2007

As Reginald previously mentioned Squish 3.2 is going to have an even more sophisticated technique for identifying objects based on some properties. This is achieved by allowing to determine whether a given object matches a given property value not only through a plain string comparison but by also testing whether the object matches a certain regular expression or wildcard-enhanced string.

I just finished implementing a first version of the same powerful magic for Web tests and so far (keeping fingers crossed) it seems to work well without introducing any regressions. Using regular expressions and/or wildcards when patching property values is especially useful for Web tests, since many Web applications happen to encode some more or less random session ID into important attributes. (more…)

Problems e-mailing us?

Thursday, March 1st, 2007

A customer has reported repeated bounces when sending mail to our support address. Unfortunately we could neither find anything in our server logs nor from the SMTP error message.

So if anyone else is experiencing problems too please drop us a mail at admin@froglogic.com or (as this might one might not work for you either) just paste the error message you got as a comment below. Will try to find a common pattern behind this.

Thank you.