Example #1
0
    def setUp(self, plugin_module):
        """Subclasses should call this in their setUp() methods.

        The plugin_module arg is the plugin module being tested. This
        is used to set the plugin_dir config variable.
        """
        # freeze time
        self.timestamp = TIMESTAMP
        self.frozen_time = self.freeze_pyblosxom_time(self.timestamp)
        self.timestamp_asc = time.ctime(self.timestamp)
        gmtime = time.gmtime(self.timestamp)
        self.timestamp_date = time.strftime('%a %d %b %Y', gmtime)
        self.timestamp_w3c = time.strftime('%Y-%m-%dT%H:%M:%SZ', gmtime)

        # set up config, including datadir and plugin_dirs
        self.datadir = tempfile.mkdtemp(prefix='pyblosxom_test_datadir')

        plugin_file = os.path.dirname(plugin_module.__file__)
        self.config_base = {
            'datadir': self.datadir,
            'plugin_dirs': [plugin_file],
            'base_url': 'http://bl.og/',
        }
        self.config = self.config_base
        tools.initialize(self.config)

        # set up environment vars and http request
        self.environ = {'PATH_INFO': '/', 'REMOTE_ADDR': ''}
        self.form_data = ''
        self.request = pyblosxom.Request(self.config, self.environ, {})
        self.http = self.request.get_http()

        # set up entries and data dict
        self.entry_name = 'test_entry'
        entry_properties = {'absolute_path': '.', 'fn': self.entry_name}
        self.entry = entries.base.generate_entry(self.request,
                                                 entry_properties, {}, gmtime)
        self.entry_list = [self.entry]
        self.data = {
            'entry_list': self.entry_list,
            'bl_type': 'file',
        }
        self.request._data = self.data

        # set up renderer and templates
        self.renderer = Renderer(self.request)
        self.renderer.set_content(self.entry_list)
        templates = ('content_type', 'head', 'story', 'foot', 'date_head',
                     'date_foot')
        self.renderer.flavour = dict([(t, t) for t in templates])

        # populate args dict
        self.args = {
            'request': self.request,
            'renderer': self.renderer,
            'entry': self.entry,
            'template': 'template starts:',
        }

        # this stores the callbacks that have been injected. it maps
        # callback names to the injected methods to call. any
        # callbacks that haven't been injected are passed through to
        # pyblosxom's callback chain.
        #
        # use inject_callback() to inject a callback.
        self.injected_callbacks = {}
        orig_run_callback = tools.run_callback

        def intercept_callback(name, args, **kwargs):
            if name in self.injected_callbacks:
                return self.injected_callbacks[name]()
            else:
                return orig_run_callback(name, args, **kwargs)

        tools.run_callback = intercept_callback
Example #2
0
    def setUp(self, plugin_module):
        """Subclasses should call this in their setUp() methods.

        The plugin_module arg is the plugin module being tested. This
        is used to set the plugin_dir config variable.
        """
        # freeze time
        self.timestamp = TIMESTAMP
        self.frozen_time = self.freeze_pyblosxom_time(self.timestamp)
        self.timestamp_asc = time.ctime(self.timestamp)
        gmtime = time.gmtime(self.timestamp)
        self.timestamp_date = time.strftime('%a %d %b %Y', gmtime)
        self.timestamp_w3c = time.strftime('%Y-%m-%dT%H:%M:%SZ', gmtime)

        # set up config, including datadir and plugin_dirs
        self.datadir = tempfile.mkdtemp(prefix='pyblosxom_test_datadir')

        plugin_file = os.path.dirname(plugin_module.__file__)
        self.config_base = {'datadir': self.datadir,
                            'plugin_dirs': [plugin_file],
                            'base_url': 'http://bl.og/',
                            }
        self.config = self.config_base
        tools.initialize(self.config)

        # set up environment vars and http request
        self.environ = {'PATH_INFO': '/', 'REMOTE_ADDR': ''}
        self.form_data = ''
        self.request = pyblosxom.Request(self.config, self.environ, {})
        self.http = self.request.get_http()

        # set up entries and data dict
        self.entry_name = 'test_entry'
        entry_properties = {'absolute_path': '.',
                            'fn': self.entry_name}
        self.entry = entries.base.generate_entry(
            self.request, entry_properties, {}, gmtime)
        self.entry_list = [self.entry]
        self.data = {'entry_list': self.entry_list,
                     'bl_type': 'file',
                     }
        self.request._data = self.data

        # set up renderer and templates
        self.renderer = Renderer(self.request)
        self.renderer.set_content(self.entry_list)
        templates = ('content_type', 'head', 'story', 'foot', 'date_head',
                     'date_foot')
        self.renderer.flavour = dict([(t, t) for t in templates])

        # populate args dict
        self.args = {'request': self.request,
                     'renderer': self.renderer,
                     'entry': self.entry,
                     'template': 'template starts:',
                     }

        # this stores the callbacks that have been injected. it maps
        # callback names to the injected methods to call. any
        # callbacks that haven't been injected are passed through to
        # pyblosxom's callback chain.
        #
        # use inject_callback() to inject a callback.
        self.injected_callbacks = {}
        orig_run_callback = tools.run_callback

        def intercept_callback(name, args, **kwargs):
            if name in self.injected_callbacks:
                return self.injected_callbacks[name]()
            else:
                return orig_run_callback(name, args, **kwargs)

        tools.run_callback = intercept_callback
