prompt: We are currently solving the following issue within our repository. Here is the issue text:
  --- BEGIN ISSUE ---
  Format JSON on save
  Is there a way to get this LSP to format json files ons save?
  
  It works for other LSPs but just not JSON,
  
  Here are my configs:
  
  Preferences
  ```
  {
          ...
  	"lsp_format_on_save": true
          ...
  }
  ```
  
  LSP
  ```
  	"lsp_code_actions_on_save": {
  		"source.organizeImports": true,
  		"source.fixAll.eslint": true,
  	}
  ```
  
  All LSP-JSON settings are default
  
  --- 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/formatting.py`
  Content:
  ```
  1 from .core.edit import parse_text_edit
  2 from .core.protocol import TextEdit
  3 from .core.registry import LspTextCommand
  4 from .core.sessions import Session
  5 from .core.settings import userprefs
  6 from .core.typing import Any, Callable, List, Optional, Iterator
  7 from .core.views import entire_content_region
  8 from .core.views import first_selection_region
  9 from .core.views import text_document_formatting
  10 from .core.views import text_document_range_formatting
  11 from .core.views import will_save_wait_until
  12 from .save_command import LspSaveCommand, SaveTask
  13 import sublime
  14 
  15 
  16 def apply_response_to_view(response: Optional[List[TextEdit]], view: sublime.View) -> None:
  17     edits = list(parse_text_edit(change) for change in response) if response else []
  18     view.run_command('lsp_apply_document_edit', {'changes': edits})
  19 
  20 
  21 class WillSaveWaitTask(SaveTask):
  22     @classmethod
  23     def is_applicable(cls, view: sublime.View) -> bool:
  24         return bool(view.file_name())
  25 
  26     def __init__(self, task_runner: LspTextCommand, on_complete: Callable[[], None]) -> None:
  27         super().__init__(task_runner, on_complete)
  28         self._session_iterator = None  # type: Optional[Iterator[Session]]
  29 
  30     def run_async(self) -> None:
  31         super().run_async()
  32         self._session_iterator = self._task_runner.sessions('textDocumentSync.willSaveWaitUntil')
  33         self._handle_next_session_async()
  34 
  35     def _handle_next_session_async(self) -> None:
  36         session = next(self._session_iterator, None) if self._session_iterator else None
  37         if session:
  38             self._purge_changes_async()
  39             self._will_save_wait_until_async(session)
  40         else:
  41             self._on_complete()
  42 
  43     def _will_save_wait_until_async(self, session: Session) -> None:
  44         session.send_request_async(
  45             will_save_wait_until(self._task_runner.view, reason=1),  # TextDocumentSaveReason.Manual
  46             self._on_response,
  47             lambda error: self._on_response(None))
  48 
  49     def _on_response(self, response: Any) -> None:
  50         if response and not self._cancelled:
  51             apply_response_to_view(response, self._task_runner.view)
  52         sublime.set_timeout_async(self._handle_next_session_async)
  53 
  54 
  55 class FormattingTask(SaveTask):
  56     @classmethod
  57     def is_applicable(cls, view: sublime.View) -> bool:
  58         settings = view.settings()
  59         view_format_on_save = settings.get('lsp_format_on_save', None)
  60         enabled = view_format_on_save if isinstance(view_format_on_save, bool) else userprefs().lsp_format_on_save
  61         return enabled and bool(view.window()) and bool(view.file_name())
  62 
  63     def run_async(self) -> None:
  64         super().run_async()
  65         self._purge_changes_async()
  66         session = self._task_runner.best_session(LspFormatDocumentCommand.capability)
  67         if session:
  68             session.send_request_async(
  69                 text_document_formatting(self._task_runner.view), self._on_response,
  70                 lambda error: self._on_response(None))
  71         else:
  72             self._on_complete()
  73 
  74     def _on_response(self, response: Any) -> None:
  75         if response and not self._cancelled:
  76             apply_response_to_view(response, self._task_runner.view)
  77         sublime.set_timeout_async(self._on_complete)
  78 
  79 
  80 LspSaveCommand.register_task(WillSaveWaitTask)
  81 LspSaveCommand.register_task(FormattingTask)
  82 
  83 
  84 class LspFormatDocumentCommand(LspTextCommand):
  85 
  86     capability = 'documentFormattingProvider'
  87 
  88     def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:
  89         return super().is_enabled() or bool(self.best_session(LspFormatDocumentRangeCommand.capability))
  90 
  91     def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:
  92         session = self.best_session(self.capability)
  93         if session:
  94             # Either use the documentFormattingProvider ...
  95             session.send_request(text_document_formatting(self.view), self.on_result)
  96         else:
  97             session = self.best_session(LspFormatDocumentRangeCommand.capability)
  98             if session:
  99                 # ... or use the documentRangeFormattingProvider and format the entire range.
  100                 req = text_document_range_formatting(self.view, entire_content_region(self.view))
  101                 session.send_request(req, self.on_result)
  102 
  103     def on_result(self, params: Any) -> None:
  104         apply_response_to_view(params, self.view)
  105 
  106 
  107 class LspFormatDocumentRangeCommand(LspTextCommand):
  108 
  109     capability = 'documentRangeFormattingProvider'
  110 
  111     def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:
  112         if super().is_enabled(event, point):
  113             if len(self.view.sel()) == 1:
  114                 region = self.view.sel()[0]
  115                 if region.begin() != region.end():
  116                     return True
  117         return False
  118 
  119     def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:
  120         session = self.best_session(self.capability)
  121         selection = first_selection_region(self.view)
  122         if session and selection is not None:
  123             req = text_document_range_formatting(self.view, selection)
  124             session.send_request(req, lambda response: apply_response_to_view(response, self.view))
  125
  ```
  --- 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()
  
  ```
  
