Skip to content

http parser implementation based on http-parser #1626

Merged
fafhrd91 merged 19 commits into
masterfrom
parser
Feb 16, 2017
Merged

http parser implementation based on http-parser #1626
fafhrd91 merged 19 commits into
masterfrom
parser

Conversation

@fafhrd91
Copy link
Copy Markdown
Member

added c-based http parser, cython code is based on https://github.com/MagicStack/httptools

it gives ~15-25% increase

Comment thread aiohttp/_parser.pyx Outdated
self._upgraded = True

encoding = None
enc = headers.get(hdrs.CONTENT_ENCODING)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any need to have two variables to reference on content encoding?

Comment thread aiohttp/_parser.pyx
return HttpVersion10
elif parser.http_minor == 1:
return HttpVersion11

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we crash if version will be something weird?

Comment thread aiohttp/_parser.pyx
messages = self._messages
self._messages = []
else:
messages = ()
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

self._messages are list, but here messages becomes a tuple.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i do not want to convert messages into tuple. doesnt really matter

Comment thread aiohttp/_parser.pyx
size_t max_field_size=8190):
self._init(cparser.HTTP_REQUEST, protocol, loop,
max_line_size, max_headers, max_field_size)
#self._proto_on_url = getattr(protocol, 'on_url', None)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

May be drop this?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i've not decided on url, http-parser provides url parsing, should give some more performance, but it requires yarl integration

Comment thread aiohttp/_parser.pyx Outdated
const char *at, size_t length) except -1:
cdef HttpParser pyparser = <HttpParser>parser.data
try:
#pyparser.url = _parse_url(at[:length], length)
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

May be remove this?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same as previous

Comment thread aiohttp/_parser.pyx Outdated
cdef int cb_on_chunk_complete(cparser.http_parser* parser) except -1:
cdef HttpParser pyparser = <HttpParser>parser.data
try:
pass
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Something TBD here?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same

Comment thread aiohttp/_parser.pyx Outdated
cdef class URL:
cdef readonly str schema
cdef readonly str host
cdef readonly object port
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why port is an object?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i have no idea :)
url handling needs some more work

Comment thread aiohttp/server.py Outdated
loop=self._loop))
return
except Exception as exc:
print('exc')
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Debug print.

Comment thread aiohttp/server.py Outdated

# feed payload
else:
if data:
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

elif data?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

good



@pytest.mark.xfail
# @pytest.mark.xfail
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

May be remove all these # pytest.mark.xfail?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i do not understand those tests, i need andrew help

@codecov-io
Copy link
Copy Markdown

codecov-io commented Feb 15, 2017

Codecov Report

❗ No coverage uploaded for pull request base (master@6a3c16a). Click here to learn what that means.
The diff coverage is 84.14%.

@@            Coverage Diff            @@
##             master    #1626   +/-   ##
=========================================
  Coverage          ?   94.61%           
=========================================
  Files             ?       31           
  Lines             ?     7395           
  Branches          ?     1281           
=========================================
  Hits              ?     6997           
  Misses            ?      264           
  Partials          ?      134
Impacted Files Coverage Δ
aiohttp/connector.py 97.5% <ø> (ø)
aiohttp/client_reqrep.py 96.28% <100%> (ø)
aiohttp/web_ws.py 92.18% <100%> (ø)
aiohttp/web_server.py 100% <100%> (ø)
aiohttp/web_urldispatcher.py 98.83% <100%> (ø)
aiohttp/signals.py 100% <100%> (ø)
aiohttp/client.py 88.82% <100%> (ø)
aiohttp/web_middlewares.py 100% <100%> (ø)
aiohttp/web.py 98.74% <100%> (ø)
aiohttp/errors.py 100% <100%> (ø)
... and 9 more

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 6a3c16a...e49b59b. Read the comment docs.

@fafhrd91
Copy link
Copy Markdown
Member Author

added http-parser's url parsing functionality.

on my mac i get ~14.3k rps, ~7k was on 1.3

@fafhrd91
Copy link
Copy Markdown
Member Author

1.2 is slightly faster than 1.3, ~7.3k rps

@fafhrd91
Copy link
Copy Markdown
Member Author

fafhrd91 commented Feb 15, 2017

with all latest changes i could get ~16.2rps

interestingly, __new__ method adds huge overhead.

@fafhrd91
Copy link
Copy Markdown
Member Author

cool, i didn't know about purest_addoption

@fafhrd91
Copy link
Copy Markdown
Member Author

@samuelcolvin added --fast option

@samuelcolvin
Copy link
Copy Markdown
Member

great!

Comment thread aiohttp/test_utils.py Outdated
by setup_test_loop.

"""
if fast is None:
Copy link
Copy Markdown
Member

@samuelcolvin samuelcolvin Feb 15, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this should be

fast |= TESTS_FAST

that way if you're testing with pytest and have AIOHTTP_TESTS_FAST=True but don't supply the --fast argument you get fast tests.

With current setup AIOHTTP_TESTS_FAST has no effect with pytest.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think AIOHTTP_TESTS_FAST is not needed

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fine by me.

@fafhrd91
Copy link
Copy Markdown
Member Author

i modified gunicorn worker to disable access log if access log is not configured

on my mac i got ~60k rps

t_srv.py:

async def intro(request):
    resp = Response(status=200)
    return resp

def init():
    app = Application()
    app.router.add_get('/', intro)
    return app

app = init()

gunicorn command:

>>> python -OO -m gunicorn.app.wsgiapp --worker-class aiohttp.worker.GunicornUVLoopWebWorker t_srv:app --workers 6 -b 127.0.0.1:8080

and wrk command:

wrk -t12 -c400 -d10s http://127.0.0.1:8080/ -s pipeline.lua --latency -- / 16

@fafhrd91 fafhrd91 force-pushed the parser branch 2 times, most recently from ba056e3 to ea68872 Compare February 15, 2017 21:29
@fafhrd91 fafhrd91 force-pushed the parser branch 4 times, most recently from 1f2d965 to a92549e Compare February 15, 2017 23:16
Copy link
Copy Markdown

@nhumrich nhumrich left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🖌

@fafhrd91 fafhrd91 merged commit e49b59b into master Feb 16, 2017
@fafhrd91 fafhrd91 deleted the parser branch February 16, 2017 00:54
@fafhrd91
Copy link
Copy Markdown
Member Author

merged to master

@kxepal if you want to modify cython code, just modify on master

@lock
Copy link
Copy Markdown

lock Bot commented Oct 29, 2019

This thread has been automatically locked since there has not been
any recent activity after it was closed. Please open a new issue for
related bugs.

If you feel like there's important points made in this discussion,
please include those exceprts into that new issue.

@lock lock Bot added the outdated label Oct 29, 2019
@lock lock Bot locked as resolved and limited conversation to collaborators Oct 29, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants