GithubHelp home page GithubHelp logo

windows support about uvicorn HOT 22 CLOSED

seewindcn avatar seewindcn commented on August 24, 2024 3
windows support

from uvicorn.

Comments (22)

uranusjr avatar uranusjr commented on August 24, 2024 2

Can confirm uvicorn now works out of the package as of 0.2.22 🕺

from uvicorn.

uranusjr avatar uranusjr commented on August 24, 2024 1

Some additional information.

Running with Python 3.7, httptools does not require me the whole Visual Studio to build. Minimal VS 2017 Build Tools setup (toolkit v14.1, CRT SDK, and Windows 10 SDK) is enough for me to get it working. I didn’t test, but imagine the same would apply for 3.6 (which also supports VSBT 14.1) and 3.5 (VSBT 14.0 should work here).

Windows detection is straightforward with modern PEP 508 support. A simple change to the uvloop requirement into

"uvloop; platform_system!='Windows'",

And it installs for me 😃

I am not sure what’s the actual requirement of uvloop, but maybe os_name=='posix' or sys_platform!='win32' could be better markers.

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Certainly the latest version (0.2) should, as there's no platform-specific stuff in there.

I don't know if there's any issues or not prior to that (or with 0.2 running under gunicorn) but happy to hear of any issues if you're seeing them

from uvicorn.

seewindcn avatar seewindcn commented on August 24, 2024

I have try to run under windows, there some stuff want to modify:

  1. uvloop no support; want to use the default loop;
  2. signals no support; disable UvicornWorker.init_signals and Server.set_signal_handlers

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

uvloop no support; want to use the default loop;

Okay, that's easy enough to do: --loop asyncio tho we might want to detect windows or pypy, and choose our loop and parser policies accordingly.

See also MagicStack/uvloop#14 and MagicStack/uvloop#62

signals no support; disable UvicornWorker.init_signals and Server.set_signal_handlers

Okay, I've disable them in #122
I've attempted to support catching Ctrl+C through signal.signal, but it's not clear to me if it's sufficient as implemented. (See https://stackoverflow.com/questions/24774980/why-cant-i-catch-sigint-when-asyncio-event-loop-is-running/24775107#24775107)

It's possible that we ought to start a new thread on windows specifically to catch signals.

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Released as 0.2.10.

It'd be hugely helpful for anyone running on windows to try...

uvicorn app:app --loop asyncio

(Use the basic example app in the README to keep everything else simple)

And see if:

  • Does it start up okay now and serve requests? (If not what output do you see?)
  • Does it terminates okay on Ctrl+C events now? (What output do you see? Does nothing happen, or is it a clean termination, or is a python exception displayed?)
  • Can it be terminated by process explorer or whatever?

from uvicorn.

daniil-konovalenko avatar daniil-konovalenko commented on August 24, 2024

Hey @tomchristie, the installation on Windows fails because uvloop does not support Windows at the moment. Is there an option to install uvicorn without uvloop?

I found an ugly workaround of installing uvicorn with --no-dependencies and then installing every dependecy except uvloop manually.
Also worth noting that httptools requires a whole Visual Studio 2015 to build

Test results

I tested it on 64-bit Windows 10 Pro 1803 and Anaconda Python 3.6.5

Does it start up okay now and serve requests? (If not what output do you see?)

Yes, it works pretty well

Does it terminates okay on Ctrl+C events now? (What output do you see? Does nothing happen, or is it a clean termination, or is a python exception displayed?)

Yes, it terminates on Ctrl+C, not without an exception though:

