@@ -3,7 +3,7 @@ import Gio from "gi://Gio";
33
44import { LSPError } from "./LSP.js" ;
55
6- import { getPid , promiseTask , once } from "../../troll/src/util.js" ;
6+ import { getPid , once } from "../../troll/src/util.js" ;
77
88const { addSignalMethods } = imports . signals ;
99
@@ -17,6 +17,26 @@ const clientInfo = {
1717 version : pkg . version ,
1818} ;
1919
20+ Gio . _promisify (
21+ Gio . InputStream . prototype ,
22+ "read_bytes_async" ,
23+ "read_bytes_finish" ,
24+ ) ;
25+ Gio . _promisify ( Gio . InputStream . prototype , "read_all_async" , "read_all_finish" ) ;
26+ Gio . _promisify ( Gio . InputStream . prototype , "close_async" , "close_finish" ) ;
27+ Gio . _promisify (
28+ Gio . DataInputStream . prototype ,
29+ "read_line_async" ,
30+ "read_line_finish" ,
31+ ) ;
32+ Gio . _promisify ( Gio . OutputStream . prototype , "close_async" , "close_finish" ) ;
33+ Gio . _promisify (
34+ Gio . OutputStream . prototype ,
35+ "write_bytes_async" ,
36+ "write_bytes_finish" ,
37+ ) ;
38+ Gio . _promisify ( Gio . Subprocess . prototype , "wait_async" , "wait_finish" ) ;
39+
2040export default class LSPClient {
2141 constructor ( argv , { rootUri, uri, languageId, buffer } ) {
2242 this . argv = argv ;
@@ -76,8 +96,10 @@ export default class LSPClient {
7696 }
7797
7898 async stop ( ) {
79- await promiseTask ( this . stdin , "close_async" , "close_finish" , null ) ;
80- await promiseTask ( this . stdout , "close_async" , "close_finish" , null ) ;
99+ await Promise . all ( [
100+ this . stdin . close_async ( null ) ,
101+ this . stdout . close_async ( null ) ,
102+ ] ) ;
81103 // this.proc?.force_exit();
82104 this . proc . send_signal ( 15 ) ;
83105 }
@@ -134,15 +156,13 @@ export default class LSPClient {
134156 flags = flags | Gio . SubprocessFlags . STDERR_SILENCE ;
135157
136158 this . proc = Gio . Subprocess . new ( this . argv , flags ) ;
137- this . proc . wait_async ( null , ( _self , res ) => {
138- try {
139- this . proc . wait_finish ( res ) ;
140- } catch ( err ) {
141- logError ( err ) ;
142- }
143- this . emit ( "exit" ) ;
144- // this._start_process();
145- } ) ;
159+ this . proc
160+ . wait_async ( null )
161+ . then ( ( ) => {
162+ this . emit ( "exit" ) ;
163+ // this._start_process();
164+ } )
165+ . catch ( logError ) ;
146166 this . stdin = this . proc . get_stdin_pipe ( ) ;
147167 this . stdout = new Gio . DataInputStream ( {
148168 base_stream : this . proc . get_stdout_pipe ( ) ,
@@ -156,11 +176,8 @@ export default class LSPClient {
156176 const headers = Object . create ( null ) ;
157177
158178 while ( true ) {
159- const [ bytes ] = await promiseTask (
160- this . stdout ,
161- "read_line_async" ,
162- "read_line_finish" ,
163- 0 ,
179+ const [ bytes ] = await this . stdout . read_line_async (
180+ GLib . PRIORITY_DEFAULT ,
164181 null ,
165182 ) ;
166183 if ( ! bytes ) break ;
@@ -177,15 +194,23 @@ export default class LSPClient {
177194 }
178195
179196 async _read_content ( length ) {
180- const bytes = await promiseTask (
181- this . stdout ,
182- "read_bytes_async" ,
183- "read_bytes_finish" ,
184- length ,
185- 0 ,
186- null ,
187- ) ;
188- const str = decoder_utf8 . decode ( bytes . toArray ( ) ) ;
197+ // read_bytes is limited by some underlying max buffer size
198+ // see https://github.com/sonnyp/Workbench/issues/240#issuecomment-1475387647
199+ // read_all is not supported in GJS so we do this instead
200+ // https://gitlab.gnome.org/GNOME/gjs/-/issues/501
201+ const uint8 = new Uint8Array ( length ) ;
202+ let read = 0 ;
203+ while ( read < length ) {
204+ const bytes = await this . stdout . read_bytes_async (
205+ length - read ,
206+ GLib . PRIORITY_DEFAULT ,
207+ null ,
208+ ) ;
209+ uint8 . set ( bytes . toArray ( ) , read ) ;
210+ read += bytes . get_size ( ) ;
211+ }
212+
213+ const str = decoder_utf8 . decode ( uint8 ) ;
189214 try {
190215 return JSON . parse ( str ) ;
191216 } catch ( err ) {
@@ -232,14 +257,7 @@ export default class LSPClient {
232257 this . stdin . flush ( ) ;
233258 }
234259
235- await promiseTask (
236- this . stdin ,
237- "write_bytes_async" ,
238- "write_bytes_finish" ,
239- bytes ,
240- GLib . PRIORITY_DEFAULT ,
241- null ,
242- ) ;
260+ await this . stdin . write_bytes_async ( bytes , GLib . PRIORITY_DEFAULT , null ) ;
243261
244262 this . emit ( "output" , message ) ;
245263 }
@@ -253,7 +271,7 @@ export default class LSPClient {
253271 } ) ;
254272 const [ result ] = await once ( this , `result::${ id } ` , {
255273 error : `error::${ id } ` ,
256- timeout : 1000 ,
274+ timeout : 5000 ,
257275 } ) ;
258276 return result ;
259277 }
0 commit comments