We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
ModuleNotFoundError: No module named 'fcntl'
How to reproduce the behaviour
---------
After downloading doccano and trying to start it via `doccano init` I get the following message:

```
doccano init
Traceback (most recent call last):
  File "C:\Users\\AppData\Local\Programs\Python\Python39\Scripts\doccano-script.py", line 33, in <module>
    sys.exit(load_entry_point('doccano==1.4.1', 'console_scripts', 'doccano')())
  File "C:\Users\\AppData\Local\Programs\Python\Python39\Scripts\doccano-script.py", line 25, in importlib_load_entry_point
    return next(matches).load()
  File "c:\users\\appdata\local\programs\python\python39\lib\importlib\metadata.py", line 77, in load
    module = import_module(match.group('module'))
  File "c:\users\\appdata\local\programs\python\python39\lib\importlib\__init__.py", line 127, in import_module
    return _bootstrap._gcd_import(name[level:], package, level)
  File "<frozen importlib._bootstrap>", line 1030, in _gcd_import
  File "<frozen importlib._bootstrap>", line 1007, in _find_and_load
  File "<frozen importlib._bootstrap>", line 986, in _find_and_load_unlocked
  File "<frozen importlib._bootstrap>", line 680, in _load_unlocked
  File "<frozen importlib._bootstrap_external>", line 790, in exec_module
  File "<frozen importlib._bootstrap>", line 228, in _call_with_frames_removed
  File "c:\users\\appdata\local\programs\python\python39\lib\site-packages\backend\cli.py", line 7, in <module>
    import gunicorn.app.base
  File "c:\users\\appdata\local\programs\python\python39\lib\site-packages\gunicorn\app\base.py", line 11, in <module>
    from gunicorn import util
  File "c:\users\\appdata\local\programs\python\python39\lib\site-packages\gunicorn\util.py", line 8, in <module>
    import fcntl
ModuleNotFoundError: No module named 'fcntl' 
```

Your Environment
---------
*   Operating System: Windows 10 1909
*   Python Version Used: 3.9.4
*   When you install doccano: 17.06.2021
*   How did you install doccano (Heroku button etc): `pip install doccano`

Own Research:
----------
Apparently Windows doesn''t support `fcntl`. Therefore nobody that uses Windows can install doccano via pip.


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `setup.py`
Content:
```
1 #!/usr/bin/env python
2 # -*- coding: utf-8 -*-
3 import io
4 import os
5 
6 from setuptools import find_packages, setup
7 
8 NAME = 'doccano'
9 DESCRIPTION = 'doccano, text annotation tool for machine learning practitioners'
10 URL = 'https://github.com/doccano/doccano'
11 EMAIL = 'hiroki.nakayama.py@gmail.com'
12 AUTHOR = 'Hironsan'
13 LICENSE = 'MIT'
14 
15 here = os.path.abspath(os.path.dirname(__file__))
16 with io.open(os.path.join(here, 'README.md'), encoding='utf-8') as f:
17     long_description = '\n' + f.read()
18 
19 required = [
20     'apache-libcloud>=3.2.0',
21     'colour>=0.1.5',
22     'conllu>=4.2.2',
23     'dj-database-url>=0.5.0',
24     'django-cors-headers>=3.5.0',
25     'django-filter>=2.4.0',
26     'django-rest-polymorphic>=0.1.9',
27     'djangorestframework-csv>=2.1.0',
28     'djangorestframework-xml>=2.0.0',
29     'drf-yasg>=1.20.0',
30     'environs>=9.2.0',
31     'furl>=2.1.0',
32     'pyexcel>=0.6.6',
33     'pyexcel-xlsx>=0.6.0',
34     'python-jose>=3.2.0',
35     'seqeval>=1.2.2',
36     'social-auth-app-django>=4.0.0',
37     'whitenoise>=5.2.0',
38     'auto-labeling-pipeline>=0.1.12',
39     'celery>=5.0.5',
40     'dj-rest-auth>=2.1.4',
41     'django-celery-results>=2.0.1',
42     'django-drf-filepond>=0.3.0',
43     'sqlalchemy>=1.4.7',
44     'gunicorn>=20.1.0',
45 ]
46 
47 setup(
48     name=NAME,
49     use_scm_version=True,
50     setup_requires=['setuptools_scm'],
51     description=DESCRIPTION,
52     long_description=long_description,
53     long_description_content_type='text/markdown',
54     author=AUTHOR,
55     author_email=EMAIL,
56     url=URL,
57     packages=find_packages(exclude=('*.tests',)),
58     entry_points={
59         'console_scripts': [
60             'doccano = backend.cli:main'
61         ]
62     },
63     install_requires=required,
64     extras_require={
65         'postgresql': ['psycopg2-binary>=2.8.6'],
66         'mssql': ['django-mssql-backend>=2.8.1'],
67     },
68     include_package_data=True,
69     license=LICENSE,
70     classifiers=[
71         'License :: OSI Approved :: MIT License',
72         'Programming Language :: Python',
73         'Programming Language :: Python :: 3.6',
74         'Programming Language :: Python :: 3.7',
75         'Programming Language :: Python :: 3.8',
76         'Programming Language :: Python :: Implementation :: CPython',
77         'Programming Language :: Python :: Implementation :: PyPy'
78     ],
79 )
80
```

