We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Test only asyncio loop by default.
aiohttp uses parametrized `loop` fixture which runs all test suite several times: one for asyncio itself and another ones for uvloop and tokio if they are installed.
It's good for aiohttp testing itself but bad for `pytest-aiohttp` users.
For example test suites for my jobs take about 15 mins, we don't like to double the time (we use uvloop, sure).
We could solve the problem by pushing custom `loop` fixture into our `conftest.py` but it is not obvious and robust solution.

I suggest moving `pytest_configure` from `pytest_plugin.py` into `tests/conftest.py` and using only asyncio loop for tests by default.
As an option we could add support for command line `--aiohttp-loops` option and `aiohttp-loops` in `pytest.ini` for helping people to run their tests on specific asyncio loop implementations.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `aiohttp/pytest_plugin.py`
Content:
```
1 import asyncio
2 import collections
3 import contextlib
4 import tempfile
5 import warnings
6 
7 import pytest
8 from py import path
9 
10 from aiohttp.web import Application
11 
12 from .test_utils import unused_port as _unused_port
13 from .test_utils import (BaseTestServer, RawTestServer, TestClient, TestServer,
14                          loop_context, setup_test_loop, teardown_test_loop)
15 
16 
17 try:
18     import uvloop
19 except:  # pragma: no cover
20     uvloop = None
21 
22 try:
23     import tokio
24 except:  # pragma: no cover
25     tokio = None
26 
27 
28 def pytest_addoption(parser):
29     parser.addoption(
30         '--fast', action='store_true', default=False,
31         help='run tests faster by disabling extra checks')
32     parser.addoption(
33         '--loop', action='append', default=[],
34         help='run tests with specific loop: pyloop, uvloop, tokio')
35     parser.addoption(
36         '--enable-loop-debug', action='store_true', default=False,
37         help='enable event loop debug mode')
38 
39 
40 @pytest.fixture
41 def fast(request):
42     """ --fast config option """
43     return request.config.getoption('--fast')  # pragma: no cover
44 
45 
46 @contextlib.contextmanager
47 def _runtime_warning_context():
48     """
49     Context manager which checks for RuntimeWarnings, specifically to
50     avoid "coroutine 'X' was never awaited" warnings being missed.
51 
52     If RuntimeWarnings occur in the context a RuntimeError is raised.
53     """
54     with warnings.catch_warnings(record=True) as _warnings:
55         yield
56         rw = ['{w.filename}:{w.lineno}:{w.message}'.format(w=w)
57               for w in _warnings if w.category == RuntimeWarning]
58         if rw:
59             raise RuntimeError('{} Runtime Warning{},\n{}'.format(
60                 len(rw),
61                 '' if len(rw) == 1 else 's',
62                 '\n'.join(rw)
63             ))
64 
65 
66 @contextlib.contextmanager
67 def _passthrough_loop_context(loop, fast=False):
68     """
69     setups and tears down a loop unless one is passed in via the loop
70     argument when it's passed straight through.
71     """
72     if loop:
73         # loop already exists, pass it straight through
74         yield loop
75     else:
76         # this shadows loop_context's standard behavior
77         loop = setup_test_loop()
78         yield loop
79         teardown_test_loop(loop, fast=fast)
80 
81 
82 def pytest_pycollect_makeitem(collector, name, obj):
83     """
84     Fix pytest collecting for coroutines.
85     """
86     if collector.funcnamefilter(name) and asyncio.iscoroutinefunction(obj):
87         return list(collector._genfunctions(name, obj))
88 
89 
90 def pytest_pyfunc_call(pyfuncitem):
91     """
92     Run coroutines in an event loop instead of a normal function call.
93     """
94     fast = pyfuncitem.config.getoption("--fast")
95     if asyncio.iscoroutinefunction(pyfuncitem.function):
96         existing_loop = pyfuncitem.funcargs.get('loop', None)
97         with _runtime_warning_context():
98             with _passthrough_loop_context(existing_loop, fast=fast) as _loop:
99                 testargs = {arg: pyfuncitem.funcargs[arg]
100                             for arg in pyfuncitem._fixtureinfo.argnames}
101 
102                 task = _loop.create_task(pyfuncitem.obj(**testargs))
103                 _loop.run_until_complete(task)
104 
105         return True
106 
107 
108 def pytest_configure(config):
109     loops = config.getoption('--loop')
110 
111     factories = {'pyloop': asyncio.new_event_loop}
112 
113     if uvloop is not None:  # pragma: no cover
114         factories['uvloop'] = uvloop.new_event_loop
115 
116     if tokio is not None:  # pragma: no cover
117         factories['tokio'] = tokio.new_event_loop
118 
119     LOOP_FACTORIES.clear()
120     LOOP_FACTORY_IDS.clear()
121 
122     if loops:
123         for names in (name.split(',') for name in loops):
124             for name in names:
125                 name = name.strip()
126                 if name not in factories:
127                     raise ValueError(
128                         "Unknown loop '%s', available loops: %s" % (
129                             name, list(factories.keys())))
130 
131                 LOOP_FACTORIES.append(factories[name])
132                 LOOP_FACTORY_IDS.append(name)
133     else:
134         LOOP_FACTORIES.append(asyncio.new_event_loop)
135         LOOP_FACTORY_IDS.append('pyloop')
136 
137         if uvloop is not None:  # pragma: no cover
138             LOOP_FACTORIES.append(uvloop.new_event_loop)
139             LOOP_FACTORY_IDS.append('uvloop')
140 
141         if tokio is not None:
142             LOOP_FACTORIES.append(tokio.new_event_loop)
143             LOOP_FACTORY_IDS.append('tokio')
144 
145     asyncio.set_event_loop(None)
146 
147 
148 LOOP_FACTORIES = []
149 LOOP_FACTORY_IDS = []
150 
151 
152 @pytest.fixture(params=LOOP_FACTORIES, ids=LOOP_FACTORY_IDS)
153 def loop(request):
154     """Return an instance of the event loop."""
155     fast = request.config.getoption('--fast')
156     debug = request.config.getoption('--enable-loop-debug')
157 
158     with loop_context(request.param, fast=fast) as _loop:
159         if debug:
160             _loop.set_debug(True)  # pragma: no cover
161         yield _loop
162 
163 
164 @pytest.fixture
165 def unused_port():
166     """Return a port that is unused on the current host."""
167     return _unused_port
168 
169 
170 @pytest.yield_fixture
171 def test_server(loop):
172     """Factory to create a TestServer instance, given an app.
173 
174     test_server(app, **kwargs)
175     """
176     servers = []
177 
178     @asyncio.coroutine
179     def go(app, **kwargs):
180         server = TestServer(app)
181         yield from server.start_server(loop=loop, **kwargs)
182         servers.append(server)
183         return server
184 
185     yield go
186 
187     @asyncio.coroutine
188     def finalize():
189         while servers:
190             yield from servers.pop().close()
191 
192     loop.run_until_complete(finalize())
193 
194 
195 @pytest.yield_fixture
196 def raw_test_server(loop):
197     """Factory to create a RawTestServer instance, given a web handler.
198 
199     raw_test_server(handler, **kwargs)
200     """
201     servers = []
202 
203     @asyncio.coroutine
204     def go(handler, **kwargs):
205         server = RawTestServer(handler)
206         yield from server.start_server(loop=loop, **kwargs)
207         servers.append(server)
208         return server
209 
210     yield go
211 
212     @asyncio.coroutine
213     def finalize():
214         while servers:
215             yield from servers.pop().close()
216 
217     loop.run_until_complete(finalize())
218 
219 
220 @pytest.yield_fixture
221 def test_client(loop):
222     """Factory to create a TestClient instance.
223 
224     test_client(app, **kwargs)
225     test_client(server, **kwargs)
226     test_client(raw_server, **kwargs)
227     """
228     clients = []
229 
230     @asyncio.coroutine
231     def go(__param, *args, server_kwargs={}, **kwargs):
232 
233         if isinstance(__param, collections.Callable) and \
234                 not isinstance(__param, (Application, BaseTestServer)):
235             __param = __param(loop, *args, **kwargs)
236             kwargs = {}
237         else:
238             assert not args, "args should be empty"
239 
240         if isinstance(__param, Application):
241             server = TestServer(__param, loop=loop, **server_kwargs)
242             client = TestClient(server, loop=loop, **kwargs)
243         elif isinstance(__param, BaseTestServer):
244             client = TestClient(__param, loop=loop, **kwargs)
245         else:
246             raise ValueError("Unknown argument type: %r" % type(__param))
247 
248         yield from client.start_server()
249         clients.append(client)
250         return client
251 
252     yield go
253 
254     @asyncio.coroutine
255     def finalize():
256         while clients:
257             yield from clients.pop().close()
258 
259     loop.run_until_complete(finalize())
260 
261 
262 @pytest.fixture
263 def shorttmpdir():
264     """Provides a temporary directory with a shorter file system path than the
265     tmpdir fixture.
266     """
267     tmpdir = path.local(tempfile.mkdtemp())
268     yield tmpdir
269     tmpdir.remove(rec=1)
270
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/aiohttp/pytest_plugin.py b/aiohttp/pytest_plugin.py
--- a/aiohttp/pytest_plugin.py
+++ b/aiohttp/pytest_plugin.py
@@ -30,8 +30,8 @@
         '--fast', action='store_true', default=False,
         help='run tests faster by disabling extra checks')
     parser.addoption(
-        '--loop', action='append', default=[],
-        help='run tests with specific loop: pyloop, uvloop, tokio')
+        '--loop', action='store', default='pyloop',
+        help='run tests with specific loop: pyloop, uvloop, tokio or all')
     parser.addoption(
         '--enable-loop-debug', action='store_true', default=False,
         help='enable event loop debug mode')
@@ -119,29 +119,19 @@
     LOOP_FACTORIES.clear()
     LOOP_FACTORY_IDS.clear()
 
-    if loops:
-        for names in (name.split(',') for name in loops):
-            for name in names:
-                name = name.strip()
-                if name not in factories:
-                    raise ValueError(
-                        "Unknown loop '%s', available loops: %s" % (
-                            name, list(factories.keys())))
-
-                LOOP_FACTORIES.append(factories[name])
-                LOOP_FACTORY_IDS.append(name)
-    else:
-        LOOP_FACTORIES.append(asyncio.new_event_loop)
-        LOOP_FACTORY_IDS.append('pyloop')
-
-        if uvloop is not None:  # pragma: no cover
-            LOOP_FACTORIES.append(uvloop.new_event_loop)
-            LOOP_FACTORY_IDS.append('uvloop')
-
-        if tokio is not None:
-            LOOP_FACTORIES.append(tokio.new_event_loop)
-            LOOP_FACTORY_IDS.append('tokio')
-
+    if loops == 'all':
+        loops = 'pyloop,uvloop?,tokio?'
+
+    for name in loops.split(','):
+        required = not name.endswith('?')
+        name = name.strip(' ?')
+        if name in factories:
+            LOOP_FACTORIES.append(factories[name])
+            LOOP_FACTORY_IDS.append(name)
+        elif required:
+            raise ValueError(
+                "Unknown loop '%s', available loops: %s" % (
+                    name, list(factories.keys())))
     asyncio.set_event_loop(None)

{"golden_diff": "diff --git a/aiohttp/pytest_plugin.py b/aiohttp/pytest_plugin.py\n--- a/aiohttp/pytest_plugin.py\n+++ b/aiohttp/pytest_plugin.py\n@@ -30,8 +30,8 @@\n         '--fast', action='store_true', default=False,\n         help='run tests faster by disabling extra checks')\n     parser.addoption(\n-        '--loop', action='append', default=[],\n-        help='run tests with specific loop: pyloop, uvloop, tokio')\n+        '--loop', action='store', default='pyloop',\n+        help='run tests with specific loop: pyloop, uvloop, tokio or all')\n     parser.addoption(\n         '--enable-loop-debug', action='store_true', default=False,\n         help='enable event loop debug mode')\n@@ -119,29 +119,19 @@\n     LOOP_FACTORIES.clear()\n     LOOP_FACTORY_IDS.clear()\n \n-    if loops:\n-        for names in (name.split(',') for name in loops):\n-            for name in names:\n-                name = name.strip()\n-                if name not in factories:\n-                    raise ValueError(\n-                        \"Unknown loop '%s', available loops: %s\" % (\n-                            name, list(factories.keys())))\n-\n-                LOOP_FACTORIES.append(factories[name])\n-                LOOP_FACTORY_IDS.append(name)\n-    else:\n-        LOOP_FACTORIES.append(asyncio.new_event_loop)\n-        LOOP_FACTORY_IDS.append('pyloop')\n-\n-        if uvloop is not None:  # pragma: no cover\n-            LOOP_FACTORIES.append(uvloop.new_event_loop)\n-            LOOP_FACTORY_IDS.append('uvloop')\n-\n-        if tokio is not None:\n-            LOOP_FACTORIES.append(tokio.new_event_loop)\n-            LOOP_FACTORY_IDS.append('tokio')\n-\n+    if loops == 'all':\n+        loops = 'pyloop,uvloop?,tokio?'\n+\n+    for name in loops.split(','):\n+        required = not name.endswith('?')\n+        name = name.strip(' ?')\n+        if name in factories:\n+            LOOP_FACTORIES.append(factories[name])\n+            LOOP_FACTORY_IDS.append(name)\n+        elif required:\n+            raise ValueError(\n+                \"Unknown loop '%s', available loops: %s\" % (\n+                    name, list(factories.keys())))\n     asyncio.set_event_loop(None)\n", "issue": "Test only asyncio loop by default.\naiohttp uses parametrized `loop` fixture which runs all test suite several times: one for asyncio itself and another ones for uvloop and tokio if they are installed.\r\nIt's good for aiohttp testing itself but bad for `pytest-aiohttp` users.\r\nFor example test suites for my jobs take about 15 mins, we don't like to double the time (we use uvloop, sure).\r\nWe could solve the problem by pushing custom `loop` fixture into our `conftest.py` but it is not obvious and robust solution.\r\n\r\nI suggest moving `pytest_configure` from `pytest_plugin.py` into `tests/conftest.py` and using only asyncio loop for tests by default.\r\nAs an option we could add support for command line `--aiohttp-loops` option and `aiohttp-loops` in `pytest.ini` for helping people to run their tests on specific asyncio loop implementations.\n", "before_files": [{"content": "import asyncio\nimport collections\nimport contextlib\nimport tempfile\nimport warnings\n\nimport pytest\nfrom py import path\n\nfrom aiohttp.web import Application\n\nfrom .test_utils import unused_port as _unused_port\nfrom .test_utils import (BaseTestServer, RawTestServer, TestClient, TestServer,\n                         loop_context, setup_test_loop, teardown_test_loop)\n\n\ntry:\n    import uvloop\nexcept:  # pragma: no cover\n    uvloop = None\n\ntry:\n    import tokio\nexcept:  # pragma: no cover\n    tokio = None\n\n\ndef pytest_addoption(parser):\n    parser.addoption(\n        '--fast', action='store_true', default=False,\n        help='run tests faster by disabling extra checks')\n    parser.addoption(\n        '--loop', action='append', default=[],\n        help='run tests with specific loop: pyloop, uvloop, tokio')\n    parser.addoption(\n        '--enable-loop-debug', action='store_true', default=False,\n        help='enable event loop debug mode')\n\n\n@pytest.fixture\ndef fast(request):\n    \"\"\" --fast config option \"\"\"\n    return request.config.getoption('--fast')  # pragma: no cover\n\n\n@contextlib.contextmanager\ndef _runtime_warning_context():\n    \"\"\"\n    Context manager which checks for RuntimeWarnings, specifically to\n    avoid \"coroutine 'X' was never awaited\" warnings being missed.\n\n    If RuntimeWarnings occur in the context a RuntimeError is raised.\n    \"\"\"\n    with warnings.catch_warnings(record=True) as _warnings:\n        yield\n        rw = ['{w.filename}:{w.lineno}:{w.message}'.format(w=w)\n              for w in _warnings if w.category == RuntimeWarning]\n        if rw:\n            raise RuntimeError('{} Runtime Warning{},\\n{}'.format(\n                len(rw),\n                '' if len(rw) == 1 else 's',\n                '\\n'.join(rw)\n            ))\n\n\n@contextlib.contextmanager\ndef _passthrough_loop_context(loop, fast=False):\n    \"\"\"\n    setups and tears down a loop unless one is passed in via the loop\n    argument when it's passed straight through.\n    \"\"\"\n    if loop:\n        # loop already exists, pass it straight through\n        yield loop\n    else:\n        # this shadows loop_context's standard behavior\n        loop = setup_test_loop()\n        yield loop\n        teardown_test_loop(loop, fast=fast)\n\n\ndef pytest_pycollect_makeitem(collector, name, obj):\n    \"\"\"\n    Fix pytest collecting for coroutines.\n    \"\"\"\n    if collector.funcnamefilter(name) and asyncio.iscoroutinefunction(obj):\n        return list(collector._genfunctions(name, obj))\n\n\ndef pytest_pyfunc_call(pyfuncitem):\n    \"\"\"\n    Run coroutines in an event loop instead of a normal function call.\n    \"\"\"\n    fast = pyfuncitem.config.getoption(\"--fast\")\n    if asyncio.iscoroutinefunction(pyfuncitem.function):\n        existing_loop = pyfuncitem.funcargs.get('loop', None)\n        with _runtime_warning_context():\n            with _passthrough_loop_context(existing_loop, fast=fast) as _loop:\n                testargs = {arg: pyfuncitem.funcargs[arg]\n                            for arg in pyfuncitem._fixtureinfo.argnames}\n\n                task = _loop.create_task(pyfuncitem.obj(**testargs))\n                _loop.run_until_complete(task)\n\n        return True\n\n\ndef pytest_configure(config):\n    loops = config.getoption('--loop')\n\n    factories = {'pyloop': asyncio.new_event_loop}\n\n    if uvloop is not None:  # pragma: no cover\n        factories['uvloop'] = uvloop.new_event_loop\n\n    if tokio is not None:  # pragma: no cover\n        factories['tokio'] = tokio.new_event_loop\n\n    LOOP_FACTORIES.clear()\n    LOOP_FACTORY_IDS.clear()\n\n    if loops:\n        for names in (name.split(',') for name in loops):\n            for name in names:\n                name = name.strip()\n                if name not in factories:\n                    raise ValueError(\n                        \"Unknown loop '%s', available loops: %s\" % (\n                            name, list(factories.keys())))\n\n                LOOP_FACTORIES.append(factories[name])\n                LOOP_FACTORY_IDS.append(name)\n    else:\n        LOOP_FACTORIES.append(asyncio.new_event_loop)\n        LOOP_FACTORY_IDS.append('pyloop')\n\n        if uvloop is not None:  # pragma: no cover\n            LOOP_FACTORIES.append(uvloop.new_event_loop)\n            LOOP_FACTORY_IDS.append('uvloop')\n\n        if tokio is not None:\n            LOOP_FACTORIES.append(tokio.new_event_loop)\n            LOOP_FACTORY_IDS.append('tokio')\n\n    asyncio.set_event_loop(None)\n\n\nLOOP_FACTORIES = []\nLOOP_FACTORY_IDS = []\n\n\n@pytest.fixture(params=LOOP_FACTORIES, ids=LOOP_FACTORY_IDS)\ndef loop(request):\n    \"\"\"Return an instance of the event loop.\"\"\"\n    fast = request.config.getoption('--fast')\n    debug = request.config.getoption('--enable-loop-debug')\n\n    with loop_context(request.param, fast=fast) as _loop:\n        if debug:\n            _loop.set_debug(True)  # pragma: no cover\n        yield _loop\n\n\n@pytest.fixture\ndef unused_port():\n    \"\"\"Return a port that is unused on the current host.\"\"\"\n    return _unused_port\n\n\n@pytest.yield_fixture\ndef test_server(loop):\n    \"\"\"Factory to create a TestServer instance, given an app.\n\n    test_server(app, **kwargs)\n    \"\"\"\n    servers = []\n\n    @asyncio.coroutine\n    def go(app, **kwargs):\n        server = TestServer(app)\n        yield from server.start_server(loop=loop, **kwargs)\n        servers.append(server)\n        return server\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while servers:\n            yield from servers.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.yield_fixture\ndef raw_test_server(loop):\n    \"\"\"Factory to create a RawTestServer instance, given a web handler.\n\n    raw_test_server(handler, **kwargs)\n    \"\"\"\n    servers = []\n\n    @asyncio.coroutine\n    def go(handler, **kwargs):\n        server = RawTestServer(handler)\n        yield from server.start_server(loop=loop, **kwargs)\n        servers.append(server)\n        return server\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while servers:\n            yield from servers.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.yield_fixture\ndef test_client(loop):\n    \"\"\"Factory to create a TestClient instance.\n\n    test_client(app, **kwargs)\n    test_client(server, **kwargs)\n    test_client(raw_server, **kwargs)\n    \"\"\"\n    clients = []\n\n    @asyncio.coroutine\n    def go(__param, *args, server_kwargs={}, **kwargs):\n\n        if isinstance(__param, collections.Callable) and \\\n                not isinstance(__param, (Application, BaseTestServer)):\n            __param = __param(loop, *args, **kwargs)\n            kwargs = {}\n        else:\n            assert not args, \"args should be empty\"\n\n        if isinstance(__param, Application):\n            server = TestServer(__param, loop=loop, **server_kwargs)\n            client = TestClient(server, loop=loop, **kwargs)\n        elif isinstance(__param, BaseTestServer):\n            client = TestClient(__param, loop=loop, **kwargs)\n        else:\n            raise ValueError(\"Unknown argument type: %r\" % type(__param))\n\n        yield from client.start_server()\n        clients.append(client)\n        return client\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while clients:\n            yield from clients.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.fixture\ndef shorttmpdir():\n    \"\"\"Provides a temporary directory with a shorter file system path than the\n    tmpdir fixture.\n    \"\"\"\n    tmpdir = path.local(tempfile.mkdtemp())\n    yield tmpdir\n    tmpdir.remove(rec=1)\n", "path": "aiohttp/pytest_plugin.py"}], "after_files": [{"content": "import asyncio\nimport collections\nimport contextlib\nimport tempfile\nimport warnings\n\nimport pytest\nfrom py import path\n\nfrom aiohttp.web import Application\n\nfrom .test_utils import unused_port as _unused_port\nfrom .test_utils import (BaseTestServer, RawTestServer, TestClient, TestServer,\n                         loop_context, setup_test_loop, teardown_test_loop)\n\n\ntry:\n    import uvloop\nexcept:  # pragma: no cover\n    uvloop = None\n\ntry:\n    import tokio\nexcept:  # pragma: no cover\n    tokio = None\n\n\ndef pytest_addoption(parser):\n    parser.addoption(\n        '--fast', action='store_true', default=False,\n        help='run tests faster by disabling extra checks')\n    parser.addoption(\n        '--loop', action='store', default='pyloop',\n        help='run tests with specific loop: pyloop, uvloop, tokio or all')\n    parser.addoption(\n        '--enable-loop-debug', action='store_true', default=False,\n        help='enable event loop debug mode')\n\n\n@pytest.fixture\ndef fast(request):\n    \"\"\" --fast config option \"\"\"\n    return request.config.getoption('--fast')  # pragma: no cover\n\n\n@contextlib.contextmanager\ndef _runtime_warning_context():\n    \"\"\"\n    Context manager which checks for RuntimeWarnings, specifically to\n    avoid \"coroutine 'X' was never awaited\" warnings being missed.\n\n    If RuntimeWarnings occur in the context a RuntimeError is raised.\n    \"\"\"\n    with warnings.catch_warnings(record=True) as _warnings:\n        yield\n        rw = ['{w.filename}:{w.lineno}:{w.message}'.format(w=w)\n              for w in _warnings if w.category == RuntimeWarning]\n        if rw:\n            raise RuntimeError('{} Runtime Warning{},\\n{}'.format(\n                len(rw),\n                '' if len(rw) == 1 else 's',\n                '\\n'.join(rw)\n            ))\n\n\n@contextlib.contextmanager\ndef _passthrough_loop_context(loop, fast=False):\n    \"\"\"\n    setups and tears down a loop unless one is passed in via the loop\n    argument when it's passed straight through.\n    \"\"\"\n    if loop:\n        # loop already exists, pass it straight through\n        yield loop\n    else:\n        # this shadows loop_context's standard behavior\n        loop = setup_test_loop()\n        yield loop\n        teardown_test_loop(loop, fast=fast)\n\n\ndef pytest_pycollect_makeitem(collector, name, obj):\n    \"\"\"\n    Fix pytest collecting for coroutines.\n    \"\"\"\n    if collector.funcnamefilter(name) and asyncio.iscoroutinefunction(obj):\n        return list(collector._genfunctions(name, obj))\n\n\ndef pytest_pyfunc_call(pyfuncitem):\n    \"\"\"\n    Run coroutines in an event loop instead of a normal function call.\n    \"\"\"\n    fast = pyfuncitem.config.getoption(\"--fast\")\n    if asyncio.iscoroutinefunction(pyfuncitem.function):\n        existing_loop = pyfuncitem.funcargs.get('loop', None)\n        with _runtime_warning_context():\n            with _passthrough_loop_context(existing_loop, fast=fast) as _loop:\n                testargs = {arg: pyfuncitem.funcargs[arg]\n                            for arg in pyfuncitem._fixtureinfo.argnames}\n\n                task = _loop.create_task(pyfuncitem.obj(**testargs))\n                _loop.run_until_complete(task)\n\n        return True\n\n\ndef pytest_configure(config):\n    loops = config.getoption('--loop')\n\n    factories = {'pyloop': asyncio.new_event_loop}\n\n    if uvloop is not None:  # pragma: no cover\n        factories['uvloop'] = uvloop.new_event_loop\n\n    if tokio is not None:  # pragma: no cover\n        factories['tokio'] = tokio.new_event_loop\n\n    LOOP_FACTORIES.clear()\n    LOOP_FACTORY_IDS.clear()\n\n    if loops == 'all':\n        loops = 'pyloop,uvloop?,tokio?'\n\n    for name in loops.split(','):\n        required = not name.endswith('?')\n        name = name.strip(' ?')\n        if name in factories:\n            LOOP_FACTORIES.append(factories[name])\n            LOOP_FACTORY_IDS.append(name)\n        elif required:\n            raise ValueError(\n                \"Unknown loop '%s', available loops: %s\" % (\n                    name, list(factories.keys())))\n    asyncio.set_event_loop(None)\n\n\nLOOP_FACTORIES = []\nLOOP_FACTORY_IDS = []\n\n\n@pytest.fixture(params=LOOP_FACTORIES, ids=LOOP_FACTORY_IDS)\ndef loop(request):\n    \"\"\"Return an instance of the event loop.\"\"\"\n    fast = request.config.getoption('--fast')\n    debug = request.config.getoption('--enable-loop-debug')\n\n    with loop_context(request.param, fast=fast) as _loop:\n        if debug:\n            _loop.set_debug(True)  # pragma: no cover\n        yield _loop\n\n\n@pytest.fixture\ndef unused_port():\n    \"\"\"Return a port that is unused on the current host.\"\"\"\n    return _unused_port\n\n\n@pytest.yield_fixture\ndef test_server(loop):\n    \"\"\"Factory to create a TestServer instance, given an app.\n\n    test_server(app, **kwargs)\n    \"\"\"\n    servers = []\n\n    @asyncio.coroutine\n    def go(app, **kwargs):\n        server = TestServer(app)\n        yield from server.start_server(loop=loop, **kwargs)\n        servers.append(server)\n        return server\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while servers:\n            yield from servers.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.yield_fixture\ndef raw_test_server(loop):\n    \"\"\"Factory to create a RawTestServer instance, given a web handler.\n\n    raw_test_server(handler, **kwargs)\n    \"\"\"\n    servers = []\n\n    @asyncio.coroutine\n    def go(handler, **kwargs):\n        server = RawTestServer(handler)\n        yield from server.start_server(loop=loop, **kwargs)\n        servers.append(server)\n        return server\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while servers:\n            yield from servers.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.yield_fixture\ndef test_client(loop):\n    \"\"\"Factory to create a TestClient instance.\n\n    test_client(app, **kwargs)\n    test_client(server, **kwargs)\n    test_client(raw_server, **kwargs)\n    \"\"\"\n    clients = []\n\n    @asyncio.coroutine\n    def go(__param, *args, server_kwargs={}, **kwargs):\n\n        if isinstance(__param, collections.Callable) and \\\n                not isinstance(__param, (Application, BaseTestServer)):\n            __param = __param(loop, *args, **kwargs)\n            kwargs = {}\n        else:\n            assert not args, \"args should be empty\"\n\n        if isinstance(__param, Application):\n            server = TestServer(__param, loop=loop, **server_kwargs)\n            client = TestClient(server, loop=loop, **kwargs)\n        elif isinstance(__param, BaseTestServer):\n            client = TestClient(__param, loop=loop, **kwargs)\n        else:\n            raise ValueError(\"Unknown argument type: %r\" % type(__param))\n\n        yield from client.start_server()\n        clients.append(client)\n        return client\n\n    yield go\n\n    @asyncio.coroutine\n    def finalize():\n        while clients:\n            yield from clients.pop().close()\n\n    loop.run_until_complete(finalize())\n\n\n@pytest.fixture\ndef shorttmpdir():\n    \"\"\"Provides a temporary directory with a shorter file system path than the\n    tmpdir fixture.\n    \"\"\"\n    tmpdir = path.local(tempfile.mkdtemp())\n    yield tmpdir\n    tmpdir.remove(rec=1)\n", "path": "aiohttp/pytest_plugin.py"}]}