We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
REPL history is lost on (quit)
REPL history is not flushed to disk if the REPL is exited using `(quit)`. 

A workaround is to remember to use `CTRL-D` to exit the REPL.

Would be nice if `(quit)` also worked.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `hy/completer.py`
Content:
```
1 # Copyright 2017 the authors.
2 # This file is part of Hy, which is free software licensed under the Expat
3 # license. See the LICENSE.
4 
5 import contextlib
6 import os
7 import re
8 import sys
9 
10 import hy.macros
11 import hy.compiler
12 from hy._compat import builtins, string_types
13 
14 
15 docomplete = True
16 
17 try:
18     import readline
19 except ImportError:
20     try:
21         import pyreadline.rlmain
22         import pyreadline.unicode_helper  # NOQA
23         import readline
24     except ImportError:
25         docomplete = False
26 
27 if sys.platform == 'darwin' and 'libedit' in readline.__doc__:
28     readline_bind = "bind ^I rl_complete"
29 else:
30     readline_bind = "tab: complete"
31 
32 
33 class Completer(object):
34 
35     def __init__(self, namespace={}):
36         if not isinstance(namespace, dict):
37             raise TypeError('namespace must be a dictionary')
38         self.namespace = namespace
39         self.path = [hy.compiler._compile_table,
40                      builtins.__dict__,
41                      hy.macros._hy_macros[None],
42                      namespace]
43         self.tag_path = [hy.macros._hy_tag[None]]
44         if '__name__' in namespace:
45             module_name = namespace['__name__']
46             self.path.append(hy.macros._hy_macros[module_name])
47             self.tag_path.append(hy.macros._hy_tag[module_name])
48 
49     def attr_matches(self, text):
50         # Borrowed from IPython's completer
51         m = re.match(r"(\S+(\.[\w-]+)*)\.([\w-]*)$", text)
52 
53         if m:
54             expr, attr = m.group(1, 3)
55             attr = attr.replace("-", "_")
56             expr = expr.replace("-", "_")
57         else:
58             return []
59 
60         try:
61             obj = eval(expr, self.namespace)
62             words = dir(obj)
63         except Exception:
64             return []
65 
66         n = len(attr)
67         matches = []
68         for w in words:
69             if w[:n] == attr:
70                 matches.append("{}.{}".format(
71                     expr.replace("_", "-"), w.replace("_", "-")))
72         return matches
73 
74     def global_matches(self, text):
75         matches = []
76         for p in self.path:
77             for k in p.keys():
78                 if isinstance(k, string_types):
79                     k = k.replace("_", "-")
80                     if k.startswith(text):
81                         matches.append(k)
82         return matches
83 
84     def tag_matches(self, text):
85         text = text[1:]
86         matches = []
87         for p in self.tag_path:
88             for k in p.keys():
89                 if isinstance(k, string_types):
90                     if k.startswith(text):
91                         matches.append("#{}".format(k))
92         return matches
93 
94     def complete(self, text, state):
95         if text.startswith("#"):
96             matches = self.tag_matches(text)
97         elif "." in text:
98             matches = self.attr_matches(text)
99         else:
100             matches = self.global_matches(text)
101         try:
102             return matches[state]
103         except IndexError:
104             return None
105 
106 
107 @contextlib.contextmanager
108 def completion(completer=None):
109     delims = "()[]{} "
110     if not completer:
111         completer = Completer()
112 
113     if docomplete:
114         readline.set_completer(completer.complete)
115         readline.set_completer_delims(delims)
116 
117         history = os.path.expanduser("~/.hy-history")
118         readline.parse_and_bind("set blink-matching-paren on")
119 
120         try:
121             readline.read_history_file(history)
122         except IOError:
123             open(history, 'a').close()
124 
125         readline.parse_and_bind(readline_bind)
126 
127     yield
128 
129     if docomplete:
130         readline.write_history_file(history)
131
```
--- 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/hy/completer.py b/hy/completer.py
--- a/hy/completer.py
+++ b/hy/completer.py
@@ -124,7 +124,8 @@
 
         readline.parse_and_bind(readline_bind)
 