Path: `backend/cli.py`
Content:
```
1 import argparse
2 import multiprocessing
3 import os
4 import subprocess
5 import sys
6 
7 import gunicorn.app.base
8 import gunicorn.util
9 
10 from .app.celery import app
11 
12 base = os.path.abspath(os.path.dirname(__file__))
13 manage_path = os.path.join(base, 'manage.py')
14 parser = argparse.ArgumentParser(description='doccano, text annotation for machine learning practitioners.')
15 
16 
17 def number_of_workers():
18     return (multiprocessing.cpu_count() * 2) + 1
19 
20 
21 class StandaloneApplication(gunicorn.app.base.BaseApplication):
22 
23     def __init__(self, options=None):
24         self.options = options or {}
25         super().__init__()
26 
27     def load_config(self):
28         config = {key: value for key, value in self.options.items()
29                   if key in self.cfg.settings and value is not None}
30         for key, value in config.items():
31             self.cfg.set(key.lower(), value)
32 
33     def load(self):
34         sys.path.append(base)
35         return gunicorn.util.import_app('app.wsgi')
36 
37 
38 def command_db_init(args):
39     print('Setup Database.')
40     subprocess.call([sys.executable, manage_path, 'wait_for_db'], shell=False)
41     subprocess.call([sys.executable, manage_path, 'migrate'], shell=False)
42     subprocess.call([sys.executable, manage_path, 'create_roles'], shell=False)
43 
44 
45 def command_user_create(args):
46     print('Create admin user.')
47     subprocess.call([sys.executable, manage_path, 'create_admin',
48                      '--username', args.username,
49                      '--password', args.password,
50                      '--email', args.email,
51                      '--noinput'], shell=False)
52 
53 
54 def command_run_webserver(args):
55     print(f'Starting server with port {args.port}.')
56     options = {
57         'bind': '%s:%s' % ('0.0.0.0', args.port),
58         'workers': number_of_workers(),
59         'chdir': base
60     }
61     StandaloneApplication(options).run()
62 
63 
64 def command_run_task_queue(args):
65     print('Starting task queue.')
66     app.worker_main(
67         argv=[
68             '--app=app',
69             '--workdir={}'.format(base),
70             'worker',
71             '--loglevel=info',
72             '--concurrency={}'.format(args.concurrency),
73         ]
74     )
75 
76 
77 def command_help(args):
78     print(parser.parse_args([args.command, '--help']))
79 
80 
81 def main():
82     # Create a command line parser.
83     subparsers = parser.add_subparsers()
84 
85     # Create a parser for db initialization.
86     parser_init = subparsers.add_parser('init', help='see `init -h`')
87 
88     parser_init.set_defaults(handler=command_db_init)
89 
90     # Create a parser for user creation.
91     parser_create_user = subparsers.add_parser('createuser', help='see `createuser -h`')
92     parser_create_user.add_argument('--username', type=str, default='admin', help='admin username')
93     parser_create_user.add_argument('--password', type=str, default='password', help='admin password')
94     parser_create_user.add_argument('--email', type=str, default='example@example.com', help='admin email')
95     parser_create_user.set_defaults(handler=command_user_create)
96 
97     # Create a parser for web server.
98     parser_server = subparsers.add_parser('webserver', help='see `webserver -h`')
99     parser_server.add_argument('--port', type=int, default=8000, help='port number')
100     parser_server.set_defaults(handler=command_run_webserver)
101 
102     # Create a parser for task queue.
103     parser_queue = subparsers.add_parser('task', help='see `task -h`')
104     parser_queue.add_argument('--concurrency', type=int, default=2, help='concurrency')
105     parser_queue.set_defaults(handler=command_run_task_queue)
106 
107     # Create a parser for help.
108     parser_help = subparsers.add_parser('help', help='see `help -h`')
109     parser_help.add_argument('command', help='command name which help is shown')
110     parser_help.set_defaults(handler=command_help)
111 
112     # Dispatch handler.
113     args = parser.parse_args()
114     if hasattr(args, 'handler'):
115         args.handler(args)
116     else:
117         # If specified unknown command, show help.
118         parser.print_help()
119 
120 
121 if __name__ == '__main__':
122     main()
123
```
--- 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/backend/cli.py b/backend/cli.py
--- a/backend/cli.py
+++ b/backend/cli.py
@@ -1,15 +1,13 @@
 import argparse
 import multiprocessing
 import os