Example #3
0
class PluginTest(unittest.TestCase):
    """Base class for plugin unit tests. Subclass this to test
    plugins.

    Many common PyBlosxom data structures are populated as attributes
    of this class, including self.environ, self.config, self.data,
    self.request, and self.args.

    By default, self.request is configured as a request for a single
    entry; its name is stored in self.entry_name. This can be
    overridden by modifying the attributes above in your test's
    setUp() method. The entry's timestamp, as seconds since the epoch,
    is stored in self.timestamp. String representations in
    self.timestamp_str and self.timestamp_w3c.

    You can change any of the data structures by modifying them
    directly in your tests or your subclass's setUp() method.

    The datadir is set to a unique temporary directory in /tmp. This
    directory is created fresh for each test, and deleted when the
    test is done.

    NOTE(ryanbarrett): Creating and deleting multiple files and
    directories for each test is inefficient. If this becomes a
    bottleneck, it might need to be reconsidered.
    """
    def setUp(self, plugin_module):
        """Subclasses should call this in their setUp() methods.

        The plugin_module arg is the plugin module being tested. This
        is used to set the plugin_dir config variable.
        """
        # freeze time
        self.timestamp = TIMESTAMP
        self.frozen_time = self.freeze_pyblosxom_time(self.timestamp)
        self.timestamp_asc = time.ctime(self.timestamp)
        gmtime = time.gmtime(self.timestamp)
        self.timestamp_date = time.strftime('%a %d %b %Y', gmtime)
        self.timestamp_w3c = time.strftime('%Y-%m-%dT%H:%M:%SZ', gmtime)

        # set up config, including datadir and plugin_dirs
        self.datadir = tempfile.mkdtemp(prefix='pyblosxom_test_datadir')

        plugin_file = os.path.dirname(plugin_module.__file__)
        self.config_base = {
            'datadir': self.datadir,
            'plugin_dirs': [plugin_file],
            'base_url': 'http://bl.og/',
        }
        self.config = self.config_base
        tools.initialize(self.config)

        # set up environment vars and http request
        self.environ = {'PATH_INFO': '/', 'REMOTE_ADDR': ''}
        self.form_data = ''
        self.request = pyblosxom.Request(self.config, self.environ, {})
        self.http = self.request.get_http()

        # set up entries and data dict
        self.entry_name = 'test_entry'
        entry_properties = {'absolute_path': '.', 'fn': self.entry_name}
        self.entry = entries.base.generate_entry(self.request,
                                                 entry_properties, {}, gmtime)
        self.entry_list = [self.entry]
        self.data = {
            'entry_list': self.entry_list,
            'bl_type': 'file',
        }
        self.request._data = self.data

        # set up renderer and templates
        self.renderer = Renderer(self.request)
        self.renderer.set_content(self.entry_list)
        templates = ('content_type', 'head', 'story', 'foot', 'date_head',
                     'date_foot')
        self.renderer.flavour = dict([(t, t) for t in templates])

        # populate args dict
        self.args = {
            'request': self.request,
            'renderer': self.renderer,
            'entry': self.entry,
            'template': 'template starts:',
        }

        # this stores the callbacks that have been injected. it maps
        # callback names to the injected methods to call. any
        # callbacks that haven't been injected are passed through to
        # pyblosxom's callback chain.
        #
        # use inject_callback() to inject a callback.
        self.injected_callbacks = {}
        orig_run_callback = tools.run_callback

        def intercept_callback(name, args, **kwargs):
            if name in self.injected_callbacks:
                return self.injected_callbacks[name]()
            else:
                return orig_run_callback(name, args, **kwargs)

        tools.run_callback = intercept_callback

    def tearDown(self):
        """Subclasses should call this in their tearDown() methods."""
        self.delete_datadir()

    def delete_datadir(self):
        """Deletes the datadir and its contents."""
        self.remove_dir(self.datadir)

    def freeze_pyblosxom_time(self, timestamp):
        """Injects a frozen time module into PyBlosxom.

        The timestamp argument should be seconds since the epoch. Returns the
        FrozenTime instance.
        """
        assert isinstance(timestamp, (int, float))
        frozen_time = FrozenTime(timestamp)
        pyblosxom.time = frozen_time
        tools.time = frozen_time
        return frozen_time

    def add_form_data(self, args):
        """Adds the given argument names and values to the request's form data.

        The argument names and values are URL-encoded and escaped before
        populating them in the request. This method also sets the request
        method to POST.
        """
        self.environ['REQUEST_METHOD'] = 'POST'
        self.request.add_http({'REQUEST_METHOD': 'POST'})

        encoded = [
            '%s=%s' % (arg, urllib.quote(val)) for arg, val in args.items()
        ]
        self.form_data += ('&' + '&'.join(encoded))
        input_ = cStringIO.StringIO(self.form_data)
        self.request._form = cgi.FieldStorage(fp=input_, environ=self.environ)

    def set_form_data(self, args):
        """Clears the request's form data, then adds the given
        arguments.
        """
        self.form_data = ''
        self.add_form_data(args)

    def inject_callback(self, name, callback):
        """Injects a callback to be run by tools.run_callback().

        The callback is run *instead* of Pyblosxom's standard callback
        chain.
        """
        self.injected_callbacks[name] = callback

    def remove_dir(self, dir):
        """Recursively removes a directory and all files and
        subdirectories.

        If dir doesn't exist or is not a directory, does nothing.
        """
        shutil.rmtree(self.datadir, ignore_errors=True)

    # allows us to use shorthand
    eq_ = unittest.TestCase.assertEquals