-    yield
-
-    if docomplete:
-        readline.write_history_file(history)
+    try:
+        yield
+    finally:
+        if docomplete:
+            readline.write_history_file(history)

{"golden_diff": "diff --git a/hy/completer.py b/hy/completer.py\n--- a/hy/completer.py\n+++ b/hy/completer.py\n@@ -124,7 +124,8 @@\n \n         readline.parse_and_bind(readline_bind)\n \n-    yield\n-\n-    if docomplete:\n-        readline.write_history_file(history)\n+    try:\n+        yield\n+    finally:\n+        if docomplete:\n+            readline.write_history_file(history)\n", "issue": "REPL history is lost on (quit)\nREPL history is not flushed to disk if the REPL is exited using `(quit)`. \r\n\r\nA workaround is to remember to use `CTRL-D` to exit the REPL.\r\n\r\nWould be nice if `(quit)` also worked.\n", "before_files": [{"content": "# Copyright 2017 the authors.\n# This file is part of Hy, which is free software licensed under the Expat\n# license. See the LICENSE.\n\nimport contextlib\nimport os\nimport re\nimport sys\n\nimport hy.macros\nimport hy.compiler\nfrom hy._compat import builtins, string_types\n\n\ndocomplete = True\n\ntry:\n    import readline\nexcept ImportError:\n    try:\n        import pyreadline.rlmain\n        import pyreadline.unicode_helper  # NOQA\n        import readline\n    except ImportError:\n        docomplete = False\n\nif sys.platform == 'darwin' and 'libedit' in readline.__doc__:\n    readline_bind = \"bind ^I rl_complete\"\nelse:\n    readline_bind = \"tab: complete\"\n\n\nclass Completer(object):\n\n    def __init__(self, namespace={}):\n        if not isinstance(namespace, dict):\n            raise TypeError('namespace must be a dictionary')\n        self.namespace = namespace\n        self.path = [hy.compiler._compile_table,\n                     builtins.__dict__,\n                     hy.macros._hy_macros[None],\n                     namespace]\n        self.tag_path = [hy.macros._hy_tag[None]]\n        if '__name__' in namespace:\n            module_name = namespace['__name__']\n            self.path.append(hy.macros._hy_macros[module_name])\n            self.tag_path.append(hy.macros._hy_tag[module_name])\n\n    def attr_matches(self, text):\n        # Borrowed from IPython's completer\n        m = re.match(r\"(\\S+(\\.[\\w-]+)*)\\.([\\w-]*)$\", text)\n\n        if m:\n            expr, attr = m.group(1, 3)\n            attr = attr.replace(\"-\", \"_\")\n            expr = expr.replace(\"-\", \"_\")\n        else:\n            return []\n\n        try:\n            obj = eval(expr, self.namespace)\n            words = dir(obj)\n        except Exception:\n            return []\n\n        n = len(attr)\n        matches = []\n        for w in words:\n            if w[:n] == attr:\n                matches.append(\"{}.{}\".format(\n                    expr.replace(\"_\", \"-\"), w.replace(\"_\", \"-\")))\n        return matches\n\n    def global_matches(self, text):\n        matches = []\n        for p in self.path:\n            for k in p.keys():\n                if isinstance(k, string_types):\n                    k = k.replace(\"_\", \"-\")\n                    if k.startswith(text):\n                        matches.append(k)\n        return matches\n\n    def tag_matches(self, text):\n        text = text[1:]\n        matches = []\n        for p in self.tag_path:\n            for k in p.keys():\n                if isinstance(k, string_types):\n                    if k.startswith(text):\n                        matches.append(\"#{}\".format(k))\n        return matches\n\n    def complete(self, text, state):\n        if text.startswith(\"#\"):\n            matches = self.tag_matches(text)\n        elif \".\" in text:\n            matches = self.attr_matches(text)\n        else:\n            matches = self.global_matches(text)\n        try:\n            return matches[state]\n        except IndexError:\n            return None\n\n\n@contextlib.contextmanager\ndef completion(completer=None):\n    delims = \"()[]{} \"\n    if not completer:\n        completer = Completer()\n\n    if docomplete:\n        readline.set_completer(completer.complete)\n        readline.set_completer_delims(delims)\n\n        history = os.path.expanduser(\"~/.hy-history\")\n        readline.parse_and_bind(\"set blink-matching-paren on\")\n\n        try:\n            readline.read_history_file(history)\n        except IOError:\n            open(history, 'a').close()\n\n        readline.parse_and_bind(readline_bind)\n\n    yield\n\n    if docomplete:\n        readline.write_history_file(history)\n", "path": "hy/completer.py"}], "after_files": [{"content": "# Copyright 2017 the authors.\n# This file is part of Hy, which is free software licensed under the Expat\n# license. See the LICENSE.\n\nimport contextlib\nimport os\nimport re\nimport sys\n\nimport hy.macros\nimport hy.compiler\nfrom hy._compat import builtins, string_types\n\n\ndocomplete = True\n\ntry:\n    import readline\nexcept ImportError:\n    try:\n        import pyreadline.rlmain\n        import pyreadline.unicode_helper  # NOQA\n        import readline\n    except ImportError:\n        docomplete = False\n\nif sys.platform == 'darwin' and 'libedit' in readline.__doc__:\n    readline_bind = \"bind ^I rl_complete\"\nelse:\n    readline_bind = \"tab: complete\"\n\n\nclass Completer(object):\n\n    def __init__(self, namespace={}):\n        if not isinstance(namespace, dict):\n            raise TypeError('namespace must be a dictionary')\n        self.namespace = namespace\n        self.path = [hy.compiler._compile_table,\n                     builtins.__dict__,\n                     hy.macros._hy_macros[None],\n                     namespace]\n        self.tag_path = [hy.macros._hy_tag[None]]\n        if '__name__' in namespace:\n            module_name = namespace['__name__']\n            self.path.append(hy.macros._hy_macros[module_name])\n            self.tag_path.append(hy.macros._hy_tag[module_name])\n\n    def attr_matches(self, text):\n        # Borrowed from IPython's completer\n        m = re.match(r\"(\\S+(\\.[\\w-]+)*)\\.([\\w-]*)$\", text)\n\n        if m:\n            expr, attr = m.group(1, 3)\n            attr = attr.replace(\"-\", \"_\")\n            expr = expr.replace(\"-\", \"_\")\n        else:\n            return []\n\n        try:\n            obj = eval(expr, self.namespace)\n            words = dir(obj)\n        except Exception:\n            return []\n\n        n = len(attr)\n        matches = []\n        for w in words:\n            if w[:n] == attr:\n                matches.append(\"{}.{}\".format(\n                    expr.replace(\"_\", \"-\"), w.replace(\"_\", \"-\")))\n        return matches\n\n    def global_matches(self, text):\n        matches = []\n        for p in self.path:\n            for k in p.keys():\n                if isinstance(k, string_types):\n                    k = k.replace(\"_\", \"-\")\n                    if k.startswith(text):\n                        matches.append(k)\n        return matches\n\n    def tag_matches(self, text):\n        text = text[1:]\n        matches = []\n        for p in self.tag_path:\n            for k in p.keys():\n                if isinstance(k, string_types):\n                    if k.startswith(text):\n                        matches.append(\"#{}\".format(k))\n        return matches\n\n    def complete(self, text, state):\n        if text.startswith(\"#\"):\n            matches = self.tag_matches(text)\n        elif \".\" in text:\n            matches = self.attr_matches(text)\n        else:\n            matches = self.global_matches(text)\n        try:\n            return matches[state]\n        except IndexError:\n            return None\n\n\n@contextlib.contextmanager\ndef completion(completer=None):\n    delims = \"()[]{} \"\n    if not completer:\n        completer = Completer()\n\n    if docomplete:\n        readline.set_completer(completer.complete)\n        readline.set_completer_delims(delims)\n\n        history = os.path.expanduser(\"~/.hy-history\")\n        readline.parse_and_bind(\"set blink-matching-paren on\")\n\n        try:\n            readline.read_history_file(history)\n        except IOError:\n            open(history, 'a').close()\n\n        readline.parse_and_bind(readline_bind)\n\n    try:\n        yield\n    finally:\n        if docomplete:\n            readline.write_history_file(history)\n", "path": "hy/completer.py"}]}