+import platform
 import subprocess
 import sys
 
-import gunicorn.app.base
-import gunicorn.util
-
 from .app.celery import app
-
 base = os.path.abspath(os.path.dirname(__file__))
+sys.path.append(base)
 manage_path = os.path.join(base, 'manage.py')
 parser = argparse.ArgumentParser(description='doccano, text annotation for machine learning practitioners.')
 
@@ -18,21 +16,37 @@
     return (multiprocessing.cpu_count() * 2) + 1
 
 
-class StandaloneApplication(gunicorn.app.base.BaseApplication):
+def run_on_nix(args):
+    import gunicorn.app.base
+    import gunicorn.util
+
+    class StandaloneApplication(gunicorn.app.base.BaseApplication):
 
-    def __init__(self, options=None):
-        self.options = options or {}
-        super().__init__()
+        def __init__(self, options=None):
+            self.options = options or {}
+            super().__init__()
 
-    def load_config(self):
-        config = {key: value for key, value in self.options.items()
-                  if key in self.cfg.settings and value is not None}
-        for key, value in config.items():
-            self.cfg.set(key.lower(), value)
+        def load_config(self):
+            config = {key: value for key, value in self.options.items()
+                      if key in self.cfg.settings and value is not None}
+            for key, value in config.items():
+                self.cfg.set(key.lower(), value)
 
-    def load(self):
-        sys.path.append(base)
-        return gunicorn.util.import_app('app.wsgi')
+        def load(self):
+            return gunicorn.util.import_app('app.wsgi')
+
+    options = {
+        'bind': '%s:%s' % ('0.0.0.0', args.port),
+        'workers': number_of_workers(),
+        'chdir': base
+    }
+    StandaloneApplication(options).run()
+
+
+def run_on_windows(args):
+    from waitress import serve
+    from app.wsgi import application
+    serve(application, port=args.port)
 
 
 def command_db_init(args):
@@ -53,12 +67,10 @@
 
 def command_run_webserver(args):
     print(f'Starting server with port {args.port}.')
-    options = {
-        'bind': '%s:%s' % ('0.0.0.0', args.port),
-        'workers': number_of_workers(),
-        'chdir': base
-    }
-    StandaloneApplication(options).run()
+    if platform.system() == 'Windows':
+        run_on_windows(args)
+    else:
+        run_on_nix(args)
 
 
 def command_run_task_queue(args):
diff --git a/setup.py b/setup.py
--- a/setup.py
+++ b/setup.py
@@ -42,6 +42,7 @@
     'django-drf-filepond>=0.3.0',
     'sqlalchemy>=1.4.7',
     'gunicorn>=20.1.0',