golden_diff: diff --git a/plugin/formatting.py b/plugin/formatting.py
  --- a/plugin/formatting.py
  +++ b/plugin/formatting.py
  @@ -1,9 +1,11 @@
   from .core.edit import parse_text_edit
  +from .core.promise import Promise
  +from .core.protocol import Error
   from .core.protocol import TextEdit
   from .core.registry import LspTextCommand
   from .core.sessions import Session
   from .core.settings import userprefs
  -from .core.typing import Any, Callable, List, Optional, Iterator
  +from .core.typing import Any, Callable, List, Optional, Iterator, Union
   from .core.views import entire_content_region
   from .core.views import first_selection_region
   from .core.views import text_document_formatting
  @@ -13,6 +15,22 @@
   import sublime
   
   
  +FormatResponse = Union[List[TextEdit], None, Error]
  +
  +
  +def format_document(text_command: LspTextCommand) -> Promise[FormatResponse]:
  +    view = text_command.view
  +    session = text_command.best_session(LspFormatDocumentCommand.capability)
  +    if session:
  +        # Either use the documentFormattingProvider ...
  +        return session.send_request_task(text_document_formatting(view))
  +    session = text_command.best_session(LspFormatDocumentRangeCommand.capability)
  +    if session:
  +        # ... or use the documentRangeFormattingProvider and format the entire range.
  +        return session.send_request_task(text_document_range_formatting(view, entire_content_region(view)))
  +    return Promise.resolve(None)
  +
  +
   def apply_response_to_view(response: Optional[List[TextEdit]], view: sublime.View) -> None:
       edits = list(parse_text_edit(change) for change in response) if response else []
       view.run_command('lsp_apply_document_edit', {'changes': edits})
  @@ -63,16 +81,10 @@
       def run_async(self) -> None:
           super().run_async()
           self._purge_changes_async()
  -        session = self._task_runner.best_session(LspFormatDocumentCommand.capability)
  -        if session:
  -            session.send_request_async(
  -                text_document_formatting(self._task_runner.view), self._on_response,
  -                lambda error: self._on_response(None))
  -        else:
  -            self._on_complete()
  +        format_document(self._task_runner).then(self._on_response)
   
  -    def _on_response(self, response: Any) -> None:
  -        if response and not self._cancelled:
  +    def _on_response(self, response: FormatResponse) -> None:
  +        if response and not isinstance(response, Error) and not self._cancelled:
               apply_response_to_view(response, self._task_runner.view)
           sublime.set_timeout_async(self._on_complete)
   
  @@ -89,19 +101,11 @@
           return super().is_enabled() or bool(self.best_session(LspFormatDocumentRangeCommand.capability))
   
       def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:
  -        session = self.best_session(self.capability)
  -        if session:
  -            # Either use the documentFormattingProvider ...
  -            session.send_request(text_document_formatting(self.view), self.on_result)
  -        else:
  -            session = self.best_session(LspFormatDocumentRangeCommand.capability)
  -            if session:
  -                # ... or use the documentRangeFormattingProvider and format the entire range.
  -                req = text_document_range_formatting(self.view, entire_content_region(self.view))
  -                session.send_request(req, self.on_result)
  -
  -    def on_result(self, params: Any) -> None:
  -        apply_response_to_view(params, self.view)
  +        format_document(self).then(self.on_result)
  +
  +    def on_result(self, result: FormatResponse) -> None:
  +        if result and not isinstance(result, Error):
  +            apply_response_to_view(result, self.view)
   
   
   class LspFormatDocumentRangeCommand(LspTextCommand):
  
