#122 Tests are failing with Python 3: TestFuncApiV20.test_get_results_by_result_data
Closed: Fixed 6 years ago Opened 6 years ago by frantisekz.

This is failing just with Python 3, Python 2 works just fine :)

============================= test session starts ==============================
platform linux -- Python 3.7.1, pytest-3.6.4, py-1.5.4, pluggy-0.6.0
rootdir: /builddir/build/BUILD/resultsdb-2.1.1, inifile: tox.ini
plugins: cov-2.5.1
collected 62 items

testing/functest_api_v10.py .                                            [  1%]
testing/functest_api_v20.py ....................................F....    [ 67%]
testing/functest_create_fedmsg.py ......                                 [ 77%]
testing/test_general.py ..............                                   [100%]

=================================== FAILURES ===================================
________________ TestFuncApiV20.test_get_results_by_result_data ________________

self = <testing.functest_api_v20.TestFuncApiV20 object at 0x7f3e6cace7b8>

    def test_get_results_by_result_data(self):
        self.test_create_result()

>       r = self.app.get('/api/v2.0/results?item=perl-Specio-0.25-1.fc26')

testing/functest_api_v20.py:754: 
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 
/usr/lib/python3.7/site-packages/werkzeug/test.py:830: in get
    return self.open(*args, **kw)
/usr/lib/python3.7/site-packages/flask/testing.py:200: in open
    follow_redirects=follow_redirects
/usr/lib/python3.7/site-packages/werkzeug/test.py:803: in open
    response = self.run_wsgi_app(environ, buffered=buffered)
/usr/lib/python3.7/site-packages/werkzeug/test.py:716: in run_wsgi_app
    rv = run_wsgi_app(self.application, environ, buffered=buffered)
/usr/lib/python3.7/site-packages/werkzeug/test.py:923: in run_wsgi_app
    app_rv = app(environ, start_response)
/usr/lib/python3.7/site-packages/flask/app.py:2309: in __call__
    return self.wsgi_app(environ, start_response)
resultsdb/proxy.py:61: in __call__
    return self.app(environ, start_response)
/usr/lib/python3.7/site-packages/flask/app.py:2295: in wsgi_app
    response = self.handle_exception(e)
/usr/lib/python3.7/site-packages/flask/app.py:1741: in handle_exception
    reraise(exc_type, exc_value, tb)
/usr/lib/python3.7/site-packages/flask/_compat.py:35: in reraise
    raise value
/usr/lib/python3.7/site-packages/flask/app.py:2292: in wsgi_app
    response = self.full_dispatch_request()
/usr/lib/python3.7/site-packages/flask/app.py:1815: in full_dispatch_request
    rv = self.handle_user_exception(e)
/usr/lib/python3.7/site-packages/flask/app.py:1718: in handle_user_exception
    reraise(exc_type, exc_value, tb)
/usr/lib/python3.7/site-packages/flask/_compat.py:35: in reraise
    raise value
/usr/lib/python3.7/site-packages/flask/app.py:1813: in full_dispatch_request
    rv = self.dispatch_request()
/usr/lib/python3.7/site-packages/flask/app.py:1799: in dispatch_request
    return self.view_functions[rule.endpoint](**req.view_args)
resultsdb/controllers/api_v2.py:512: in get_results
    p = __get_results_parse_args()
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ 

    def __get_results_parse_args():
        retval = {"args": None, "error": None, "result_data": None}
        try:
            args = RP['get_results'].parse_args()
        except JSONBadRequest as error:
            retval["error"] = (jsonify({"message": "Malformed Request: %s" % error}), error.code)
            return retval
        except HTTPException as error:
            retval["error"] = (jsonify(error.data), error.code)
            return retval

        if args.get('outcome', None) is not None:
            args['outcome'] = [outcome.strip().upper() for outcome in args['outcome'].split(',')]
            for outcome in args['outcome']:
                if outcome not in RESULT_OUTCOME:
                    retval["error"] = (
                        jsonify({'message': "outcome %r not one of %r" % (outcome, RESULT_OUTCOME,)}), 400)
                    return retval

        try:
            s, e = parse_since(args.get('since', None))
        except iso8601.iso8601.ParseError:
            retval["error"] = (jsonify({"message": "'since' parameter not in ISO8601 format"}), 400)
            return retval

        args['since'] = {'start': s, 'end': e}
        args['testcases'] = [tc.strip() for tc in args['testcases'].split(',') if tc.strip()]
        args['testcases:like'] = [tc.strip() for tc in args['testcases:like'].split(',') if tc.strip()]
        args['groups'] = [group.strip() for group in args['groups'].split(',') if group.strip()]
        retval['args'] = args

        # find results_data with the query parameters
        # these are the paramters other than those defined in RequestParser
        req_args = dict(request.args)  # this is important, do not delete ;)

        # req_args is a dict of lists, where keys are param names and values are param values
        #  the value is a list even if only one param value was specified
        results_data = {key: req_args[key] for key in req_args.keys() if key not in args}
        for param, values in results_data.items():
            for i, value in enumerate(values):