+    'waitress>=2.0.0',
 ]
 
 setup(

{"golden_diff": "diff --git a/backend/cli.py b/backend/cli.py\n--- a/backend/cli.py\n+++ b/backend/cli.py\n@@ -1,15 +1,13 @@\n import argparse\n import multiprocessing\n import os\n+import platform\n import subprocess\n import sys\n \n-import gunicorn.app.base\n-import gunicorn.util\n-\n from .app.celery import app\n-\n base = os.path.abspath(os.path.dirname(__file__))\n+sys.path.append(base)\n manage_path = os.path.join(base, 'manage.py')\n parser = argparse.ArgumentParser(description='doccano, text annotation for machine learning practitioners.')\n \n@@ -18,21 +16,37 @@\n     return (multiprocessing.cpu_count() * 2) + 1\n \n \n-class StandaloneApplication(gunicorn.app.base.BaseApplication):\n+def run_on_nix(args):\n+    import gunicorn.app.base\n+    import gunicorn.util\n+\n+    class StandaloneApplication(gunicorn.app.base.BaseApplication):\n \n-    def __init__(self, options=None):\n-        self.options = options or {}\n-        super().__init__()\n+        def __init__(self, options=None):\n+            self.options = options or {}\n+            super().__init__()\n \n-    def load_config(self):\n-        config = {key: value for key, value in self.options.items()\n-                  if key in self.cfg.settings and value is not None}\n-        for key, value in config.items():\n-            self.cfg.set(key.lower(), value)\n+        def load_config(self):\n+            config = {key: value for key, value in self.options.items()\n+                      if key in self.cfg.settings and value is not None}\n+            for key, value in config.items():\n+                self.cfg.set(key.lower(), value)\n \n-    def load(self):\n-        sys.path.append(base)\n-        return gunicorn.util.import_app('app.wsgi')\n+        def load(self):\n+            return gunicorn.util.import_app('app.wsgi')\n+\n+    options = {\n+        'bind': '%s:%s' % ('0.0.0.0', args.port),\n+        'workers': number_of_workers(),\n+        'chdir': base\n+    }\n+    StandaloneApplication(options).run()\n+\n+\n+def run_on_windows(args):\n+    from waitress import serve\n+    from app.wsgi import application\n+    serve(application, port=args.port)\n \n \n def command_db_init(args):\n@@ -53,12 +67,10 @@\n \n def command_run_webserver(args):\n     print(f'Starting server with port {args.port}.')\n-    options = {\n-        'bind': '%s:%s' % ('0.0.0.0', args.port),\n-        'workers': number_of_workers(),\n-        'chdir': base\n-    }\n-    StandaloneApplication(options).run()\n+    if platform.system() == 'Windows':\n+        run_on_windows(args)\n+    else:\n+        run_on_nix(args)\n \n \n def command_run_task_queue(args):\ndiff --git a/setup.py b/setup.py\n--- a/setup.py\n+++ b/setup.py\n@@ -42,6 +42,7 @@\n     'django-drf-filepond>=0.3.0',\n     'sqlalchemy>=1.4.7',\n     'gunicorn>=20.1.0',\n+    'waitress>=2.0.0',\n ]\n \n setup(\n", "issue": "ModuleNotFoundError: No module named 'fcntl'\nHow to reproduce the behaviour\r\n---------\r\nAfter downloading doccano and trying to start it via `doccano init` I get the following message:\r\n\r\n```\r\ndoccano init\r\nTraceback (most recent call last):\r\n  File \"C:\\Users\\\\AppData\\Local\\Programs\\Python\\Python39\\Scripts\\doccano-script.py\", line 33, in <module>\r\n    sys.exit(load_entry_point('doccano==1.4.1', 'console_scripts', 'doccano')())\r\n  File \"C:\\Users\\\\AppData\\Local\\Programs\\Python\\Python39\\Scripts\\doccano-script.py\", line 25, in importlib_load_entry_point\r\n    return next(matches).load()\r\n  File \"c:\\users\\\\appdata\\local\\programs\\python\\python39\\lib\\importlib\\metadata.py\", line 77, in load\r\n    module = import_module(match.group('module'))\r\n  File \"c:\\users\\\\appdata\\local\\programs\\python\\python39\\lib\\importlib\\__init__.py\", line 127, in import_module\r\n    return _bootstrap._gcd_import(name[level:], package, level)\r\n  File \"<frozen importlib._bootstrap>\", line 1030, in _gcd_import\r\n  File \"<frozen importlib._bootstrap>\", line 1007, in _find_and_load\r\n  File \"<frozen importlib._bootstrap>\", line 986, in _find_and_load_unlocked\r\n  File \"<frozen importlib._bootstrap>\", line 680, in _load_unlocked\r\n  File \"<frozen importlib._bootstrap_external>\", line 790, in exec_module\r\n  File \"<frozen importlib._bootstrap>\", line 228, in _call_with_frames_removed\r\n  File \"c:\\users\\\\appdata\\local\\programs\\python\\python39\\lib\\site-packages\\backend\\cli.py\", line 7, in <module>\r\n    import gunicorn.app.base\r\n  File \"c:\\users\\\\appdata\\local\\programs\\python\\python39\\lib\\site-packages\\gunicorn\\app\\base.py\", line 11, in <module>\r\n    from gunicorn import util\r\n  File \"c:\\users\\\\appdata\\local\\programs\\python\\python39\\lib\\site-packages\\gunicorn\\util.py\", line 8, in <module>\r\n    import fcntl\r\nModuleNotFoundError: No module named 'fcntl' \r\n```\r\n\r\nYour Environment\r\n---------\r\n*   Operating System: Windows 10 1909\r\n*   Python Version Used: 3.9.4\r\n*   When you install doccano: 17.06.2021\r\n*   How did you install doccano (Heroku button etc): `pip install doccano`\r\n\r\nOwn Research:\r\n----------\r\nApparently Windows doesn''t support `fcntl`. Therefore nobody that uses Windows can install doccano via pip.\r\n\n", "before_files": [{"content": "#!/usr/bin/env python\n# -*- coding: utf-8 -*-\nimport io\nimport os\n\nfrom setuptools import find_packages, setup\n\nNAME = 'doccano'\nDESCRIPTION = 'doccano, text annotation tool for machine learning practitioners'\nURL = 'https://github.com/doccano/doccano'\nEMAIL = 'hiroki.nakayama.py@gmail.com'\nAUTHOR = 'Hironsan'\nLICENSE = 'MIT'\n\nhere = os.path.abspath(os.path.dirname(__file__))\nwith io.open(os.path.join(here, 'README.md'), encoding='utf-8') as f:\n    long_description = '\\n' + f.read()\n\nrequired = [\n    'apache-libcloud>=3.2.0',\n    'colour>=0.1.5',\n    'conllu>=4.2.2',\n    'dj-database-url>=0.5.0',\n    'django-cors-headers>=3.5.0',\n    'django-filter>=2.4.0',\n    'django-rest-polymorphic>=0.1.9',\n    'djangorestframework-csv>=2.1.0',\n    'djangorestframework-xml>=2.0.0',\n    'drf-yasg>=1.20.0',\n    'environs>=9.2.0',\n    'furl>=2.1.0',\n    'pyexcel>=0.6.6',\n    'pyexcel-xlsx>=0.6.0',\n    'python-jose>=3.2.0',\n    'seqeval>=1.2.2',\n    'social-auth-app-django>=4.0.0',\n    'whitenoise>=5.2.0',\n    'auto-labeling-pipeline>=0.1.12',\n    'celery>=5.0.5',\n    'dj-rest-auth>=2.1.4',\n    'django-celery-results>=2.0.1',\n    'django-drf-filepond>=0.3.0',\n    'sqlalchemy>=1.4.7',\n    'gunicorn>=20.1.0',\n]\n\nsetup(\n    name=NAME,\n    use_scm_version=True,\n    setup_requires=['setuptools_scm'],\n    description=DESCRIPTION,\n    long_description=long_description,\n    long_description_content_type='text/markdown',\n    author=AUTHOR,\n    author_email=EMAIL,\n    url=URL,\n    packages=find_packages(exclude=('*.tests',)),\n    entry_points={\n        'console_scripts': [\n            'doccano = backend.cli:main'\n        ]\n    },\n    install_requires=required,\n    extras_require={\n        'postgresql': ['psycopg2-binary>=2.8.6'],\n        'mssql': ['django-mssql-backend>=2.8.1'],\n    },\n    include_package_data=True,\n    license=LICENSE,\n    classifiers=[\n        'License :: OSI Approved :: MIT License',\n        'Programming Language :: Python',\n        'Programming Language :: Python :: 3.6',\n        'Programming Language :: Python :: 3.7',\n        'Programming Language :: Python :: 3.8',\n        'Programming Language :: Python :: Implementation :: CPython',\n        'Programming Language :: Python :: Implementation :: PyPy'\n    ],\n)\n", "path": "setup.py"}, {"content": "import argparse\nimport multiprocessing\nimport os\nimport subprocess\nimport sys\n\nimport gunicorn.app.base\nimport gunicorn.util\n\nfrom .app.celery import app\n\nbase = os.path.abspath(os.path.dirname(__file__))\nmanage_path = os.path.join(base, 'manage.py')\nparser = argparse.ArgumentParser(description='doccano, text annotation for machine learning practitioners.')\n\n\ndef number_of_workers():\n    return (multiprocessing.cpu_count() * 2) + 1\n\n\nclass StandaloneApplication(gunicorn.app.base.BaseApplication):\n\n    def __init__(self, options=None):\n        self.options = options or {}\n        super().__init__()\n\n    def load_config(self):\n        config = {key: value for key, value in self.options.items()\n                  if key in self.cfg.settings and value is not None}\n        for key, value in config.items():\n            self.cfg.set(key.lower(), value)\n\n    def load(self):\n        sys.path.append(base)\n        return gunicorn.util.import_app('app.wsgi')\n\n\ndef command_db_init(args):\n    print('Setup Database.')\n    subprocess.call([sys.executable, manage_path, 'wait_for_db'], shell=False)\n    subprocess.call([sys.executable, manage_path, 'migrate'], shell=False)\n    subprocess.call([sys.executable, manage_path, 'create_roles'], shell=False)\n\n\ndef command_user_create(args):\n    print('Create admin user.')\n    subprocess.call([sys.executable, manage_path, 'create_admin',\n                     '--username', args.username,\n                     '--password', args.password,\n                     '--email', args.email,\n                     '--noinput'], shell=False)\n\n\ndef command_run_webserver(args):\n    print(f'Starting server with port {args.port}.')\n    options = {\n        'bind': '%s:%s' % ('0.0.0.0', args.port),\n        'workers': number_of_workers(),\n        'chdir': base\n    }\n    StandaloneApplication(options).run()\n\n\ndef command_run_task_queue(args):\n    print('Starting task queue.')\n    app.worker_main(\n        argv=[\n            '--app=app',\n            '--workdir={}'.format(base),\n            'worker',\n            '--loglevel=info',\n            '--concurrency={}'.format(args.concurrency),\n        ]\n    )\n\n\ndef command_help(args):\n    print(parser.parse_args([args.command, '--help']))\n\n\ndef main():\n    # Create a command line parser.\n    subparsers = parser.add_subparsers()\n\n    # Create a parser for db initialization.\n    parser_init = subparsers.add_parser('init', help='see `init -h`')\n\n    parser_init.set_defaults(handler=command_db_init)\n\n    # Create a parser for user creation.\n    parser_create_user = subparsers.add_parser('createuser', help='see `createuser -h`')\n    parser_create_user.add_argument('--username', type=str, default='admin', help='admin username')\n    parser_create_user.add_argument('--password', type=str, default='password', help='admin password')\n    parser_create_user.add_argument('--email', type=str, default='example@example.com', help='admin email')\n    parser_create_user.set_defaults(handler=command_user_create)\n\n    # Create a parser for web server.\n    parser_server = subparsers.add_parser('webserver', help='see `webserver -h`')\n    parser_server.add_argument('--port', type=int, default=8000, help='port number')\n    parser_server.set_defaults(handler=command_run_webserver)\n\n    # Create a parser for task queue.\n    parser_queue = subparsers.add_parser('task', help='see `task -h`')\n    parser_queue.add_argument('--concurrency', type=int, default=2, help='concurrency')\n    parser_queue.set_defaults(handler=command_run_task_queue)\n\n    # Create a parser for help.\n    parser_help = subparsers.add_parser('help', help='see `help -h`')\n    parser_help.add_argument('command', help='command name which help is shown')\n    parser_help.set_defaults(handler=command_help)\n\n    # Dispatch handler.\n    args = parser.parse_args()\n    if hasattr(args, 'handler'):\n        args.handler(args)\n    else:\n        # If specified unknown command, show help.\n        parser.print_help()\n\n\nif __name__ == '__main__':\n    main()\n", "path": "backend/cli.py"}], "after_files": [{"content": "#!/usr/bin/env python\n# -*- coding: utf-8 -*-\nimport io\nimport os\n\nfrom setuptools import find_packages, setup\n\nNAME = 'doccano'\nDESCRIPTION = 'doccano, text annotation tool for machine learning practitioners'\nURL = 'https://github.com/doccano/doccano'\nEMAIL = 'hiroki.nakayama.py@gmail.com'\nAUTHOR = 'Hironsan'\nLICENSE = 'MIT'\n\nhere = os.path.abspath(os.path.dirname(__file__))\nwith io.open(os.path.join(here, 'README.md'), encoding='utf-8') as f:\n    long_description = '\\n' + f.read()\n\nrequired = [\n    'apache-libcloud>=3.2.0',\n    'colour>=0.1.5',\n    'conllu>=4.2.2',\n    'dj-database-url>=0.5.0',\n    'django-cors-headers>=3.5.0',\n    'django-filter>=2.4.0',\n    'django-rest-polymorphic>=0.1.9',\n    'djangorestframework-csv>=2.1.0',\n    'djangorestframework-xml>=2.0.0',\n    'drf-yasg>=1.20.0',\n    'environs>=9.2.0',\n    'furl>=2.1.0',\n    'pyexcel>=0.6.6',\n    'pyexcel-xlsx>=0.6.0',\n    'python-jose>=3.2.0',\n    'seqeval>=1.2.2',\n    'social-auth-app-django>=4.0.0',\n    'whitenoise>=5.2.0',\n    'auto-labeling-pipeline>=0.1.12',\n    'celery>=5.0.5',\n    'dj-rest-auth>=2.1.4',\n    'django-celery-results>=2.0.1',\n    'django-drf-filepond>=0.3.0',\n    'sqlalchemy>=1.4.7',\n    'gunicorn>=20.1.0',\n    'waitress>=2.0.0',\n]\n\nsetup(\n    name=NAME,\n    use_scm_version=True,\n    setup_requires=['setuptools_scm'],\n    description=DESCRIPTION,\n    long_description=long_description,\n    long_description_content_type='text/markdown',\n    author=AUTHOR,\n    author_email=EMAIL,\n    url=URL,\n    packages=find_packages(exclude=('*.tests',)),\n    entry_points={\n        'console_scripts': [\n            'doccano = backend.cli:main'\n        ]\n    },\n    install_requires=required,\n    extras_require={\n        'postgresql': ['psycopg2-binary>=2.8.6'],\n        'mssql': ['django-mssql-backend>=2.8.1'],\n    },\n    include_package_data=True,\n    license=LICENSE,\n    classifiers=[\n        'License :: OSI Approved :: MIT License',\n        'Programming Language :: Python',\n        'Programming Language :: Python :: 3.6',\n        'Programming Language :: Python :: 3.7',\n        'Programming Language :: Python :: 3.8',\n        'Programming Language :: Python :: Implementation :: CPython',\n        'Programming Language :: Python :: Implementation :: PyPy'\n    ],\n)\n", "path": "setup.py"}, {"content": "import argparse\nimport multiprocessing\nimport os\nimport platform\nimport subprocess\nimport sys\n\nfrom .app.celery import app\nbase = os.path.abspath(os.path.dirname(__file__))\nsys.path.append(base)\nmanage_path = os.path.join(base, 'manage.py')\nparser = argparse.ArgumentParser(description='doccano, text annotation for machine learning practitioners.')\n\n\ndef number_of_workers():\n    return (multiprocessing.cpu_count() * 2) + 1\n\n\ndef run_on_nix(args):\n    import gunicorn.app.base\n    import gunicorn.util\n\n    class StandaloneApplication(gunicorn.app.base.BaseApplication):\n\n        def __init__(self, options=None):\n            self.options = options or {}\n            super().__init__()\n\n        def load_config(self):\n            config = {key: value for key, value in self.options.items()\n                      if key in self.cfg.settings and value is not None}\n            for key, value in config.items():\n                self.cfg.set(key.lower(), value)\n\n        def load(self):\n            return gunicorn.util.import_app('app.wsgi')\n\n    options = {\n        'bind': '%s:%s' % ('0.0.0.0', args.port),\n        'workers': number_of_workers(),\n        'chdir': base\n    }\n    StandaloneApplication(options).run()\n\n\ndef run_on_windows(args):\n    from waitress import serve\n    from app.wsgi import application\n    serve(application, port=args.port)\n\n\ndef command_db_init(args):\n    print('Setup Database.')\n    subprocess.call([sys.executable, manage_path, 'wait_for_db'], shell=False)\n    subprocess.call([sys.executable, manage_path, 'migrate'], shell=False)\n    subprocess.call([sys.executable, manage_path, 'create_roles'], shell=False)\n\n\ndef command_user_create(args):\n    print('Create admin user.')\n    subprocess.call([sys.executable, manage_path, 'create_admin',\n                     '--username', args.username,\n                     '--password', args.password,\n                     '--email', args.email,\n                     '--noinput'], shell=False)\n\n\ndef command_run_webserver(args):\n    print(f'Starting server with port {args.port}.')\n    if platform.system() == 'Windows':\n        run_on_windows(args)\n    else:\n        run_on_nix(args)\n\n\ndef command_run_task_queue(args):\n    print('Starting task queue.')\n    app.worker_main(\n        argv=[\n            '--app=app',\n            '--workdir={}'.format(base),\n            'worker',\n            '--loglevel=info',\n            '--concurrency={}'.format(args.concurrency),\n        ]\n    )\n\n\ndef command_help(args):\n    print(parser.parse_args([args.command, '--help']))\n\n\ndef main():\n    # Create a command line parser.\n    subparsers = parser.add_subparsers()\n\n    # Create a parser for db initialization.\n    parser_init = subparsers.add_parser('init', help='see `init -h`')\n\n    parser_init.set_defaults(handler=command_db_init)\n\n    # Create a parser for user creation.\n    parser_create_user = subparsers.add_parser('createuser', help='see `createuser -h`')\n    parser_create_user.add_argument('--username', type=str, default='admin', help='admin username')\n    parser_create_user.add_argument('--password', type=str, default='password', help='admin password')\n    parser_create_user.add_argument('--email', type=str, default='example@example.com', help='admin email')\n    parser_create_user.set_defaults(handler=command_user_create)\n\n    # Create a parser for web server.\n    parser_server = subparsers.add_parser('webserver', help='see `webserver -h`')\n    parser_server.add_argument('--port', type=int, default=8000, help='port number')\n    parser_server.set_defaults(handler=command_run_webserver)\n\n    # Create a parser for task queue.\n    parser_queue = subparsers.add_parser('task', help='see `task -h`')\n    parser_queue.add_argument('--concurrency', type=int, default=2, help='concurrency')\n    parser_queue.set_defaults(handler=command_run_task_queue)\n\n    # Create a parser for help.\n    parser_help = subparsers.add_parser('help', help='see `help -h`')\n    parser_help.add_argument('command', help='command name which help is shown')\n    parser_help.set_defaults(handler=command_help)\n\n    # Dispatch handler.\n    args = parser.parse_args()\n    if hasattr(args, 'handler'):\n        args.handler(args)\n    else:\n        # If specified unknown command, show help.\n        parser.print_help()\n\n\nif __name__ == '__main__':\n    main()\n", "path": "backend/cli.py"}]}