verification_info: {"golden_diff": "diff --git a/plugin/formatting.py b/plugin/formatting.py\n--- a/plugin/formatting.py\n+++ b/plugin/formatting.py\n@@ -1,9 +1,11 @@\n from .core.edit import parse_text_edit\n+from .core.promise import Promise\n+from .core.protocol import Error\n from .core.protocol import TextEdit\n from .core.registry import LspTextCommand\n from .core.sessions import Session\n from .core.settings import userprefs\n-from .core.typing import Any, Callable, List, Optional, Iterator\n+from .core.typing import Any, Callable, List, Optional, Iterator, Union\n from .core.views import entire_content_region\n from .core.views import first_selection_region\n from .core.views import text_document_formatting\n@@ -13,6 +15,22 @@\n import sublime\n \n \n+FormatResponse = Union[List[TextEdit], None, Error]\n+\n+\n+def format_document(text_command: LspTextCommand) -> Promise[FormatResponse]:\n+    view = text_command.view\n+    session = text_command.best_session(LspFormatDocumentCommand.capability)\n+    if session:\n+        # Either use the documentFormattingProvider ...\n+        return session.send_request_task(text_document_formatting(view))\n+    session = text_command.best_session(LspFormatDocumentRangeCommand.capability)\n+    if session:\n+        # ... or use the documentRangeFormattingProvider and format the entire range.\n+        return session.send_request_task(text_document_range_formatting(view, entire_content_region(view)))\n+    return Promise.resolve(None)\n+\n+\n def apply_response_to_view(response: Optional[List[TextEdit]], view: sublime.View) -> None:\n     edits = list(parse_text_edit(change) for change in response) if response else []\n     view.run_command('lsp_apply_document_edit', {'changes': edits})\n@@ -63,16 +81,10 @@\n     def run_async(self) -> None:\n         super().run_async()\n         self._purge_changes_async()\n-        session = self._task_runner.best_session(LspFormatDocumentCommand.capability)\n-        if session:\n-            session.send_request_async(\n-                text_document_formatting(self._task_runner.view), self._on_response,\n-                lambda error: self._on_response(None))\n-        else:\n-            self._on_complete()\n+        format_document(self._task_runner).then(self._on_response)\n \n-    def _on_response(self, response: Any) -> None:\n-        if response and not self._cancelled:\n+    def _on_response(self, response: FormatResponse) -> None:\n+        if response and not isinstance(response, Error) and not self._cancelled:\n             apply_response_to_view(response, self._task_runner.view)\n         sublime.set_timeout_async(self._on_complete)\n \n@@ -89,19 +101,11 @@\n         return super().is_enabled() or bool(self.best_session(LspFormatDocumentRangeCommand.capability))\n \n     def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:\n-        session = self.best_session(self.capability)\n-        if session:\n-            # Either use the documentFormattingProvider ...\n-            session.send_request(text_document_formatting(self.view), self.on_result)\n-        else:\n-            session = self.best_session(LspFormatDocumentRangeCommand.capability)\n-            if session:\n-                # ... or use the documentRangeFormattingProvider and format the entire range.\n-                req = text_document_range_formatting(self.view, entire_content_region(self.view))\n-                session.send_request(req, self.on_result)\n-\n-    def on_result(self, params: Any) -> None:\n-        apply_response_to_view(params, self.view)\n+        format_document(self).then(self.on_result)\n+\n+    def on_result(self, result: FormatResponse) -> None:\n+        if result and not isinstance(result, Error):\n+            apply_response_to_view(result, self.view)\n \n \n class LspFormatDocumentRangeCommand(LspTextCommand):\n", "issue": "Format JSON on save\nIs there a way to get this LSP to format json files ons save?\r\n\r\nIt works for other LSPs but just not JSON,\r\n\r\nHere are my configs:\r\n\r\nPreferences\r\n```\r\n{\r\n        ...\r\n\t\"lsp_format_on_save\": true\r\n        ...\r\n}\r\n```\r\n\r\nLSP\r\n```\r\n\t\"lsp_code_actions_on_save\": {\r\n\t\t\"source.organizeImports\": true,\r\n\t\t\"source.fixAll.eslint\": true,\r\n\t}\r\n```\r\n\r\nAll LSP-JSON settings are default\n", "before_files": [{"content": "from .core.edit import parse_text_edit\nfrom .core.protocol import TextEdit\nfrom .core.registry import LspTextCommand\nfrom .core.sessions import Session\nfrom .core.settings import userprefs\nfrom .core.typing import Any, Callable, List, Optional, Iterator\nfrom .core.views import entire_content_region\nfrom .core.views import first_selection_region\nfrom .core.views import text_document_formatting\nfrom .core.views import text_document_range_formatting\nfrom .core.views import will_save_wait_until\nfrom .save_command import LspSaveCommand, SaveTask\nimport sublime\n\n\ndef apply_response_to_view(response: Optional[List[TextEdit]], view: sublime.View) -> None:\n    edits = list(parse_text_edit(change) for change in response) if response else []\n    view.run_command('lsp_apply_document_edit', {'changes': edits})\n\n\nclass WillSaveWaitTask(SaveTask):\n    @classmethod\n    def is_applicable(cls, view: sublime.View) -> bool:\n        return bool(view.file_name())\n\n    def __init__(self, task_runner: LspTextCommand, on_complete: Callable[[], None]) -> None:\n        super().__init__(task_runner, on_complete)\n        self._session_iterator = None  # type: Optional[Iterator[Session]]\n\n    def run_async(self) -> None:\n        super().run_async()\n        self._session_iterator = self._task_runner.sessions('textDocumentSync.willSaveWaitUntil')\n        self._handle_next_session_async()\n\n    def _handle_next_session_async(self) -> None:\n        session = next(self._session_iterator, None) if self._session_iterator else None\n        if session:\n            self._purge_changes_async()\n            self._will_save_wait_until_async(session)\n        else:\n            self._on_complete()\n\n    def _will_save_wait_until_async(self, session: Session) -> None:\n        session.send_request_async(\n            will_save_wait_until(self._task_runner.view, reason=1),  # TextDocumentSaveReason.Manual\n            self._on_response,\n            lambda error: self._on_response(None))\n\n    def _on_response(self, response: Any) -> None:\n        if response and not self._cancelled:\n            apply_response_to_view(response, self._task_runner.view)\n        sublime.set_timeout_async(self._handle_next_session_async)\n\n\nclass FormattingTask(SaveTask):\n    @classmethod\n    def is_applicable(cls, view: sublime.View) -> bool:\n        settings = view.settings()\n        view_format_on_save = settings.get('lsp_format_on_save', None)\n        enabled = view_format_on_save if isinstance(view_format_on_save, bool) else userprefs().lsp_format_on_save\n        return enabled and bool(view.window()) and bool(view.file_name())\n\n    def run_async(self) -> None:\n        super().run_async()\n        self._purge_changes_async()\n        session = self._task_runner.best_session(LspFormatDocumentCommand.capability)\n        if session:\n            session.send_request_async(\n                text_document_formatting(self._task_runner.view), self._on_response,\n                lambda error: self._on_response(None))\n        else:\n            self._on_complete()\n\n    def _on_response(self, response: Any) -> None:\n        if response and not self._cancelled:\n            apply_response_to_view(response, self._task_runner.view)\n        sublime.set_timeout_async(self._on_complete)\n\n\nLspSaveCommand.register_task(WillSaveWaitTask)\nLspSaveCommand.register_task(FormattingTask)\n\n\nclass LspFormatDocumentCommand(LspTextCommand):\n\n    capability = 'documentFormattingProvider'\n\n    def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:\n        return super().is_enabled() or bool(self.best_session(LspFormatDocumentRangeCommand.capability))\n\n    def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:\n        session = self.best_session(self.capability)\n        if session:\n            # Either use the documentFormattingProvider ...\n            session.send_request(text_document_formatting(self.view), self.on_result)\n        else:\n            session = self.best_session(LspFormatDocumentRangeCommand.capability)\n            if session:\n                # ... or use the documentRangeFormattingProvider and format the entire range.\n                req = text_document_range_formatting(self.view, entire_content_region(self.view))\n                session.send_request(req, self.on_result)\n\n    def on_result(self, params: Any) -> None:\n        apply_response_to_view(params, self.view)\n\n\nclass LspFormatDocumentRangeCommand(LspTextCommand):\n\n    capability = 'documentRangeFormattingProvider'\n\n    def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:\n        if super().is_enabled(event, point):\n            if len(self.view.sel()) == 1:\n                region = self.view.sel()[0]\n                if region.begin() != region.end():\n                    return True\n        return False\n\n    def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:\n        session = self.best_session(self.capability)\n        selection = first_selection_region(self.view)\n        if session and selection is not None:\n            req = text_document_range_formatting(self.view, selection)\n            session.send_request(req, lambda response: apply_response_to_view(response, self.view))\n", "path": "plugin/formatting.py"}], "after_files": [{"content": "from .core.edit import parse_text_edit\nfrom .core.promise import Promise\nfrom .core.protocol import Error\nfrom .core.protocol import TextEdit\nfrom .core.registry import LspTextCommand\nfrom .core.sessions import Session\nfrom .core.settings import userprefs\nfrom .core.typing import Any, Callable, List, Optional, Iterator, Union\nfrom .core.views import entire_content_region\nfrom .core.views import first_selection_region\nfrom .core.views import text_document_formatting\nfrom .core.views import text_document_range_formatting\nfrom .core.views import will_save_wait_until\nfrom .save_command import LspSaveCommand, SaveTask\nimport sublime\n\n\nFormatResponse = Union[List[TextEdit], None, Error]\n\n\ndef format_document(text_command: LspTextCommand) -> Promise[FormatResponse]:\n    view = text_command.view\n    session = text_command.best_session(LspFormatDocumentCommand.capability)\n    if session:\n        # Either use the documentFormattingProvider ...\n        return session.send_request_task(text_document_formatting(view))\n    session = text_command.best_session(LspFormatDocumentRangeCommand.capability)\n    if session:\n        # ... or use the documentRangeFormattingProvider and format the entire range.\n        return session.send_request_task(text_document_range_formatting(view, entire_content_region(view)))\n    return Promise.resolve(None)\n\n\ndef apply_response_to_view(response: Optional[List[TextEdit]], view: sublime.View) -> None:\n    edits = list(parse_text_edit(change) for change in response) if response else []\n    view.run_command('lsp_apply_document_edit', {'changes': edits})\n\n\nclass WillSaveWaitTask(SaveTask):\n    @classmethod\n    def is_applicable(cls, view: sublime.View) -> bool:\n        return bool(view.file_name())\n\n    def __init__(self, task_runner: LspTextCommand, on_complete: Callable[[], None]) -> None:\n        super().__init__(task_runner, on_complete)\n        self._session_iterator = None  # type: Optional[Iterator[Session]]\n\n    def run_async(self) -> None:\n        super().run_async()\n        self._session_iterator = self._task_runner.sessions('textDocumentSync.willSaveWaitUntil')\n        self._handle_next_session_async()\n\n    def _handle_next_session_async(self) -> None:\n        session = next(self._session_iterator, None) if self._session_iterator else None\n        if session:\n            self._purge_changes_async()\n            self._will_save_wait_until_async(session)\n        else:\n            self._on_complete()\n\n    def _will_save_wait_until_async(self, session: Session) -> None:\n        session.send_request_async(\n            will_save_wait_until(self._task_runner.view, reason=1),  # TextDocumentSaveReason.Manual\n            self._on_response,\n            lambda error: self._on_response(None))\n\n    def _on_response(self, response: Any) -> None:\n        if response and not self._cancelled:\n            apply_response_to_view(response, self._task_runner.view)\n        sublime.set_timeout_async(self._handle_next_session_async)\n\n\nclass FormattingTask(SaveTask):\n    @classmethod\n    def is_applicable(cls, view: sublime.View) -> bool:\n        settings = view.settings()\n        view_format_on_save = settings.get('lsp_format_on_save', None)\n        enabled = view_format_on_save if isinstance(view_format_on_save, bool) else userprefs().lsp_format_on_save\n        return enabled and bool(view.window()) and bool(view.file_name())\n\n    def run_async(self) -> None:\n        super().run_async()\n        self._purge_changes_async()\n        format_document(self._task_runner).then(self._on_response)\n\n    def _on_response(self, response: FormatResponse) -> None:\n        if response and not isinstance(response, Error) and not self._cancelled:\n            apply_response_to_view(response, self._task_runner.view)\n        sublime.set_timeout_async(self._on_complete)\n\n\nLspSaveCommand.register_task(WillSaveWaitTask)\nLspSaveCommand.register_task(FormattingTask)\n\n\nclass LspFormatDocumentCommand(LspTextCommand):\n\n    capability = 'documentFormattingProvider'\n\n    def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:\n        return super().is_enabled() or bool(self.best_session(LspFormatDocumentRangeCommand.capability))\n\n    def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:\n        format_document(self).then(self.on_result)\n\n    def on_result(self, result: FormatResponse) -> None:\n        if result and not isinstance(result, Error):\n            apply_response_to_view(result, self.view)\n\n\nclass LspFormatDocumentRangeCommand(LspTextCommand):\n\n    capability = 'documentRangeFormattingProvider'\n\n    def is_enabled(self, event: Optional[dict] = None, point: Optional[int] = None) -> bool:\n        if super().is_enabled(event, point):\n            if len(self.view.sel()) == 1:\n                region = self.view.sel()[0]\n                if region.begin() != region.end():\n                    return True\n        return False\n\n    def run(self, edit: sublime.Edit, event: Optional[dict] = None) -> None:\n        session = self.best_session(self.capability)\n        selection = first_selection_region(self.view)\n        if session and selection is not None:\n            req = text_document_range_formatting(self.view, selection)\n            session.send_request(req, lambda response: apply_response_to_view(response, self.view))\n", "path": "plugin/formatting.py"}]}