fix line numbering issues with vala generator - hopefully fixes completion in node...
[roobuilder] / src / Palete / LanguageClient.vala
index 245e321..d3dd092 100644 (file)
 
 namespace Palete {
 
-       public enum  LanguageClientAction {
-               INIT,
-               LAUNCH,
-               ACCEPT,
-               
-               DIAG,
-               OPEN,
-               SAVE,
-               CLOSE,
-               CHANGE,
-               TERM,
-               COMPLETE,
-               COMPLETE_REPLY,
-               
-               RESTART,
-               ERROR,
-               ERROR_START,
-               ERROR_RPC,
-               ERROR_REPLY,
-
-               EXIT,
-       }
 
        public abstract class LanguageClient :   Jsonrpc.Server {
        
                public Project.Project project;
-               private GLib.SubprocessLauncher launcher = null;
-               private GLib.Subprocess? subprocess = null;
-               private IOStream? subprocess_stream = null;
+               private GLib.SubprocessLauncher launcher;
+               private GLib.Subprocess subprocess;
+               private IOStream subprocess_stream;
            public Jsonrpc.Client? jsonrpc_client = null;
                
-               Gee.ArrayList<JsRender.JsRender> open_files;
-               private JsRender.JsRender? _change_queue_file = null;
-               private string change_queue_file_source = "";
-               
-               JsRender.JsRender? change_queue_file {
-                       set {
-                               this.change_queue_file_source = value == null ? "" : value.toSource();
-                               this._change_queue_file = value;
-                       } 
-                       get {
-                               return this._change_queue_file;
-                       } 
-               }
-               uint change_queue_id = 0;
-               int countdown = 0;
-               protected bool initialized = false;
-               bool sent_shutdown = false;
-               private bool _closed = false;
-               private bool closed {
-                       get { return this._closed ; } 
-                       set {
-                               GLib.debug("closed has been set? to %s" , value ? "TRUE" : "FALSE" );
-                               this._closed = value;
-                       }
-               }
-       
-               public signal void log(LanguageClientAction action, string message);
-               
-               
                protected LanguageClient(Project.Project project)
                {
                        // extend versions will proably call initialize to start and connect to server.
                        this.project = project;
-                       this.open_files = new   Gee.ArrayList<JsRender.JsRender>();
-                       this.change_queue_id = GLib.Timeout.add_seconds(1, () => {
-                               if (this.change_queue_file == null) {
-                                       return true;
-                               }
-                               this.countdown--;
-                               if (this.countdown < 0){
-                                       this.document_change_real(this.change_queue_file,  this.change_queue_file_source);
-                                       this.change_queue_file = null;
-                                          
-                               }
-                               return true;
-                       });
+                       
                
                }
                 
                public bool initProcess(string process_path)
                {
-                       this.onClose();
-                       this.log(LanguageClientAction.LAUNCH, process_path);
-                       GLib.debug("Launching %s", process_path);
                        this.launcher = new GLib.SubprocessLauncher (SubprocessFlags.STDIN_PIPE | SubprocessFlags.STDOUT_PIPE);
                        this.launcher.set_environ(GLib.Environ.get());
                        try {
-
-                               
                                this.subprocess = launcher.spawnv ({ process_path });
-                               
-                               this.subprocess.wait_async.begin( null, ( obj,res ) => {
-                                       try {
-                                               this.subprocess.wait_async.end(res);
-                                       } catch (GLib.Error e) {
-                                               this.log(LanguageClientAction.ERROR_START, e.message);
-                                               GLib.debug("subprocess startup error %s", e.message);           
-                                       }
-                                       this.log(LanguageClientAction.EXIT, "process ended");
-                                       GLib.debug("Subprocess ended %s", process_path);
-                                       this.onClose();
-
-                               });
                                var input_stream = this.subprocess.get_stdout_pipe ();
                                var output_stream = this.subprocess.get_stdin_pipe ();
  
@@ -122,60 +41,19 @@ namespace Palete {
                                        if (!GLib.Unix.set_fd_nonblocking(((GLib.UnixInputStream)input_stream).fd, true)
                                         || !GLib.Unix.set_fd_nonblocking (((GLib.UnixOutputStream)output_stream).fd, true)) 
                                         {
-                                               GLib.debug("could not set pipes to nonblocking");
-                                               this.onClose();
+                                                GLib.debug("could not set pipes to nonblocking");
                                            return false;
                                    }
                            }
-                           this.subprocess_stream = new GLib.SimpleIOStream (input_stream, output_stream);
+                           this.subprocess_stream = new SimpleIOStream (input_stream, output_stream);
                        this.accept_io_stream ( this.subprocess_stream);
                        } catch (GLib.Error e) {
-                               this.log(LanguageClientAction.ERROR_START, e.message);
-                               GLib.debug("subprocess startup error %s", e.message);   
-                               this.onClose();
+                               GLib.debug("subprocess startup error %s", e.message);           
                                return false;
                }
             return true;
         }
-        bool in_close = false;
-               protected void onClose()
-               {
-                       if (this.in_close) {
-                               return;
-                       }
-                       if (this.launcher == null) {
-                               return;
-                       }
-                       this.in_close = true;
-                       GLib.debug("onClose called");
-                       
-                       if (this.jsonrpc_client != null) {
-                               try {
-                                       this.jsonrpc_client.close();
-                               } catch (GLib.Error e) {
-                                       GLib.debug("rpc Error close error %s", e.message);      
-                               }               
-                       }
-                       if (this.subprocess_stream != null) {
-                               try {
-                                       this.subprocess_stream.close();
-                               } catch (GLib.Error e) {
-                                       GLib.debug("stream Error close  %s", e.message);        
-                               }               
-                       }
-                       if (this.subprocess != null) {
-                               this.subprocess.force_exit();
-                       }
-                       if (this.launcher != null) {
-                               this.launcher.close();
-                       }
-                       
-                       this.launcher = null;
-                       this.subprocess = null;
-                       this.jsonrpc_client = null;
-                       this.closed = true;             
-                       this.in_close = false;
-               }
+        
                /**
                utility method to build variant based queries
                */
@@ -199,16 +77,13 @@ namespace Palete {
                                this.jsonrpc_client = client;
                                
                                GLib.debug("client accepted connection - calling init server");
-                               this.log(LanguageClientAction.ACCEPT, "client accepted");
+                                
 
                                this.jsonrpc_client.notification.connect((method, paramz) => {
                                        this.onNotification(method, paramz);
                                });
                                 
                                this.jsonrpc_client.failed.connect(() => {
-                                       this.log(LanguageClientAction.ERROR_RPC, "client failed");
-                                       this.onClose();
-                                       
                                        GLib.debug("language server server has failed");
                                });
 
@@ -219,19 +94,6 @@ namespace Palete {
                }
                public bool isReady()
                {
-                       if (this.closed) {
-                               this.log(LanguageClientAction.RESTART,"closed is set - restarting");
-                               GLib.debug("server stopped = restarting");
-                               this.initialized = false;
-                               this.closed = false;
-                               this.startServer();
-                               foreach(var f in this.open_files) {
-                                       this.document_open(f);
-                               }
-                               return false; // can't do an operation yet?
-                                
-                       }
-                       
                        if (!this.initialized) {
                                GLib.debug("Server has not been initialized");
                                return false;
@@ -240,19 +102,16 @@ namespace Palete {
                                GLib.debug("Server has been started its shutting down process");
                                return false;
                        }
-                       // restart server..
-
-                       
-                       
                        return true;
                }
                
                
                public abstract  void initialize_server();
-               public abstract  void startServer();
+               
                //public abstract   void  initialize_server()  ;
                 
-               
+               protected bool initialized = false;
+               bool sent_shutdown = false;
                
                
                public void onNotification(string method, Variant? return_value)
@@ -274,13 +133,10 @@ namespace Palete {
                */
                public void onDiagnostic(Variant? return_value) 
                {
-
                        var dg = Json.gobject_deserialize (typeof (Lsp.Diagnostics), Json.gvariant_serialize (return_value)) as Lsp.Diagnostics; 
-                       this.log(LanguageClientAction.DIAG, dg.filename);
                        var f = this.project.getByPath(dg.filename);
                        if (f == null) {
-                               //GLib.debug("no file %s", dg.uri);
-                               this.project.updateErrorsforFile(null);
+                               GLib.debug("no file %s", dg.uri);
                                return;
                        }
                        foreach(var v in f.errorsByType.values) {
@@ -302,10 +158,6 @@ namespace Palete {
                        if (!this.isReady()) {
                                return;
                        }
-                       if (!this.open_files.contains(file)) {
-                               this.open_files.add(file);
-                       }
-                       
                        GLib.debug ("LS sent open");                     
                        try {
                                this.jsonrpc_client.send_notification (
@@ -320,10 +172,7 @@ namespace Palete {
                                        ),
                                        null
                                );
-                               this.log(LanguageClientAction.OPEN, file.path);
                        } catch( GLib.Error  e) {
-                               this.log(LanguageClientAction.ERROR_RPC, e.message);
-                               this.onClose();
                                GLib.debug ("LS sent open err %s", e.message);
                        }
 
@@ -334,24 +183,20 @@ namespace Palete {
                        if (!this.isReady()) {
                                return;
                        }
-                       this.change_queue_file = null;
-                       GLib.debug ("LS send save");
+                               GLib.debug ("LS send save");
                         try {
                                  this.jsonrpc_client.send_notification  (
                                        "textDocument/didChange",
                                        this.buildDict (  
                                                textDocument : this.buildDict (    ///TextDocumentItem;
-                                                       uri: new GLib.Variant.string (file.to_url()),
-                                                       version :  new GLib.Variant.uint64 ( (uint64) file.version)
+                                                       uri: new GLib.Variant.string (file.to_url())
+                                                       
                                                )
                                        ),
                                        null 
                                );
-                               this.log(LanguageClientAction.SAVE, file.path);
                        } catch( GLib.Error  e) {
-                               this.log(LanguageClientAction.ERROR_RPC, e.message);
-                               GLib.debug ("LS   save err %s", e.message);
-                               this.onClose();
+                               GLib.debug ("LS sent save err %s", e.message);
                        }
 
          
@@ -361,13 +206,7 @@ namespace Palete {
                        if (!this.isReady()) {
                                return;
                        }
-                       this.change_queue_file = null;
-                       
-                       if (this.open_files.contains(file)) {
-                               this.open_files.remove(file);
-                       }
-                       this.log(LanguageClientAction.CLOSE, file.path);
-                       GLib.debug ("LS send close");
+                                                       GLib.debug ("LS send close");
                        try {
                                  this.jsonrpc_client.send_notification  (
                                        "textDocument/didChange",
@@ -380,44 +219,23 @@ namespace Palete {
                                        null  
                                );
                        } catch( GLib.Error  e) {
-                               this.log(LanguageClientAction.ERROR_RPC, e.message);
-                               GLib.debug ("LS close err %s", e.message);
-                               this.onClose();
+                               GLib.debug ("LS sent close err %s", e.message);
                        }
 
          
        }
-       
-        
-               public void document_change (JsRender.JsRender file   )    
-               {
-                       if (this.change_queue_file != null && this.change_queue_file.path != file.path) {
-                               this.document_change_real(this.change_queue_file, this.change_queue_file_source);
-                       }
-                       
-                       this.countdown = 3;
-                       this.change_queue_file = file;
-                        
-                       
-
-               }
-       
-
-               public void document_change_real (JsRender.JsRender file, string contents)  
+               public    void document_change (JsRender.JsRender file)  
        {
                        if (!this.isReady()) {
                                return;
                        }
-                            
-                       
                        GLib.debug ("LS send change");
                        var ar = new Json.Array();
                        var obj = new Json.Object();
-                       obj.set_string_member("text", contents);
+                       obj.set_string_member("text", file.toSource());
                        ar.add_object_element(obj);
                        var node = new Json.Node(Json.NodeType.ARRAY);
                        node.set_array(ar);
-                       this.log(LanguageClientAction.CHANGE, file.path);
                         try {
                                this.jsonrpc_client.send_notification (
                                        "textDocument/didChange",
@@ -432,37 +250,30 @@ namespace Palete {
                                        null 
                                );
                        } catch( GLib.Error  e) {
-                               this.log(LanguageClientAction.ERROR_RPC, e.message);
-                               GLib.debug ("LS change err %s", e.message);
-                               this.onClose();
+                               GLib.debug ("LS sent close err %s", e.message);
                        }
 
          
        }
-       // called by close window (on last window)...
                public   void exit () throws GLib.Error 
                {
                        if (!this.isReady()) {
-                       
                                return;
                        }
-                       this.log(LanguageClientAction.TERM, "SEND exit");
+                       this.sent_shutdown  = true;
                 
-                         this.jsonrpc_client.send_notification (
+                         this.jsonrpc_client.send_notification_async (
                                "exit",
                                null,
                                null 
                        );
-                       this.onClose();
-
-               }
-               // not used currently..
+                       
+               }
                public async void shutdown () throws GLib.Error 
                {
                        if (!this.isReady()) {
                                return;
                        }
-                       this.log(LanguageClientAction.TERM, "SEND shutodwn");
                        this.sent_shutdown  = true;
                        Variant? return_value;
                        yield this.jsonrpc_client.call_async (
@@ -481,27 +292,19 @@ namespace Palete {
                
                @triggerType 1 = typing or ctl-spac, 2 = tiggercharactres?  3= inside completion?
                */
-                public async Lsp.CompletionList?  completion(JsRender.JsRender file, int line, int offset , int triggerType = 1) throws GLib.Error 
+                public async void completion (JsRender.JsRender file, int line, int offset , int triggerType = 1, out Lsp.CompletionList? ret) throws GLib.Error 
                 {
                        /* partial_result_token ,  work_done_token   context = null) */
                        GLib.debug("get completion %s @ %d:%d", file.relpath, line, offset);
                        
-                       var ret = new Lsp.CompletionList();     
-                       
+                       ret = null;
                    if (!this.isReady()) {
-                       GLib.debug("completion - language server not ready");
-                               return ret;
+                               return;
                        }
-                       // make sure completion has the latest info..
-                       //if (this.change_queue_file != null && this.change_queue_file.path != file.path) {
-                       //      this.document_change_real(this.change_queue_file, this.change_queue_file_source);
-                       //      this.change_queue_file != null;
-                       //}
-                       this.log(LanguageClientAction.COMPLETE, "SEND complete  %s @ %d:%d".printf(file.relpath, line, offset) );
-                       
                        Variant? return_value;
-                       
-                       var args = this.buildDict (  
+                       yield this.jsonrpc_client.call_async (
+                               "textDocument/completion",
+                               this.buildDict (  
                                        context : this.buildDict (    ///CompletionContext;
                                                triggerKind: new GLib.Variant.int32 (triggerType) 
                                        //      triggerCharacter :  new GLib.Variant.string ("")
@@ -511,16 +314,10 @@ namespace Palete {
                                                version :  new GLib.Variant.uint64 ( (uint64) file.version) 
                                        ), 
                                        position :  this.buildDict ( 
-                                               line :  new GLib.Variant.uint64 ( (uint) line) ,
-                                               character :  new GLib.Variant.uint64 ( uint.max(0,  (offset -1))
+                                               line :  new GLib.Variant.uint64 ( (uint64) line) ,
+                                               character :  new GLib.Variant.uint64 ( (uint64) offset
                                        )
-                               );
-                        
-                       GLib.debug ("textDocument/completion send with %s", Json.to_string (Json.gvariant_serialize (args), true));                                     
-                       
-                       yield this.jsonrpc_client.call_async (
-                               "textDocument/completion",
-                               args,
+                               ),
                                null,
                                out return_value
                        );
@@ -528,76 +325,26 @@ namespace Palete {
                        
                        //GLib.debug ("LS replied with %s", Json.to_string (Json.gvariant_serialize (return_value), true));                                     
                        var json = Json.gvariant_serialize (return_value);
+                       var ar = json.get_array();
 
-
-                       if (json.get_node_type() == Json.NodeType.OBJECT) {
+                       if (ar == null) {
                                ret = Json.gobject_deserialize (typeof (Lsp.CompletionList), json) as Lsp.CompletionList; 
-                               this.log(LanguageClientAction.COMPLETE_REPLY, "GOT complete  %d items".printf(ret.items.size) );
-                               GLib.debug ("LS replied with Object");
-                               return ret;
+                               return;
                        }  
-
-                       if (json.get_node_type() != Json.NodeType.ARRAY) {
-                               GLib.debug ("LS replied with %s", Json.to_string (Json.gvariant_serialize (return_value), true));                                       
-                               this.log(LanguageClientAction.ERROR_REPLY, "GOT something else??");
-                               return ret;
-                       
-                       }
-                       var ar = json.get_array();                      
-                       
+                       ret = new Lsp.CompletionList(); 
                        for(var i = 0; i < ar.get_length(); i++ ) {
                                var add= Json.gobject_deserialize ( typeof (Lsp.CompletionItem),  ar.get_element(i)) as Lsp.CompletionItem;
                                ret.items.add( add);
                                         
                        }
-                       this.log(LanguageClientAction.COMPLETE_REPLY, "GOT array %d items".printf(ret.items.size) );
-                       GLib.debug ("LS replied with Array");
-                       return ret;
+                                 
+                       
                
 
                }
                //CompletionListInfo.itmems.parse_varient  or CompletionListInfo.parsevarient
-               public async Gee.ArrayList<Lsp.DocumentSymbol> syntax (JsRender.JsRender file) throws GLib.Error 
-                {
-                       /* partial_result_token ,  work_done_token   context = null) */
-                       GLib.debug("get syntax %s", file.relpath);
-                       var ret = new Gee.ArrayList<Lsp.DocumentSymbol>();      
-                       //ret = null;
-                   if (!this.isReady()) {
-                               return ret;
-                       }
-                       Variant? return_value;
-                       yield this.jsonrpc_client.call_async (
-                               "textDocument/documentSymbol",
-                               this.buildDict (  
-                                        
-                                       textDocument : this.buildDict (    ///TextDocumentItem;
-                                               uri: new GLib.Variant.string (file.to_url()),
-                                               version :  new GLib.Variant.uint64 ( (uint64) file.version) 
-                                       ) 
-                                        
-                               ),
-                               null,
-                               out return_value
-                       );
-                       
-                       
-                       GLib.debug ("LS replied with %s", Json.to_string (Json.gvariant_serialize (return_value), true));                                       
-                       var json = Json.gvariant_serialize (return_value);
-                        
-                        
 
-                       var ar = json.get_array();
-                       for(var i = 0; i < ar.get_length(); i++ ) {
-                               var add= Json.gobject_deserialize ( typeof (Lsp.DocumentSymbol),  ar.get_element(i)) as Lsp.DocumentSymbol;
-                               ret.add( add);
-                                        
-                       }
-                               return ret ;
-                       
-               
 
-               }
                
        }
 }