We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
[LSP-elm] Documentation popup is no logner visible when "More" link is clicked
* OS and language server - Ubunutu 20.04, LSP-elm, ST 4085 
* How you installed LSP - git, latest st-4000-exploration

When clicking the `More` link in the AC popup,
I expect to see a documentation popup.
But I see nothing. 

This commit introduced this behavior 19df9e19afeb0f32064a8b7e3a11ebaa4254f63c
If I checkout the commit before 19df9e19afeb0f32064a8b7e3a11ebaa4254f63c, everything works as expected.

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `plugin/completion.py`
Content:
```
1 import mdpopups
2 import sublime
3 import sublime_plugin
4 import webbrowser
5 from .core.css import css
6 from .core.logging import debug
7 from .core.edit import parse_text_edit
8 from .core.protocol import Request, InsertTextFormat, Range
9 from .core.registry import LspTextCommand
10 from .core.typing import Any, List, Dict, Optional, Generator, Union
11 from .core.views import FORMAT_STRING, FORMAT_MARKUP_CONTENT, minihtml
12 from .core.views import range_to_region
13 
14 
15 class LspResolveDocsCommand(LspTextCommand):
16 
17     completions = []  # type: List[Dict[str, Any]]
18 
19     def run(self, edit: sublime.Edit, index: int, event: Optional[dict] = None) -> None:
20         item = self.completions[index]
21         detail = self.format_documentation(item.get('detail') or "")
22         documentation = self.format_documentation(item.get("documentation") or "")
23         # don't show the detail in the cooperate AC popup if it is already shown in the AC details filed.
24         self.is_detail_shown = bool(detail)
25         if not detail or not documentation:
26             # To make sure that the detail or documentation fields doesn't exist we need to resove the completion item.
27             # If those fields appear after the item is resolved we show them in the popup.
28             self.do_resolve(item)
29         else:
30             minihtml_content = self.get_content(documentation, detail)
31             self.show_popup(minihtml_content)
32 
33     def format_documentation(self, content: Union[str, Dict[str, str]]) -> str:
34         return minihtml(self.view, content, allowed_formats=FORMAT_STRING | FORMAT_MARKUP_CONTENT)
35 
36     def get_content(self, documentation: str, detail: str) -> str:
37         content = ""
38         if detail and not self.is_detail_shown:
39             content += "<div class='highlight'>{}</div>".format(detail)
40         if documentation:
41             content += "<div>{}</div>".format(documentation)
42         return content
43 
44     def show_popup(self, minihtml_content: str) -> None:
45         viewport_width = self.view.viewport_extent()[0]
46         mdpopups.show_popup(
47             self.view,
48             minihtml_content,
49             flags=sublime.COOPERATE_WITH_AUTO_COMPLETE,
50             css=css().popups,
51             wrapper_class=css().popups_classname,
52             max_width=viewport_width,
53             on_navigate=self.on_navigate
54         )
55 
56     def on_navigate(self, url: str) -> None:
57         webbrowser.open(url)
58 
59     def do_resolve(self, item: dict) -> None:
60         session = self.best_session('completionProvider.resolveProvider')
61         if session:
62             session.send_request(
63                 Request.resolveCompletionItem(item),
64                 lambda res: self.handle_resolve_response(res))
65 
66     def handle_resolve_response(self, item: Optional[dict]) -> None:
67         detail = ""
68         documentation = ""
69         if item:
70             detail = self.format_documentation(item.get('detail') or "")
71             documentation = self.format_documentation(item.get("documentation") or "")
72         if not documentation:
73             documentation = self.format_documentation({"kind": "markdown", "value": "*No documentation available.*"})
74         minihtml_content = self.get_content(documentation, detail)
75         show = self.update_popup if self.view.is_popup_visible() else self.show_popup
76         # NOTE: Update/show popups from the main thread, or else the popup might make the AC widget disappear.
77         sublime.set_timeout(lambda: show(minihtml_content))
78 
79     def update_popup(self, minihtml_content: str) -> None:
80         mdpopups.update_popup(
81             self.view,
82             minihtml_content,
83             css=css().popups,
84             wrapper_class=css().popups_classname,
85         )
86 
87 
88 class LspCompleteCommand(sublime_plugin.TextCommand):
89 
90     def epilogue(self, item: Dict[str, Any]) -> None:
91         additional_edits = item.get('additionalTextEdits')
92         if additional_edits:
93             edits = [parse_text_edit(additional_edit) for additional_edit in additional_edits]
94             self.view.run_command("lsp_apply_document_edit", {'changes': edits})
95         command = item.get("command")
96         if command:
97             debug('Running server command "{}" for view {}'.format(command, self.view.id()))
98             self.view.run_command("lsp_execute", {"command_name": command})
99 
100 
101 class LspCompleteInsertTextCommand(LspCompleteCommand):
102 
103     def run(self, edit: sublime.Edit, **item: Any) -> None:
104         insert_text = item.get("insertText") or item["label"]
105         if item.get("insertTextFormat", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:
106             self.view.run_command("insert_snippet", {"contents": insert_text})
107         else:
108             self.view.run_command("insert", {"characters": insert_text})
109         self.epilogue(item)
110 
111 
112 class LspCompleteTextEditCommand(LspCompleteCommand):
113 
114     def run(self, edit: sublime.Edit, **item: Any) -> None:
115         text_edit = item["textEdit"]
116         new_text = text_edit['newText']
117         edit_region = range_to_region(Range.from_lsp(text_edit['range']), self.view)
118         if item.get("insertTextFormat", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:
119             for region in self.translated_regions(edit_region):
120                 self.view.erase(edit, region)
121             self.view.run_command("insert_snippet", {"contents": new_text})
122         else:
123             for region in self.translated_regions(edit_region):
124                 # NOTE: Cannot do .replace, because ST will select the replacement.
125                 self.view.erase(edit, region)
126                 self.view.insert(edit, region.a, new_text)
127         self.epilogue(item)
128 
129     def translated_regions(self, edit_region: sublime.Region) -> Generator[sublime.Region, None, None]:
130         selection = self.view.sel()
131         primary_cursor_position = selection[0].b
132         for region in reversed(selection):
133             # For each selection region, apply the same removal as for the "primary" region.
134             # To do that, translate, or offset, the LSP edit region into the non-"primary" regions.
135             # The concept of "primary" is our own, and there is no mention of it in the LSP spec.
136             translation = region.b - primary_cursor_position
137             translated_edit_region = sublime.Region(edit_region.a + translation, edit_region.b + translation)
138             yield translated_edit_region
139 
140 
141 def resolve(completion_list: sublime.CompletionList, items: List[sublime.CompletionItem], flags: int = 0) -> None:
142     # Resolve the promise on the main thread to prevent any sort of data race for _set_target (see sublime_plugin.py).
143     sublime.set_timeout(lambda: completion_list.set_completions(items, flags))
144
```
--- 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/plugin/completion.py b/plugin/completion.py
--- a/plugin/completion.py
+++ b/plugin/completion.py
@@ -25,10 +25,12 @@
         if not detail or not documentation:
             # To make sure that the detail or documentation fields doesn't exist we need to resove the completion item.
             # If those fields appear after the item is resolved we show them in the popup.
