diff options
author | Tim Burke <tim.burke@gmail.com> | 2016-07-20 14:13:16 -0700 |
---|---|---|
committer | Tim Burke <tim.burke@gmail.com> | 2016-07-20 14:13:16 -0700 |
commit | a2a041b7da2850c82df195ab36450a8aee8129b5 (patch) | |
tree | 41b854b02229a9cc3d6830a6221f778bc16d0a53 /tests | |
download | pastedeploy-git-a2a041b7da2850c82df195ab36450a8aee8129b5.tar.gz |
Fix string-formatting args when raising LookupError
Previously, this would trigger
TypeError: not enough arguments for format string
Diffstat (limited to 'tests')
23 files changed, 631 insertions, 0 deletions
diff --git a/tests/__init__.py b/tests/__init__.py new file mode 100644 index 0000000..cffe526 --- /dev/null +++ b/tests/__init__.py @@ -0,0 +1,13 @@ +import os +import sys + +here = os.path.dirname(__file__) +base = os.path.dirname(here) +sys.path.insert(0, base) + +# We can only import this after we adjust the paths +import pkg_resources + +# Make absolutely sure we're testing *this* package, not +# some other installed package +pkg_resources.require('PasteDeploy') diff --git a/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/PKG-INFO b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/PKG-INFO new file mode 100644 index 0000000..a2a1137 --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/PKG-INFO @@ -0,0 +1,10 @@ +Metadata-Version: 1.0 +Name: FakeApp +Version: 1.0 +Summary: UNKNOWN +Home-page: UNKNOWN +Author: UNKNOWN +Author-email: UNKNOWN +License: UNKNOWN +Description: UNKNOWN +Platform: UNKNOWN diff --git a/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/entry_points.txt b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/entry_points.txt new file mode 100644 index 0000000..9bfc986 --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/entry_points.txt @@ -0,0 +1,22 @@ +[paste.app_factory] + + basic_app=fakeapp.apps:make_basic_app + other=fakeapp.apps:make_basic_app2 + configed=fakeapp.configapps:SimpleApp.make_app + + +[paste.composit_factory] + + remote_addr=fakeapp.apps:make_remote_addr + + +[paste.filter_app_factory] + + caps2=fakeapp.apps:CapFilter + + +[paste.filter_factory] + + caps=fakeapp.apps:make_cap_filter + + diff --git a/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/top_level.txt b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/top_level.txt new file mode 100644 index 0000000..79ed67a --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/FakeApp.egg-info/top_level.txt @@ -0,0 +1 @@ +fakeapp diff --git a/tests/fake_packages/FakeApp.egg/fakeapp/__init__.py b/tests/fake_packages/FakeApp.egg/fakeapp/__init__.py new file mode 100644 index 0000000..792d600 --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/fakeapp/__init__.py @@ -0,0 +1 @@ +# diff --git a/tests/fake_packages/FakeApp.egg/fakeapp/apps.py b/tests/fake_packages/FakeApp.egg/fakeapp/apps.py new file mode 100644 index 0000000..cae7eba --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/fakeapp/apps.py @@ -0,0 +1,69 @@ +############################################################ +## Apps +############################################################ + +def simple_app(response, environ, start_response): + start_response('200 OK', [('Content-type', 'text/html')]) + return ['This is ', response] + +def basic_app(environ, start_response): + return simple_app('basic app', environ, start_response) + +def make_basic_app(global_conf, **conf): + return basic_app + +def basic_app2(environ, start_response): + return simple_app('basic app2', environ, start_response) + +def make_basic_app2(global_conf, **conf): + return basic_app2 + +############################################################ +## Composits +############################################################ + +def make_remote_addr(loader, global_conf, **conf): + apps = {} + addrs = {} + for name, value in conf.items(): + if name.startswith('app.'): + apps[name[4:]] = loader.get_app(value, global_conf) + elif name.startswith('addr.'): + addrs[name[5:]] = value + dispatcher = RemoteAddrDispatch() + for name in apps: + dispatcher.map[addrs[name]] = apps[name] + return dispatcher + +class RemoteAddrDispatch(object): + def __init__(self, map=None): + self.map = map or {} + + def __call__(self, environ, start_response): + addr = environ['REMOTE_ADDR'] + app = self.map.get(addr) or self.map['0.0.0.0'] + return app(environ, start_response) + +############################################################ +## Filters +############################################################ + +def make_cap_filter(global_conf, method_to_call='upper'): + def cap_filter(app): + return CapFilter(app, global_conf, method_to_call) + return cap_filter + +class CapFilter(object): + + def __init__(self, app, global_conf, method_to_call='upper'): + self.app = app + self.method_to_call = method_to_call + self.global_conf = global_conf + + def __call__(self, environ, start_response): + app_iter = self.app(environ, start_response) + for item in app_iter: + yield getattr(item, self.method_to_call)() + if hasattr(app_iter, 'close'): + app_iter.close() + diff --git a/tests/fake_packages/FakeApp.egg/fakeapp/configapps.py b/tests/fake_packages/FakeApp.egg/fakeapp/configapps.py new file mode 100644 index 0000000..ef13182 --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/fakeapp/configapps.py @@ -0,0 +1,14 @@ +class SimpleApp(object): + def __init__(self, global_conf, local_conf, name): + self.global_conf = global_conf + self.local_conf = local_conf + self.name = name + + def __call__(self, environ, start_response): + start_response('200 OK', [('Content-type', 'text/html')]) + return ['I am: ', name] + + def make_app(cls, global_conf, **conf): + return cls(global_conf, conf, 'basic') + make_app = classmethod(make_app) + diff --git a/tests/fake_packages/FakeApp.egg/setup.py b/tests/fake_packages/FakeApp.egg/setup.py new file mode 100644 index 0000000..854483e --- /dev/null +++ b/tests/fake_packages/FakeApp.egg/setup.py @@ -0,0 +1,23 @@ +from setuptools import setup, find_packages + +setup( + name="FakeApp", + version="1.0", + packages=find_packages(), + entry_points={ + 'paste.app_factory': """ + basic_app=fakeapp.apps:make_basic_app + other=fakeapp.apps:make_basic_app2 + configed=fakeapp.configapps:SimpleApp.make_app + """, + 'paste.composit_factory': """ + remote_addr=fakeapp.apps:make_remote_addr + """, + 'paste.filter_factory': """ + caps=fakeapp.apps:make_cap_filter + """, + 'paste.filter_app_factory': """ + caps2=fakeapp.apps:CapFilter + """, + }, + ) diff --git a/tests/fixture.py b/tests/fixture.py new file mode 100644 index 0000000..751659d --- /dev/null +++ b/tests/fixture.py @@ -0,0 +1,20 @@ +import os +import sys +import shutil + +test_dir = os.path.dirname(__file__) +egg_info_dir = os.path.join(test_dir, 'fake_packages', 'FakeApp.egg', + 'EGG-INFO') +info_dir = os.path.join(test_dir, 'fake_packages', 'FakeApp.egg', + 'FakeApp.egg-info') +if not os.path.exists(egg_info_dir): + try: + os.symlink(info_dir, egg_info_dir) + except: + shutil.copytree(info_dir, egg_info_dir) + +sys.path.append(os.path.dirname(egg_info_dir)) + +from pkg_resources import * +working_set.add_entry(os.path.dirname(egg_info_dir)) +require('FakeApp') diff --git a/tests/sample_configs/basic_app.ini b/tests/sample_configs/basic_app.ini new file mode 100644 index 0000000..f1d931c --- /dev/null +++ b/tests/sample_configs/basic_app.ini @@ -0,0 +1,14 @@ +[application:main] +use = egg:FakeApp#basic_app + +[application:other] +use = egg:FakeApp#other + +[composit:remote_addr] +use = egg:FakeApp#remote_addr +app.1 = main +addr.1 = 127.0.0.1 + +app.2 = other +addr.2 = 0.0.0.0 + diff --git a/tests/sample_configs/executable.ini b/tests/sample_configs/executable.ini new file mode 100755 index 0000000..3b75fe9 --- /dev/null +++ b/tests/sample_configs/executable.ini @@ -0,0 +1,10 @@ +#!/usr/bin/env paster +[exe] +sys.path = /fake/path/ + /another/fake/path ../fake_packages/ + +[server] +use = egg:PasteScript#cgi + +[app] +use = egg:FakeApp#basic_app diff --git a/tests/sample_configs/test_config.ini b/tests/sample_configs/test_config.ini new file mode 100644 index 0000000..d614829 --- /dev/null +++ b/tests/sample_configs/test_config.ini @@ -0,0 +1,38 @@ +[DEFAULT] +def1 = a +def2 = b +basepath = %(here)s + +[app:test1] +use = egg:FakeApp#configed +setting1 = foo +setting2 = bar +apppath = %(basepath)s/app + +[app:test2] +use = egg:FakeApp#configed +set def1 = test2 +set another = TEST +local conf = something + +[app:test3] +use = test2 +set def1 = test3 +another = something more + across several + lines + +[app:test_foreign_config] +use = config:test_config_included.ini +set glob = override +another = FOO + +[app:test_get] +use = egg:FakeApp#configed +set def2 = TEST +get def1 = def1 +get foo = def2 + +[app:test_global_conf] +use = egg:FakeApp#configed +test_interp = this:%(inherit)s diff --git a/tests/sample_configs/test_config_included.ini b/tests/sample_configs/test_config_included.ini new file mode 100644 index 0000000..cc0da7a --- /dev/null +++ b/tests/sample_configs/test_config_included.ini @@ -0,0 +1,10 @@ +[DEFAULT] +def2 = from include +def3 = c + +[app:main] +# Equivalent to the egg reference, but just for kicks... +paste.app_factory = fakeapp.configapps:SimpleApp.make_app +set glob = orig +bob = your uncle +another = BAR diff --git a/tests/sample_configs/test_error.ini b/tests/sample_configs/test_error.ini new file mode 100644 index 0000000..b6ad5b2 --- /dev/null +++ b/tests/sample_configs/test_error.ini @@ -0,0 +1,8 @@ +[DEFAULT] +def1 = a +def2 = b + +[app:main] +use = egg:FakeApp#configed +setting1 = foo +setting2 = %(does_not_exist)s/bar diff --git a/tests/sample_configs/test_filter.ini b/tests/sample_configs/test_filter.ini new file mode 100644 index 0000000..733c0aa --- /dev/null +++ b/tests/sample_configs/test_filter.ini @@ -0,0 +1,26 @@ +[app:normal] +use = egg:FakeApp#basic_app + +[pipeline:piped] +pipeline = egg:FakeApp#caps normal + +[filter-app:filt] +use = egg:FakeApp#caps +method_to_call = lower +next = normal + +[pipeline:piped2] +pipeline = egg:FakeApp#caps2 normal + +[filter-app:filt2] +use = egg:FakeApp#caps2 +method_to_call = lower +next = normal + +[app:inv] +use = egg:FakeApp#basic_app +filter-with = egg:FakeApp#caps + +[pipeline:piped3] +pipeline = egg:FakeApp#caps normal +extra_config_option = bad diff --git a/tests/sample_configs/test_filter_with.ini b/tests/sample_configs/test_filter_with.ini new file mode 100644 index 0000000..118804f --- /dev/null +++ b/tests/sample_configs/test_filter_with.ini @@ -0,0 +1,12 @@ +[app:main] +use = egg:FakeApp#basic_app +example = test +filter-with = filter1 + +[filter:filter1] +use = egg:FakeApp#caps +filter-with = filter2 + +[filter:filter2] +use = egg:FakeApp#caps + diff --git a/tests/sample_configs/test_func.ini b/tests/sample_configs/test_func.ini new file mode 100644 index 0000000..a0d28c4 --- /dev/null +++ b/tests/sample_configs/test_func.ini @@ -0,0 +1,13 @@ +[application:main] +use = call:fakeapp.apps:make_basic_app + +[application:other] +use = call:fakeapp.apps:make_basic_app2 + +[composit:remote_addr] +use = call:fakeapp.apps:make_remote_addr +app.1 = main +addr.1 = 127.0.0.1 + +app.2 = other +addr.2 = 0.0.0.0
\ No newline at end of file diff --git a/tests/test_basic_app.py b/tests/test_basic_app.py new file mode 100644 index 0000000..1ddb52b --- /dev/null +++ b/tests/test_basic_app.py @@ -0,0 +1,36 @@ +from paste.deploy import loadapp + +from tests.fixture import * +import fakeapp.apps + + +here = os.path.dirname(__file__) + + +def test_main(): + app = loadapp('config:sample_configs/basic_app.ini', + relative_to=here) + assert app is fakeapp.apps.basic_app + app = loadapp('config:sample_configs/basic_app.ini#main', + relative_to=here) + assert app is fakeapp.apps.basic_app + app = loadapp('config:sample_configs/basic_app.ini', + relative_to=here, name='main') + assert app is fakeapp.apps.basic_app + app = loadapp('config:sample_configs/basic_app.ini#ignored', + relative_to=here, name='main') + assert app is fakeapp.apps.basic_app + + +def test_other(): + app = loadapp('config:sample_configs/basic_app.ini#other', + relative_to=here) + assert app is fakeapp.apps.basic_app2 + + +def test_composit(): + app = loadapp('config:sample_configs/basic_app.ini#remote_addr', + relative_to=here) + assert isinstance(app, fakeapp.apps.RemoteAddrDispatch) + assert app.map['127.0.0.1'] is fakeapp.apps.basic_app + assert app.map['0.0.0.0'] is fakeapp.apps.basic_app2 diff --git a/tests/test_config.py b/tests/test_config.py new file mode 100644 index 0000000..3acbc5b --- /dev/null +++ b/tests/test_config.py @@ -0,0 +1,172 @@ +from paste.deploy import loadapp, appconfig +from tests.fixture import * +import fakeapp.configapps as fc +import fakeapp.apps + + +ini_file = 'config:sample_configs/test_config.ini' +here = os.path.dirname(__file__) +config_path = os.path.join(here, 'sample_configs') +config_filename = os.path.join(config_path, 'test_config.ini') + + +def test_config_egg(): + app = loadapp('egg:FakeApp#configed') + assert isinstance(app, fc.SimpleApp) + + +def test_config1(): + app = loadapp(ini_file, relative_to=here, name='test1') + assert app.local_conf == { + 'setting1': 'foo', + 'setting2': 'bar', + 'apppath': os.path.join(config_path, 'app')} + assert app.global_conf == { + 'def1': 'a', + 'def2': 'b', + 'basepath': config_path, + 'here': config_path, + '__file__': config_filename} + + +def test_config2(): + app = loadapp(ini_file, relative_to=here, name='test2') + assert app.local_conf == { + 'local conf': 'something'} + assert app.global_conf == { + 'def1': 'test2', + 'def2': 'b', + 'basepath': config_path, + 'another': 'TEST', + 'here': config_path, + '__file__': config_filename} + # Run this to make sure the global-conf-modified test2 + # didn't mess up the general global conf + test_config1() + + +def test_config3(): + app = loadapp(ini_file, relative_to=here, name='test3') + assert isinstance(app, fc.SimpleApp) + assert app.local_conf == { + 'local conf': 'something', + 'another': 'something more\nacross several\nlines'} + assert app.global_conf == { + 'def1': 'test3', + 'def2': 'b', + 'basepath': config_path, + 'another': 'TEST', + 'here': config_path, + '__file__': config_filename} + test_config2() + + +def test_main(): + app = loadapp('config:test_func.ini', + relative_to=config_path) + assert app is fakeapp.apps.basic_app + app = loadapp('config:test_func.ini#main', + relative_to=config_path) + assert app is fakeapp.apps.basic_app + app = loadapp('config:test_func.ini', + relative_to=config_path, name='main') + assert app is fakeapp.apps.basic_app + app = loadapp('config:test_func.ini#ignored', + relative_to=config_path, name='main') + assert app is fakeapp.apps.basic_app + + +def test_other(): + app = loadapp('config:test_func.ini#other', relative_to=config_path) + assert app is fakeapp.apps.basic_app2 + + +def test_composit(): + app = loadapp('config:test_func.ini#remote_addr', relative_to=config_path) + assert isinstance(app, fakeapp.apps.RemoteAddrDispatch) + assert app.map['127.0.0.1'] is fakeapp.apps.basic_app + assert app.map['0.0.0.0'] is fakeapp.apps.basic_app2 + + +def test_foreign_config(): + app = loadapp(ini_file, relative_to=here, name='test_foreign_config') + assert isinstance(app, fc.SimpleApp) + assert app.local_conf == { + 'another': 'FOO', + 'bob': 'your uncle'} + assert app.global_conf == { + 'def1': 'a', + # Note overwrite of DEFAULT value from foreign config + 'def2': 'b', + 'def3': 'c', + 'basepath': config_path, + 'glob': 'override', + 'here': config_path, + '__file__': os.path.join(config_path, 'test_config.ini')} + + +def test_config_get(): + app = loadapp(ini_file, relative_to=here, name='test_get') + assert isinstance(app, fc.SimpleApp) + assert app.local_conf == { + 'def1': 'a', + 'foo': 'TEST'} + assert app.global_conf == { + 'def1': 'a', + 'def2': 'TEST', + 'basepath': os.path.join(here, 'sample_configs'), + 'here': config_path, + '__file__': config_filename} + + +def test_appconfig(): + conf = appconfig(ini_file, relative_to=here, name='test_get') + assert conf == { + 'def1': 'a', + 'def2': 'TEST', + 'basepath': os.path.join(here, 'sample_configs'), + 'here': config_path, + '__file__': config_filename, + 'foo': 'TEST'} + assert conf.local_conf == { + 'def1': 'a', + 'foo': 'TEST'} + assert conf.global_conf == { + 'def1': 'a', + 'def2': 'TEST', + 'basepath': os.path.join(here, 'sample_configs'), + 'here': config_path, + '__file__': config_filename} + + +def test_appconfig_filter_with(): + conf = appconfig('config:test_filter_with.ini', relative_to=config_path) + assert conf['example'] == 'test' + + +def test_global_conf(): + conf = appconfig(ini_file, relative_to=here, name='test_global_conf', + global_conf={'def2': 'TEST DEF 2', 'inherit': 'bazbar'}) + assert conf == { + 'def1': 'a', + # Note overwrite of DEFAULT value + 'def2': 'TEST DEF 2', + 'basepath': os.path.join(here, 'sample_configs'), + 'here': config_path, + 'inherit': 'bazbar', + '__file__': config_filename, + 'test_interp': 'this:bazbar', + } + assert conf.local_conf == { + 'test_interp': 'this:bazbar'} + + +def test_interpolate_exception(): + try: + appconfig('config:test_error.ini', relative_to=config_path) + except Exception: + e = sys.exc_info()[1] + expected = "Error in file %s" % os.path.join(config_path, 'test_error.ini') + assert str(e).split(':')[0] == expected + else: + assert False, 'Should have raised an exception' diff --git a/tests/test_config_middleware.py b/tests/test_config_middleware.py new file mode 100644 index 0000000..56c3d04 --- /dev/null +++ b/tests/test_config_middleware.py @@ -0,0 +1,27 @@ +import pytest + +from paste.deploy.config import ConfigMiddleware + + +class Bug(Exception): + pass + + +def app_with_exception(environ, start_response): + def cont(): + yield b"something" + raise Bug + start_response('200 OK', [('Content-type', 'text/html')]) + return cont() + + +def test_error(): + # This import is conditional due to Paste not yet working on py3k + try: + from paste.fixture import TestApp + except ImportError: + raise SkipTest + + wrapped = ConfigMiddleware(app_with_exception, {'test': 1}) + test_app = TestApp(wrapped) + pytest.raises(Bug, test_app.get, '/') diff --git a/tests/test_converters.py b/tests/test_converters.py new file mode 100644 index 0000000..5361310 --- /dev/null +++ b/tests/test_converters.py @@ -0,0 +1,17 @@ +def test_asbool_truthy(): + from paste.deploy.converters import asbool + assert asbool('true') + assert asbool('yes') + assert asbool('on') + assert asbool('y') + assert asbool('t') + assert asbool('1') + +def test_asbool_falsy(): + from paste.deploy.converters import asbool + assert not asbool('false') + assert not asbool('no') + assert not asbool('off') + assert not asbool('n') + assert not asbool('f') + assert not asbool('0') diff --git a/tests/test_filter.py b/tests/test_filter.py new file mode 100644 index 0000000..470a9dd --- /dev/null +++ b/tests/test_filter.py @@ -0,0 +1,63 @@ +from paste.deploy import loadapp +from tests.fixture import * +import fakeapp.apps + + +here = os.path.dirname(__file__) + + +def test_filter_app(): + app = loadapp('config:sample_configs/test_filter.ini#filt', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert app.app is fakeapp.apps.basic_app + assert app.method_to_call == 'lower' + + +def test_pipeline(): + app = loadapp('config:sample_configs/test_filter.ini#piped', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert app.app is fakeapp.apps.basic_app + assert app.method_to_call == 'upper' + + +def test_filter_app2(): + app = loadapp('config:sample_configs/test_filter.ini#filt2', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert app.app is fakeapp.apps.basic_app + assert app.method_to_call == 'lower' + + +def test_pipeline2(): + app = loadapp('config:sample_configs/test_filter.ini#piped2', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert app.app is fakeapp.apps.basic_app + assert app.method_to_call == 'upper' + + +def test_filter_app_inverted(): + app = loadapp('config:sample_configs/test_filter.ini#inv', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert app.app is fakeapp.apps.basic_app + + +def test_filter_with_filter_with(): + app = loadapp('config:sample_configs/test_filter_with.ini', + relative_to=here) + assert isinstance(app, fakeapp.apps.CapFilter) + assert isinstance(app.app, fakeapp.apps.CapFilter) + assert app.app.app is fakeapp.apps.basic_app + + +def test_bad_pipeline(): + try: + app = loadapp('config:sample_configs/test_filter.ini#piped3', + relative_to=here) + except LookupError as err: + assert 'has extra (disallowed) settings' in err.args[0] + else: + assert False, 'should have raised LookupError' diff --git a/tests/test_load_package.py b/tests/test_load_package.py new file mode 100644 index 0000000..b3fea55 --- /dev/null +++ b/tests/test_load_package.py @@ -0,0 +1,12 @@ +from pprint import pprint +import sys + +import pkg_resources + +from paste.deploy.compat import print_ + + +def test_load_package(): + print_('Path:') + pprint(sys.path) + print_(pkg_resources.require('FakeApp')) |