>               results_data[param][i] = value.split(',')
E               TypeError: 'str' object does not support item assignment

resultsdb/controllers/api_v2.py:431: TypeError
---------------------------- Captured stdout setup -----------------------------
Initializing database
 - Dropping all tables
 - Creating tables
 - Stamping alembic's current version to 'head'
 - Database is currently at rev cd581d0e83df
Upgrading Database to Latest Revision
---------------------------- Captured stderr setup -----------------------------
[migration.py:117] 2018-11-18 22:24:21 INFO    Context impl SQLiteImpl.
[migration.py:122] 2018-11-18 22:24:21 INFO    Will assume non-transactional DDL.
[migration.py:117] 2018-11-18 22:24:21 INFO    Context impl SQLiteImpl.
[migration.py:122] 2018-11-18 22:24:21 INFO    Will assume non-transactional DDL.
[migration.py:117] 2018-11-18 22:24:21 INFO    Context impl SQLiteImpl.
[migration.py:122] 2018-11-18 22:24:21 INFO    Will assume non-transactional DDL.
------------------------------ Captured log setup ------------------------------
migration.py               117 INFO     Context impl SQLiteImpl.
migration.py               122 INFO     Will assume non-transactional DDL.
migration.py               117 INFO     Context impl SQLiteImpl.
migration.py               122 INFO     Will assume non-transactional DDL.
migration.py               117 INFO     Context impl SQLiteImpl.
migration.py               122 INFO     Will assume non-transactional DDL.
----------------------------- Captured stderr call -----------------------------
[api_v2.py:676] 2018-11-18 22:24:21 DEBUG   Created new result for testcase scratch.testing.mytestcase with outcome PASSED
[api_v2.py:676] 2018-11-18 22:24:21 DEBUG   Created new result for testcase scratch.testing.mytestcase with outcome PASSED
[api_v2.py:679] 2018-11-18 22:24:21 DEBUG   Preparing to publish message for result id 1
[api_v2.py:679] 2018-11-18 22:24:21 DEBUG   Preparing to publish message for result id 1
[messaging.py:181] 2018-11-18 22:24:21 DEBUG   Found the following installed messaging plugin {'dummy': <class 'resultsdb.messaging.DummyPlugin'>, 'fedmsg': <class 'resultsdb.messaging.FedmsgPlugin'>, 'stomp': <class 'resultsdb.messaging.StompPlugin'>}
[messaging.py:191] 2018-11-18 22:24:21 DEBUG   Instantiating plugin <class 'resultsdb.messaging.DummyPlugin'> named dummy
[messaging.py:134] 2018-11-18 22:24:21 INFO    <resultsdb.messaging.DummyPlugin object at 0x7f3e6c4e0518>->{'id': 1, 'groups': ['3ce5f6d7-ce34-489b-ab61-325ce634eab5'], 'testcase': {'name': 'scratch.testing.mytestcase', 'ref_url': 'http://example.com/scratch.testing.mytestcase', 'href': 'http://localhost/api/v2.0/testcases/scratch.testing.mytestcase'}, 'submit_time': '2018-11-18T21:24:21.352515', 'outcome': 'PASSED', 'note': 'Result Note', 'ref_url': 'http://example.com/testing.result', 'data': {'item': ['perl-Specio-0.25-1.fc26'], 'type': ['koji_build'], 'arch': ['x86_64'], 'moo': ['boo', 'woof']}, 'href': 'http://localhost/api/v2.0/results/1'}
------------------------------ Captured log call -------------------------------
api_v2.py                  676 DEBUG    Created new result for testcase scratch.testing.mytestcase with outcome PASSED
api_v2.py                  679 DEBUG    Preparing to publish message for result id 1
messaging.py               181 DEBUG    Found the following installed messaging plugin {'dummy': <class 'resultsdb.messaging.DummyPlugin'>, 'fedmsg': <class 'resultsdb.messaging.FedmsgPlugin'>, 'stomp': <class 'resultsdb.messaging.StompPlugin'>}
messaging.py               191 DEBUG    Instantiating plugin <class 'resultsdb.messaging.DummyPlugin'> named dummy
messaging.py               134 INFO     <resultsdb.messaging.DummyPlugin object at 0x7f3e6c4e0518>->{'id': 1, 'groups': ['3ce5f6d7-ce34-489b-ab61-325ce634eab5'], 'testcase': {'name': 'scratch.testing.mytestcase', 'ref_url': 'http://example.com/scratch.testing.mytestcase', 'href': 'http://localhost/api/v2.0/testcases/scratch.testing.mytestcase'}, 'submit_time': '2018-11-18T21:24:21.352515', 'outcome': 'PASSED', 'note': 'Result Note', 'ref_url': 'http://example.com/testing.result', 'data': {'item': ['perl-Specio-0.25-1.fc26'], 'type': ['koji_build'], 'arch': ['x86_64'], 'moo': ['boo', 'woof']}, 'href': 'http://localhost/api/v2.0/results/1'}