(venv) C:\Users\ddkon\Projects\uvicorn-win-test>uvicorn app:App --loop asyncio
* Uvicorn running on http://127.0.0.1:8000 🦄 (Press CTRL+C to quit)
INFO: Started worker [10504]
INFO: 127.0.0.1 - "GET / HTTP/1.1" 200
INFO: 127.0.0.1 - "GET /favicon.ico HTTP/1.1" 200
INFO: 127.0.0.1 - "GET / HTTP/1.1" 200
INFO: 127.0.0.1 - "GET /favicon.ico HTTP/1.1" 200
INFO: 127.0.0.1 - "GET / HTTP/1.1" 200
INFO: 127.0.0.1 - "GET /favicon.ico HTTP/1.1" 200
INFO: 127.0.0.1 - "GET /what HTTP/1.1" 200
INFO: 127.0.0.1 - "GET /favicon.ico HTTP/1.1" 200
Traceback (most recent call last):
  File "c:\users\ddkon\anaconda3\Lib\runpy.py", line 193, in _run_module_as_main
    "__main__", mod_spec)
  File "c:\users\ddkon\anaconda3\Lib\runpy.py", line 85, in _run_code
    exec(code, run_globals)
  File "C:\Users\ddkon\Projects\uvicorn-win-test\venv\Scripts\uvicorn.exe\__main__.py", line 9, in <module>
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\click\core.py", line 722, in __call__
    return self.main(*args, **kwargs)
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\click\core.py", line 697, in main
    rv = self.invoke(ctx)
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\click\core.py", line 895, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\click\core.py", line 535, in invoke
    return callback(*args, **kwargs)
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\uvicorn\main.py", line 50, in main
    server.run()
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\uvicorn\main.py", line 142, in run
    self.loop.run_forever()
  File "c:\users\ddkon\anaconda3\Lib\asyncio\base_events.py", line 422, in run_forever
    self._run_once()
  File "c:\users\ddkon\anaconda3\Lib\asyncio\base_events.py", line 1396, in _run_once
    event_list = self._selector.select(timeout)
  File "c:\users\ddkon\anaconda3\Lib\selectors.py", line 323, in select
    r, w, _ = self._select(self._readers, self._writers, [], timeout)
  File "c:\users\ddkon\anaconda3\Lib\selectors.py", line 314, in _select
    r, w, x = select.select(r, w, w, timeout)
  File "c:\users\ddkon\projects\uvicorn-win-test\venv\lib\site-packages\uvicorn\main.py", line 145, in handle_exit
    self.logger.warning("Received signal {}. Shutting down.".format(sig.name))
AttributeError: 'int' object has no attribute 'name'

Can it be terminated by process explorer or whatever?

Yes, it is visible in Task Manager and I was able to terminate it from there
image

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Wonderful, thanks so much! 😎😎😎

So ‘pip install uvicorn’ raises an error then?
Will have to think about how to handle that gracefully. Presumably setup.py could detect if it’s being installed on windows and adapt the requirements. (Running with ‘—loop uvloop —http h11’ would make sense.)

The Ctrl-C exception looks easy enough to resolve.

And thanks again, that’s super-helpful!

from uvicorn.

uranusjr avatar uranusjr commented on August 24, 2024

One other installation issue: Currently setup.py uses the built-in open to read README. This would likely cause problems in the majority of Windows machines, where the default system encoding cannot decode the Unicorn emoji. This is not difficult to resolve for a Python 3-only project—simply add encoding='utf8' to open.

Getting past that (I cloned and manually deleted the emoji), you’ll hit the uvloop support problem mentioned previously:

> pip install .\uvicorn\
Processing c:\users\uranusjr\documents\playground\uvicorn-play\uvicorn
Collecting click (from uvicorn==0.2.12)
  Using cached https://files.pythonhosted.org/packages/34/c1/8806f99713ddb993c5366c362b2f908f18269f8d792aff1abfd700775a77/click-6.7-py2.py3-none-any.whl
Collecting h11 (from uvicorn==0.2.12)
  Using cached https://files.pythonhosted.org/packages/f9/f3/8e4cf5fa1a3d8bda942a0b1cf92f87815494216fd439f82eb99073141ba0/h11-0.8.1-py2.py3-none-any.whl
Collecting httptools (from uvicorn==0.2.12)
  Using cached https://files.pythonhosted.org/packages/a3/75/40cdb732e8ef547d9f34ceb83c43ea7188c0ffb719ddc6a1ad160464292d/httptools-0.0.11.tar.gz
Collecting uvloop (from uvicorn==0.2.12)
  Using cached https://files.pythonhosted.org/packages/cd/e5/1492d3a6ee52f261df764eece684513bb8abbe988d4bd3d94093f39e2bea/uvloop-0.11.0.tar.gz
    Complete output from command python setup.py egg_info:
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "C:\Users\uranusjr\AppData\Local\Temp\pip-install-mlbym38h\uvloop\setup.py", line 15, in <module>
        raise RuntimeError('uvloop does not support Windows at the moment')
    RuntimeError: uvloop does not support Windows at the moment

from uvicorn.

daniil-konovalenko avatar daniil-konovalenko commented on August 24, 2024

I'm glad I could help!
Yeah, it does raise an error, such as the one that @uranusjr posted.
I was thinking that it might be a good idea to make uvloop an optional dependency (Yuri Selivanov strongly advises to). What do you think?

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

I’d like the behaviour to be that it’s used by default, but falls back to asyncio gracefully. We’re very close to that now - just need a few tweaks to setup.py and modify the defaulting behaviour in main.py a little

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Okay, I think we should be looking much better now! 👍

Version 0.2.13 released, with fixes from #130

Anyone able to give it a whirl? 😄