Example #4
0
class PluginTest(unittest.TestCase):
    """Base class for plugin unit tests. Subclass this to test
    plugins.

    Many common Pyblosxom data structures are populated as attributes
    of this class, including self.environ, self.config, self.data,
    self.request, and self.args.

    By default, self.request is configured as a request for a single
    entry; its name is stored in self.entry_name. This can be
    overridden by modifying the attributes above in your test's
    setUp() method. The entry's timestamp, as seconds since the epoch,
    is stored in self.timestamp. String representations in
    self.timestamp_str and self.timestamp_w3c.

    You can change any of the data structures by modifying them
    directly in your tests or your subclass's setUp() method.

    The datadir is set to a unique temporary directory in /tmp. This
    directory is created fresh for each test, and deleted when the
    test is done.

    NOTE(ryanbarrett): Creating and deleting multiple files and
    directories for each test is inefficient. If this becomes a
    bottleneck, it might need to be reconsidered.
    """

    def setUp(self, plugin_module):
        """Subclasses should call this in their setUp() methods.

        The plugin_module arg is the plugin module being tested. This
        is used to set the plugin_dir config variable.
        """
        # freeze time
        self.timestamp = TIMESTAMP
        self.frozen_time = self.freeze_pyblosxom_time(self.timestamp)
        self.timestamp_asc = time.ctime(self.timestamp)
        gmtime = time.gmtime(self.timestamp)
        self.timestamp_date = time.strftime('%a %d %b %Y', gmtime)
        self.timestamp_w3c = time.strftime('%Y-%m-%dT%H:%M:%SZ', gmtime)

        # set up config, including datadir and plugin_dirs
        self.datadir = tempfile.mkdtemp(prefix='pyblosxom_test_datadir')

        plugin_file = os.path.dirname(plugin_module.__file__)
        self.config_base = {'datadir': self.datadir,
                            'plugin_dirs': [plugin_file],
                            'base_url': 'http://bl.og/',
                            }
        self.config = self.config_base
        tools.initialize(self.config)

        # set up environment vars and http request
        self.environ = {'PATH_INFO': '/', 'REMOTE_ADDR': ''}
        self.form_data = ''
        self.request = pyblosxom.Request(self.config, self.environ, {})
        self.http = self.request.get_http()

        # set up entries and data dict
        self.entry_name = 'test_entry'
        entry_properties = {'absolute_path': '.',
                            'fn': self.entry_name}
        self.entry = entries.base.generate_entry(
            self.request, entry_properties, {}, gmtime)
        self.entry_list = [self.entry]
        self.data = {'entry_list': self.entry_list,
                     'bl_type': 'file',
                     }
        self.request._data = self.data

        # set up renderer and templates
        self.renderer = Renderer(self.request)
        self.renderer.set_content(self.entry_list)
        templates = ('content_type', 'head', 'story', 'foot', 'date_head',
                     'date_foot')
        self.renderer.flavour = dict([(t, t) for t in templates])

        # populate args dict
        self.args = {'request': self.request,
                     'renderer': self.renderer,
                     'entry': self.entry,
                     'template': 'template starts:',
                     }

        # this stores the callbacks that have been injected. it maps
        # callback names to the injected methods to call. any
        # callbacks that haven't been injected are passed through to
        # pyblosxom's callback chain.
        #
        # use inject_callback() to inject a callback.
        self.injected_callbacks = {}
        orig_run_callback = tools.run_callback

        def intercept_callback(name, args, **kwargs):
            if name in self.injected_callbacks:
                return self.injected_callbacks[name]()
            else:
                return orig_run_callback(name, args, **kwargs)

        tools.run_callback = intercept_callback

    def tearDown(self):
        """Subclasses should call this in their tearDown() methods."""
        self.delete_datadir()

    def delete_datadir(self):
        """Deletes the datadir and its contents."""
        self.remove_dir(self.datadir)

    def freeze_pyblosxom_time(self, timestamp):
        """Injects a frozen time module into Pyblosxom.

        The timestamp argument should be seconds since the epoch. Returns the
        FrozenTime instance.
        """
        assert isinstance(timestamp, (int, float))
        frozen_time = FrozenTime(timestamp)
        pyblosxom.time = frozen_time
        tools.time = frozen_time
        return frozen_time

    def add_form_data(self, args):
        """Adds the given argument names and values to the request's form data.

        The argument names and values are URL-encoded and escaped before
        populating them in the request. This method also sets the request
        method to POST.
        """
        self.environ['REQUEST_METHOD'] = 'POST'
        self.request.add_http({'REQUEST_METHOD': 'POST'})

        encoded = ['%s=%s' % (arg, urllib.quote(val))
                   for arg, val in args.items()]
        self.form_data += ('&' + '&'.join(encoded))
        input_ = StringIO.StringIO(self.form_data)
        self.request._form = cgi.FieldStorage(fp=input_, environ=self.environ)

    def set_form_data(self, args):
        """Clears the request's form data, then adds the given
        arguments.
        """
        self.form_data = ''
        self.add_form_data(args)

    def inject_callback(self, name, callback):
        """Injects a callback to be run by tools.run_callback().

        The callback is run *instead* of Pyblosxom's standard callback
        chain.
        """
        self.injected_callbacks[name] = callback

    def remove_dir(self, dir):
        """Recursively removes a directory and all files and
        subdirectories.

        If dir doesn't exist or is not a directory, does nothing.
        """
        shutil.rmtree(self.datadir, ignore_errors=True)

    # allows us to use shorthand
    eq_ = unittest.TestCase.assertEquals