-            self.do_resolve(item)
-        else:
-            minihtml_content = self.get_content(documentation, detail)
-            self.show_popup(minihtml_content)
+            session = self.best_session('completionProvider.resolveProvider')
+            if session:
+                session.send_request(Request.resolveCompletionItem(item), self.handle_resolve_response)
+                return
+        minihtml_content = self.get_content(documentation, detail)
+        self.show_popup(minihtml_content)
 
     def format_documentation(self, content: Union[str, Dict[str, str]]) -> str:
         return minihtml(self.view, content, allowed_formats=FORMAT_STRING | FORMAT_MARKUP_CONTENT)
@@ -56,13 +58,6 @@
     def on_navigate(self, url: str) -> None:
         webbrowser.open(url)
 
-    def do_resolve(self, item: dict) -> None:
-        session = self.best_session('completionProvider.resolveProvider')
-        if session:
-            session.send_request(
-                Request.resolveCompletionItem(item),
-                lambda res: self.handle_resolve_response(res))
-
     def handle_resolve_response(self, item: Optional[dict]) -> None:
         detail = ""
         documentation = ""

{"golden_diff": "diff --git a/plugin/completion.py b/plugin/completion.py\n--- a/plugin/completion.py\n+++ b/plugin/completion.py\n@@ -25,10 +25,12 @@\n         if not detail or not documentation:\n             # To make sure that the detail or documentation fields doesn't exist we need to resove the completion item.\n             # If those fields appear after the item is resolved we show them in the popup.\n-            self.do_resolve(item)\n-        else:\n-            minihtml_content = self.get_content(documentation, detail)\n-            self.show_popup(minihtml_content)\n+            session = self.best_session('completionProvider.resolveProvider')\n+            if session:\n+                session.send_request(Request.resolveCompletionItem(item), self.handle_resolve_response)\n+                return\n+        minihtml_content = self.get_content(documentation, detail)\n+        self.show_popup(minihtml_content)\n \n     def format_documentation(self, content: Union[str, Dict[str, str]]) -> str:\n         return minihtml(self.view, content, allowed_formats=FORMAT_STRING | FORMAT_MARKUP_CONTENT)\n@@ -56,13 +58,6 @@\n     def on_navigate(self, url: str) -> None:\n         webbrowser.open(url)\n \n-    def do_resolve(self, item: dict) -> None:\n-        session = self.best_session('completionProvider.resolveProvider')\n-        if session:\n-            session.send_request(\n-                Request.resolveCompletionItem(item),\n-                lambda res: self.handle_resolve_response(res))\n-\n     def handle_resolve_response(self, item: Optional[dict]) -> None:\n         detail = \"\"\n         documentation = \"\"\n", "issue": "[LSP-elm] Documentation popup is no logner visible when \"More\" link is clicked\n* OS and language server - Ubunutu 20.04, LSP-elm, ST 4085 \r\n* How you installed LSP - git, latest st-4000-exploration\r\n\r\nWhen clicking the `More` link in the AC popup,\r\nI expect to see a documentation popup.\r\nBut I see nothing. \r\n\r\nThis commit introduced this behavior 19df9e19afeb0f32064a8b7e3a11ebaa4254f63c\r\nIf I checkout the commit before 19df9e19afeb0f32064a8b7e3a11ebaa4254f63c, everything works as expected.\n", "before_files": [{"content": "import mdpopups\nimport sublime\nimport sublime_plugin\nimport webbrowser\nfrom .core.css import css\nfrom .core.logging import debug\nfrom .core.edit import parse_text_edit\nfrom .core.protocol import Request, InsertTextFormat, Range\nfrom .core.registry import LspTextCommand\nfrom .core.typing import Any, List, Dict, Optional, Generator, Union\nfrom .core.views import FORMAT_STRING, FORMAT_MARKUP_CONTENT, minihtml\nfrom .core.views import range_to_region\n\n\nclass LspResolveDocsCommand(LspTextCommand):\n\n    completions = []  # type: List[Dict[str, Any]]\n\n    def run(self, edit: sublime.Edit, index: int, event: Optional[dict] = None) -> None:\n        item = self.completions[index]\n        detail = self.format_documentation(item.get('detail') or \"\")\n        documentation = self.format_documentation(item.get(\"documentation\") or \"\")\n        # don't show the detail in the cooperate AC popup if it is already shown in the AC details filed.\n        self.is_detail_shown = bool(detail)\n        if not detail or not documentation:\n            # To make sure that the detail or documentation fields doesn't exist we need to resove the completion item.\n            # If those fields appear after the item is resolved we show them in the popup.\n            self.do_resolve(item)\n        else:\n            minihtml_content = self.get_content(documentation, detail)\n            self.show_popup(minihtml_content)\n\n    def format_documentation(self, content: Union[str, Dict[str, str]]) -> str:\n        return minihtml(self.view, content, allowed_formats=FORMAT_STRING | FORMAT_MARKUP_CONTENT)\n\n    def get_content(self, documentation: str, detail: str) -> str:\n        content = \"\"\n        if detail and not self.is_detail_shown:\n            content += \"<div class='highlight'>{}</div>\".format(detail)\n        if documentation:\n            content += \"<div>{}</div>\".format(documentation)\n        return content\n\n    def show_popup(self, minihtml_content: str) -> None:\n        viewport_width = self.view.viewport_extent()[0]\n        mdpopups.show_popup(\n            self.view,\n            minihtml_content,\n            flags=sublime.COOPERATE_WITH_AUTO_COMPLETE,\n            css=css().popups,\n            wrapper_class=css().popups_classname,\n            max_width=viewport_width,\n            on_navigate=self.on_navigate\n        )\n\n    def on_navigate(self, url: str) -> None:\n        webbrowser.open(url)\n\n    def do_resolve(self, item: dict) -> None:\n        session = self.best_session('completionProvider.resolveProvider')\n        if session:\n            session.send_request(\n                Request.resolveCompletionItem(item),\n                lambda res: self.handle_resolve_response(res))\n\n    def handle_resolve_response(self, item: Optional[dict]) -> None:\n        detail = \"\"\n        documentation = \"\"\n        if item:\n            detail = self.format_documentation(item.get('detail') or \"\")\n            documentation = self.format_documentation(item.get(\"documentation\") or \"\")\n        if not documentation:\n            documentation = self.format_documentation({\"kind\": \"markdown\", \"value\": \"*No documentation available.*\"})\n        minihtml_content = self.get_content(documentation, detail)\n        show = self.update_popup if self.view.is_popup_visible() else self.show_popup\n        # NOTE: Update/show popups from the main thread, or else the popup might make the AC widget disappear.\n        sublime.set_timeout(lambda: show(minihtml_content))\n\n    def update_popup(self, minihtml_content: str) -> None:\n        mdpopups.update_popup(\n            self.view,\n            minihtml_content,\n            css=css().popups,\n            wrapper_class=css().popups_classname,\n        )\n\n\nclass LspCompleteCommand(sublime_plugin.TextCommand):\n\n    def epilogue(self, item: Dict[str, Any]) -> None:\n        additional_edits = item.get('additionalTextEdits')\n        if additional_edits:\n            edits = [parse_text_edit(additional_edit) for additional_edit in additional_edits]\n            self.view.run_command(\"lsp_apply_document_edit\", {'changes': edits})\n        command = item.get(\"command\")\n        if command:\n            debug('Running server command \"{}\" for view {}'.format(command, self.view.id()))\n            self.view.run_command(\"lsp_execute\", {\"command_name\": command})\n\n\nclass LspCompleteInsertTextCommand(LspCompleteCommand):\n\n    def run(self, edit: sublime.Edit, **item: Any) -> None:\n        insert_text = item.get(\"insertText\") or item[\"label\"]\n        if item.get(\"insertTextFormat\", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:\n            self.view.run_command(\"insert_snippet\", {\"contents\": insert_text})\n        else:\n            self.view.run_command(\"insert\", {\"characters\": insert_text})\n        self.epilogue(item)\n\n\nclass LspCompleteTextEditCommand(LspCompleteCommand):\n\n    def run(self, edit: sublime.Edit, **item: Any) -> None:\n        text_edit = item[\"textEdit\"]\n        new_text = text_edit['newText']\n        edit_region = range_to_region(Range.from_lsp(text_edit['range']), self.view)\n        if item.get(\"insertTextFormat\", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:\n            for region in self.translated_regions(edit_region):\n                self.view.erase(edit, region)\n            self.view.run_command(\"insert_snippet\", {\"contents\": new_text})\n        else:\n            for region in self.translated_regions(edit_region):\n                # NOTE: Cannot do .replace, because ST will select the replacement.\n                self.view.erase(edit, region)\n                self.view.insert(edit, region.a, new_text)\n        self.epilogue(item)\n\n    def translated_regions(self, edit_region: sublime.Region) -> Generator[sublime.Region, None, None]:\n        selection = self.view.sel()\n        primary_cursor_position = selection[0].b\n        for region in reversed(selection):\n            # For each selection region, apply the same removal as for the \"primary\" region.\n            # To do that, translate, or offset, the LSP edit region into the non-\"primary\" regions.\n            # The concept of \"primary\" is our own, and there is no mention of it in the LSP spec.\n            translation = region.b - primary_cursor_position\n            translated_edit_region = sublime.Region(edit_region.a + translation, edit_region.b + translation)\n            yield translated_edit_region\n\n\ndef resolve(completion_list: sublime.CompletionList, items: List[sublime.CompletionItem], flags: int = 0) -> None:\n    # Resolve the promise on the main thread to prevent any sort of data race for _set_target (see sublime_plugin.py).\n    sublime.set_timeout(lambda: completion_list.set_completions(items, flags))\n", "path": "plugin/completion.py"}], "after_files": [{"content": "import mdpopups\nimport sublime\nimport sublime_plugin\nimport webbrowser\nfrom .core.css import css\nfrom .core.logging import debug\nfrom .core.edit import parse_text_edit\nfrom .core.protocol import Request, InsertTextFormat, Range\nfrom .core.registry import LspTextCommand\nfrom .core.typing import Any, List, Dict, Optional, Generator, Union\nfrom .core.views import FORMAT_STRING, FORMAT_MARKUP_CONTENT, minihtml\nfrom .core.views import range_to_region\n\n\nclass LspResolveDocsCommand(LspTextCommand):\n\n    completions = []  # type: List[Dict[str, Any]]\n\n    def run(self, edit: sublime.Edit, index: int, event: Optional[dict] = None) -> None:\n        item = self.completions[index]\n        detail = self.format_documentation(item.get('detail') or \"\")\n        documentation = self.format_documentation(item.get(\"documentation\") or \"\")\n        # don't show the detail in the cooperate AC popup if it is already shown in the AC details filed.\n        self.is_detail_shown = bool(detail)\n        if not detail or not documentation:\n            # To make sure that the detail or documentation fields doesn't exist we need to resove the completion item.\n            # If those fields appear after the item is resolved we show them in the popup.\n            session = self.best_session('completionProvider.resolveProvider')\n            if session:\n                session.send_request(Request.resolveCompletionItem(item), self.handle_resolve_response)\n                return\n        minihtml_content = self.get_content(documentation, detail)\n        self.show_popup(minihtml_content)\n\n    def format_documentation(self, content: Union[str, Dict[str, str]]) -> str:\n        return minihtml(self.view, content, allowed_formats=FORMAT_STRING | FORMAT_MARKUP_CONTENT)\n\n    def get_content(self, documentation: str, detail: str) -> str:\n        content = \"\"\n        if detail and not self.is_detail_shown:\n            content += \"<div class='highlight'>{}</div>\".format(detail)\n        if documentation:\n            content += \"<div>{}</div>\".format(documentation)\n        return content\n\n    def show_popup(self, minihtml_content: str) -> None:\n        viewport_width = self.view.viewport_extent()[0]\n        mdpopups.show_popup(\n            self.view,\n            minihtml_content,\n            flags=sublime.COOPERATE_WITH_AUTO_COMPLETE,\n            css=css().popups,\n            wrapper_class=css().popups_classname,\n            max_width=viewport_width,\n            on_navigate=self.on_navigate\n        )\n\n    def on_navigate(self, url: str) -> None:\n        webbrowser.open(url)\n\n    def handle_resolve_response(self, item: Optional[dict]) -> None:\n        detail = \"\"\n        documentation = \"\"\n        if item:\n            detail = self.format_documentation(item.get('detail') or \"\")\n            documentation = self.format_documentation(item.get(\"documentation\") or \"\")\n        if not documentation:\n            documentation = self.format_documentation({\"kind\": \"markdown\", \"value\": \"*No documentation available.*\"})\n        minihtml_content = self.get_content(documentation, detail)\n        show = self.update_popup if self.view.is_popup_visible() else self.show_popup\n        # NOTE: Update/show popups from the main thread, or else the popup might make the AC widget disappear.\n        sublime.set_timeout(lambda: show(minihtml_content))\n\n    def update_popup(self, minihtml_content: str) -> None:\n        mdpopups.update_popup(\n            self.view,\n            minihtml_content,\n            css=css().popups,\n            wrapper_class=css().popups_classname,\n        )\n\n\nclass LspCompleteCommand(sublime_plugin.TextCommand):\n\n    def epilogue(self, item: Dict[str, Any]) -> None:\n        additional_edits = item.get('additionalTextEdits')\n        if additional_edits:\n            edits = [parse_text_edit(additional_edit) for additional_edit in additional_edits]\n            self.view.run_command(\"lsp_apply_document_edit\", {'changes': edits})\n        command = item.get(\"command\")\n        if command:\n            debug('Running server command \"{}\" for view {}'.format(command, self.view.id()))\n            self.view.run_command(\"lsp_execute\", {\"command_name\": command})\n\n\nclass LspCompleteInsertTextCommand(LspCompleteCommand):\n\n    def run(self, edit: sublime.Edit, **item: Any) -> None:\n        insert_text = item.get(\"insertText\") or item[\"label\"]\n        if item.get(\"insertTextFormat\", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:\n            self.view.run_command(\"insert_snippet\", {\"contents\": insert_text})\n        else:\n            self.view.run_command(\"insert\", {\"characters\": insert_text})\n        self.epilogue(item)\n\n\nclass LspCompleteTextEditCommand(LspCompleteCommand):\n\n    def run(self, edit: sublime.Edit, **item: Any) -> None:\n        text_edit = item[\"textEdit\"]\n        new_text = text_edit['newText']\n        edit_region = range_to_region(Range.from_lsp(text_edit['range']), self.view)\n        if item.get(\"insertTextFormat\", InsertTextFormat.PlainText) == InsertTextFormat.Snippet:\n            for region in self.translated_regions(edit_region):\n                self.view.erase(edit, region)\n            self.view.run_command(\"insert_snippet\", {\"contents\": new_text})\n        else:\n            for region in self.translated_regions(edit_region):\n                # NOTE: Cannot do .replace, because ST will select the replacement.\n                self.view.erase(edit, region)\n                self.view.insert(edit, region.a, new_text)\n        self.epilogue(item)\n\n    def translated_regions(self, edit_region: sublime.Region) -> Generator[sublime.Region, None, None]:\n        selection = self.view.sel()\n        primary_cursor_position = selection[0].b\n        for region in reversed(selection):\n            # For each selection region, apply the same removal as for the \"primary\" region.\n            # To do that, translate, or offset, the LSP edit region into the non-\"primary\" regions.\n            # The concept of \"primary\" is our own, and there is no mention of it in the LSP spec.\n            translation = region.b - primary_cursor_position\n            translated_edit_region = sublime.Region(edit_region.a + translation, edit_region.b + translation)\n            yield translated_edit_region\n\n\ndef resolve(completion_list: sublime.CompletionList, items: List[sublime.CompletionItem], flags: int = 0) -> None:\n    # Resolve the promise on the main thread to prevent any sort of data race for _set_target (see sublime_plugin.py).\n    sublime.set_timeout(lambda: completion_list.set_completions(items, flags))\n", "path": "plugin/completion.py"}]}