{ "metadata": { "name": "", "signature": "sha256:1848ceaccc070baee397b0e7033b8d773e76fd7f5aacdedf442309a9cb5e6cba" }, "nbformat": 3, "nbformat_minor": 0, "worksheets": [ { "cells": [ { "cell_type": "heading", "level": 1, "metadata": {}, "source": [ "robotframework-tools" ] }, { "cell_type": "code", "collapsed": false, "input": [ "import robottools\n", "print(robottools.__version__)" ], "language": "python", "metadata": {}, "outputs": [ { "output_type": "stream", "stream": "stdout", "text": [ "0.1a111\n" ] } ], "prompt_number": 1 }, { "cell_type": "code", "collapsed": false, "input": [ "print(robottools.__description__)" ], "language": "python", "metadata": {}, "outputs": [ { "output_type": "stream", "stream": "stdout", "text": [ "Python Tools for Robot Framework and Test Libraries.\n" ] } ], "prompt_number": 2 }, { "cell_type": "markdown", "metadata": {}, "source": [ "* `testlibrary()` [creates Dynamic Test Libraries][1]\n", "* A [`ContextHandler`][1.1] framework for `testlibrary`\n", " to create switchable sets of different Keyword implementations.\n", "* A [`SessionHandler`][1.2] framework for `testlibrary`\n", " to auto-generate Keywords for session management.\n", "* A [`TestLibraryInspector`][2].\n", "* A [`RemoteRobot`][4], combining `TestRobot`\n", " with external [`RobotRemoteServer`](\n", " https://pypi.python.org/pypi/robotremoteserver)\n", "* A [`ToolsLibrary`][5],\n", " accompanying Robot Framework's standard Test Libraries.\n", "* A [`robotshell`][6] extension for [IPython](http://ipython.org).\n", "\n", "[1]: #1.-Creating-Dynamic-Test-Libraries" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "<https://bitbucket.org/userzimmermann/robotframework-tools>\n", "\n", "<https://github.com/userzimmermann/robotframework-tools>" ] }, { "cell_type": "heading", "level": 1, "metadata": {}, "source": [ "0. Setup" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "__Supported Python versions__:\n", "[2.7](http://docs.python.org/2.7),\n", "[3.3](http://docs.python.org/3.3),\n", "[3.4](http://docs.python.org/3.4)\n", "\n", "Just install the latest release\n", "from [PyPI](https://pypi.python.org/pypi/robotframework-tools)\n", "with [pip](http://www.pip-installer.org):" ] }, { "cell_type": "code", "collapsed": false, "input": [ "# !pip install robotframework-tools" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 3 }, { "cell_type": "markdown", "metadata": {}, "source": [ "or from [Binstar](https://binstar.org/userzimmermann/robotframework-tools)\n", "with [conda](http://conda.pydata.org):" ] }, { "cell_type": "code", "collapsed": false, "input": [ "# !conda install -c userzimmermann robotframework-tools" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 4 }, { "cell_type": "markdown", "metadata": {}, "source": [ "Both automatically install requirements:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "robottools.__requires__" ], "language": "python", "metadata": {}, "outputs": [ { "metadata": {}, "output_type": "pyout", "prompt_number": 5, "text": [ "six\n", "path.py\n", "moretools>=0.1a38" ] } ], "prompt_number": 5 }, { "cell_type": "markdown", "metadata": {}, "source": [ "* __Python 2.7__: `robotframework>=2.8`\n", "\n", "* __Python 3.x__: `robotframework-python3>=2.8.4`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "`RemoteRobot` and `robotshell` have extra requirements:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "robottools.__extras__" ], "language": "python", "metadata": {}, "outputs": [ { "metadata": {}, "output_type": "pyout", "prompt_number": 6, "text": [ "[remote]\n", "robotremoteserver\n", "\n", "[robotshell]\n", "ipython" ] } ], "prompt_number": 6 }, { "cell_type": "markdown", "metadata": {}, "source": [ "Pip doesn't install them by default.\n", "Just append any comma separated extra tags in `[]` brackets to the package name.\n", "To install with all extra requirements:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "# !pip install robotframework-tools[all]" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 7 }, { "cell_type": "markdown", "metadata": {}, "source": [ "This `README.ipynb` will also be installed. Just copy it:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "# robottools.__notebook__.copy('path/name.ipynb')" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 8 }, { "cell_type": "heading", "level": 1, "metadata": {}, "source": [ "1. Creating Dynamic Test Libraries" ] }, { "cell_type": "code", "collapsed": false, "input": [ "from robottools import testlibrary" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 9 }, { "cell_type": "code", "collapsed": false, "input": [ "TestLibrary = testlibrary()" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 10 }, { "cell_type": "markdown", "metadata": {}, "source": [ "This generated Dynamic `TestLibrary` class\n", "could now directly be imported in Robot Framework.\n", "It features all the Dynamic API methods:\n", "\n", "* `get_keyword_names`\n", "* `get_keyword_arguments`\n", "* `get_keyword_documentation`\n", "* `run_keyword`" ] }, { "cell_type": "heading", "level": 3, "metadata": {}, "source": [ "Keywords" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The `TestLibrary` has no Keywords so far...\n", "To add some just use the `TestLibrary.keyword` decorator:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "@TestLibrary.keyword\n", "def some_keyword(self, arg, *rest):\n", " pass" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 11 }, { "cell_type": "markdown", "metadata": {}, "source": [ "A keyword function can be defined anywhere in any scope.\n", "The `TestLibrary.keyword` decorator\n", "always links it to the `TestLibrary`\n", "(but always returns the original function object).\n", "And when called as a Keyword from Robot Framework\n", "the `self` parameter will always get the `TestLibrary` instance." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "You may want to define your keyword methods\n", "at your Test Library class scope.\n", "Just derive your actual Dynamic Test Library class from `TestLibrary`:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "class SomeLibrary(TestLibrary):\n", " def no_keyword(self, *args):\n", " pass\n", "\n", " @TestLibrary.keyword\n", " def some_other_keyword(self, *args):\n", " pass" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 12 }, { "cell_type": "markdown", "metadata": {}, "source": [ "To get a simple interactive `SomeLibrary` overview just instantiate it:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "lib = SomeLibrary()" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 13 }, { "cell_type": "markdown", "metadata": {}, "source": [ "You can inspect all Keywords in Robot CamelCase style\n", "(and call them for testing):" ] }, { "cell_type": "code", "collapsed": false, "input": [ "lib.SomeKeyword" ], "language": "python", "metadata": {}, "outputs": [ { "metadata": {}, "output_type": "pyout", "prompt_number": 14, "text": [ "SomeLibrary.Some Keyword [ arg | *rest ]" ] } ], "prompt_number": 14 }, { "cell_type": "markdown", "metadata": {}, "source": [ "By default the Keyword names and argument lists are auto-generated\n", "from the function definition.\n", "You can override that:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "@TestLibrary.keyword(name='KEYword N@me', args=['f|r$t', 'se[ond'])\n", "def function(self, *args):\n", " pass" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 15 }, { "cell_type": "heading", "level": 3, "metadata": {}, "source": [ "Keyword Options" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "When you apply custom decorators to your Keyword functions\n", "which don't return the original function objects,\n", "you would have to take care of preserving the original argspec for Robot.\n", "`testlibrary` can handle this for you:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "def some_decorator(func):\n", " def wrapper(self, *args):\n", " return func(self, *args)\n", "\n", " # You still have to take care of the function(-->Keyword) name:\n", " wrapper.__name__ = func.__name__\n", " return wrapper\n", "\n", "TestLibrary = testlibrary(\n", " register_keyword_options=[\n", " # Either just:\n", " some_decorator,\n", " # Or with some other name:\n", " ('some_option', some_decorator),\n", " ],\n", " )\n", "\n", "@TestLibrary.keyword.some_option\n", "def some_keyword_with_options(self, arg, *rest):\n", " pass" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 16 }, { "cell_type": "markdown", "metadata": {}, "source": [ "There are predefined options. Currently:\n", "\n", "* `unicode_to_str` - Convert all `unicode` values (pybot's default) to `str`." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "You can specify `default_keyword_options` that will always be applied:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "TestLibrary = testlibrary(\n", " register_keyword_options=[\n", " ('some_option', some_decorator),\n", " ],\n", " default_keyword_options=[\n", " 'unicode_to_str',\n", " 'some_option',\n", " ],\n", " )" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 17 }, { "cell_type": "markdown", "metadata": {}, "source": [ "To bypass the `default_keyword_options` for single Keywords:" ] }, { "cell_type": "code", "collapsed": false, "input": [ "@TestLibrary.keyword.no_options\n", "def some_keyword_without_options(self, arg, *rest):\n", " pass\n", "\n", "@TestLibrary.keyword.reset_options.some_option\n", "def some_keyword_without_default_options(self, arg, *rest):\n", " pass" ], "language": "python", "metadata": {}, "outputs": [], "prompt_number": 18 } ], "metadata": {} } ] }