from uvicorn.

uranusjr avatar uranusjr commented on August 24, 2024

I would strongly recommend using PEP 508 environment markers to specify dependencies instead. This allows for the same effect (in relatively recent Setuptools and pip), prevents the packager from needing to maintain platform-specific artifacts (e.g. wheels), and has immensely better compatibility with the new trend of locking-aware dependency management tools like Pipenv and Poetry.

The following should be functionality-wise equivalent to the if-elif-else clause:

requirements = [
    'click',
    'h11',
    'websockets>=6.0',
    "httptools; platform_system != 'Windows' and 'CYGWIN' not in platform_system and platform_python_implementation != 'PyPy'",
    "uvloop; platform_system != 'Windows' and 'CYGWIN' not in platform_system and platform_python_implementation != 'PyPy'",
]

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Presumably things are problematic ATM, as we're importing httptools regardless of if it's installed or not.

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

@uranusjr Okay, I could be up for that. Any idea which versions of pip will support it, or if there's likely any other compatibility issues it could introduce?

from uvicorn.

uranusjr avatar uranusjr commented on August 24, 2024

The markers were introduced in Setuptools 36.2.0, released 2017-07-13. This version is officially bundled in ensurepip only after 3.6.5, but all major package managers have picked it up long before that.

Syntax support shouldn’t be a problem as long as the user updates setuptools (or pip, which implies a setuptools update) in a remotely regular basis. (And there is little reason not to, since setuptools maintains backward compatibility next to forever.) Practically I have yet to see anyone actually complain about this.

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Practically I have yet to see anyone actually complain about this.

@uranusjr Okay - Are there any reasonably prominent examples of projects using it? (Just so I can make a call on ubiquity of support) Thanks for all this!

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Treating this as a separate issue, at #135

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

I believe we now have functioning windows support from 0.2.14 onwards.
Confirmation from anyone would be ace! /cc @daniil-konovalenko @uranusjr

from uvicorn.

uranusjr avatar uranusjr commented on August 24, 2024

Running the example in README gives me the following error:

C:\Users\uranusjr\Documents\playground\uvicorn-play
(uvicorn-play) λ python -c "import uvicorn; print(uvicorn.__version__)"
0.2.14

C:\Users\uranusjr\Documents\playground\uvicorn-play
(uvicorn-play) λ uvicorn app:App
Traceback (most recent call last):
  File "C:\Users\uranusjr\AppData\Local\Programs\Python\Python37\Lib\runpy.py", line 193, in _run_module_as_main
    "__main__", mod_spec)
  File "C:\Users\uranusjr\AppData\Local\Programs\Python\Python37\Lib\runpy.py", line 85, in _run_code
    exec(code, run_globals)
  File "C:\Users\uranusjr\Documents\playground\uvicorn-play\.venv\Scripts\uvicorn.exe\__main__.py", line 9, in <module>
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\click\core.py", line 722, in __call__
    return self.main(*args, **kwargs)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\click\core.py", line 697, in main
    rv = self.invoke(ctx)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\click\core.py", line 895, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\click\core.py", line 535, in invoke
    return callback(*args, **kwargs)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\uvicorn\main.py", line 55, in main
    run(app, host, port, http, loop, log_level)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\uvicorn\main.py", line 64, in run
    loop_setup = import_from_string(LOOP_SETUPS[loop])
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\site-packages\uvicorn\importer.py", line 20, in import_from_string
    module = importlib.import_module(module_str)
  File "c:\users\uranusjr\documents\playground\uvicorn-play\.venv\lib\importlib\__init__.py", line 127, in import_module
    return _bootstrap._gcd_import(name[level:], package, level)
  File "<frozen importlib._bootstrap>", line 1006, in _gcd_import
  File "<frozen importlib._bootstrap>", line 983, in _find_and_load
  File "<frozen importlib._bootstrap>", line 953, in _find_and_load_unlocked
  File "<frozen importlib._bootstrap>", line 219, in _call_with_frames_removed
  File "<frozen importlib._bootstrap>", line 1006, in _gcd_import
  File "<frozen importlib._bootstrap>", line 983, in _find_and_load
  File "<frozen importlib._bootstrap>", line 965, in _find_and_load_unlocked
ModuleNotFoundError: No module named 'uvicorn.loops'

Didn’t look deep but it seems like a circular import problem?

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

I think we do now have windows support properly enabled again.
Confirmations from anyone would be much appreciated. 😄

(Also any thoughts on CI services that'd allow me to test against this?)

from uvicorn.

tomchristie avatar tomchristie commented on August 24, 2024

Rad! ✨

from uvicorn.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.