----------- coverage: platform linux, python 3.7.1-final-0 -----------
Name                                                                                 Stmts   Miss  Cover   Missing
------------------------------------------------------------------------------------------------------------------
resultsdb/__init__.py                                                                  117     57    51%   61-64, 72-73, 78-79, 86, 89-90, 113-119, 122-128, 141-183
resultsdb/alembic/env.py                                                                28      5    82%   42-46, 79
resultsdb/alembic/versions/153c416322c2_create_indexes_on_foreign_keys.py               14      6    57%   21-23, 29-31
resultsdb/alembic/versions/15f5eeb9f635_initial_revision.py                             10      2    80%   21, 27
resultsdb/alembic/versions/17ec41bd6e9a_added_uuid_column_to_the_job_table.py           10      2    80%   21, 27
resultsdb/alembic/versions/34760e10040b_add_aborted_outcome.py                          28     15    46%   28-36, 41-51
resultsdb/alembic/versions/433d0b5b3b96_added_index_on_the_keyval_store.py               9      2    78%   20, 27
resultsdb/alembic/versions/4ace44a44bf_change_index_on_result_data_so_like_can_.py      11      4    64%   20-22, 28-29
resultsdb/alembic/versions/4bf1390f06d1_added_index_on_submit_time.py                   10      2    80%   21, 27
resultsdb/alembic/versions/4dbe714897fe_remove_the_user_model.py                        10      2    80%   19, 23
resultsdb/alembic/versions/540dbe71fa91_change_schema_to_v2_0_step_1.py                 94     71    24%   43-121, 127-158
resultsdb/alembic/versions/978007ecd2b_changed_testcase_name_to_text.py                 12      4    67%   21-22, 29-30
resultsdb/alembic/versions/cd581d0e83df_change_outcome_from_enum_to_string.py           12      4    67%   20-21, 26-27
resultsdb/alembic/versions/dbfab576c81_change_schema_to_v2_0_step_2.py                  87     56    36%   56-96, 100-122
resultsdb/cli.py                                                                        89     50    44%   48-60, 90-91, 95-133, 137-166, 170
resultsdb/config.py                                                                     42      0   100%
resultsdb/controllers/__init__.py                                                        0      0   100%
resultsdb/controllers/api_v1.py                                                        399    252    37%   56, 61, 97-112, 119-137, 141-161, 165-173, 177-233, 265-285, 298-309, 316-319, 334-349, 379-424, 430-452, 464-484, 489-494, 501-504, 510-511, 518-519, 525, 534, 549, 552, 557, 560-561, 579, 606-619, 630-635, 640-656, 662-678, 684
resultsdb/controllers/api_v2.py                                                        472     73    85%   58, 63, 111-112, 135, 158-161, 214-215, 239-242, 250, 256, 295-298, 365-387, 395-400, 406-408, 412-414, 433, 436, 456, 514, 549, 555, 586-587, 606-607, 609-610, 655, 663, 666-667, 687-688, 728-731, 765-766
resultsdb/controllers/main.py                                                            5      1    80%   28
resultsdb/lib/__init__.py                                                                0      0   100%
resultsdb/lib/helpers.py                                                                34      1    97%   15
resultsdb/messaging.py                                                                  80     33    59%   69-100, 119, 123, 141, 147-156, 159-172, 183, 189
resultsdb/models/__init__.py                                                             0      0   100%
resultsdb/models/results.py                                                             62      1    98%   70
resultsdb/proxy.py                                                                      18      6    67%   49-52, 56, 60
resultsdb/serializers/__init__.py                                                       26      1    96%   41
resultsdb/serializers/api_v1.py                                                         25      2    92%   79-84
resultsdb/serializers/api_v2.py                                                         21      2    90%   70-75
------------------------------------------------------------------------------------------------------------------
TOTAL                                                                                 1725    654    62%

===================== 1 failed, 61 passed in 5.81 seconds ======================

How are you executing the tests? What are the versions of the relevant packages? I can't reproduce the issue using tox on the current develop's head.

py36 installed: alembic==1.0.3,aniso8601==4.0.1,arrow==0.12.1,atomicwrites==1.2.1,attrs==18.2.0,certifi==2018.10.15,chardet==3.0.4,Click==7.0,coverage==4.5.2,fedmsg==1.1.1,Flask==1.0.2,flask-oidc==1.4.0,Flask-RESTful==0.3.5,Flask-SQLAlchemy==2.3.2,httplib2==0.12.0,idna==2.7,iso8601==0.1.12,itsdangerous==1.1.0,Jinja2==2.10,kitchen==1.2.5,Mako==1.0.7,MarkupSafe==1.1.0,more-itertools==4.3.0,oauth2client==4.1.3,pluggy==0.8.0,py==1.7.0,pyasn1==0.4.4,pyasn1-modules==0.2.2,pytest==4.0.0,pytest-cov==2.6.0,python-dateutil==2.7.5,python-editor==1.0.3,pytz==2018.7,pyzmq==17.1.2,requests==2.20.1,resultsdb==2.1.1,rsa==4.0,six==1.11.0,SQLAlchemy==1.2.14,urllib3==1.24.1,Werkzeug==0.14.1

py36 runtests: PYTHONHASHSEED='345027516'
py36 runtests: commands[0] | python -m pytest
========================================== test session starts ==========================================
platform linux -- Python 3.6.6, pytest-4.0.0, py-1.7.0, pluggy-0.8.0
rootdir: /home/src/taskbot_hub/resultsdb/resultsdb, inifile: tox.ini
plugins: cov-2.6.0
collected 62 items                                                                                      

testing/functest_api_v10.py .                                                                     [  1%]
testing/functest_api_v20.py .........................................                             [ 67%]
testing/functest_create_fedmsg.py ......                                                          [ 77%]
testing/test_general.py ..............                                                            [100%]

Python 3.7 broke it.

Try:

sed -i -e 's/py36/py37/g' tox.ini
tox

It will fail.

Not wanna be too rude, but maybe try including a reasonable reproducer in the OP next time, instead of "just" a wall of logs? :) (will try with py37 though)

Yeah, I didn't know it was caused by Python 3.7, I've just seen it failing in mock during %check :(

No worries, you'll do better next time :) Important thing is, we got to point in the end...

Fixed by 4bfd59b, BTW

Metadata Update from @jskladan:
- Issue close_status updated to: Fixed
- Issue status updated to: Closed (was: Open)

6 years ago

Log in to comment on this ticket.

Metadata