def start_process(self, conf_path, classpath, cache_dir, java_home, java_flags): Util.mkdir_p(cache_dir) log_path = os.path.join(cache_dir, "server.log") log = open(log_path, "w") null = open("/dev/null", "r") args = ( [os.path.join(java_home, "bin", "java")] + ["-cp", classpath] + [a for a in java_flags.split(" ") if a != ""] + ["-Densime.config={}".format(conf_path), "org.ensime.server.Server"]) process = subprocess.Popen( args, stdin=null, stdout=log, stderr=subprocess.STDOUT) pid_path = os.path.join(cache_dir, "server.pid") Util.write_file(pid_path, str(process.pid)) def on_stop(): log.close() with catch(Exception, lambda e: None): os.remove(pid_path) return EnsimeProcess(cache_dir, process, log_path, on_stop)
def start_process(self, classpath): cache_dir = self.config['cache-dir'] java_flags = self.config['java-flags'] Util.mkdir_p(cache_dir) log_path = os.path.join(cache_dir, "server.log") log = open(log_path, "w") null = open(os.devnull, "r") java = os.path.join(self.config['java-home'], 'bin', 'java') if not os.path.exists(java): raise InvalidJavaPathError(errno.ENOENT, 'No such file or directory', java) elif not os.access(java, os.X_OK): raise InvalidJavaPathError(errno.EACCES, 'Permission denied', java) args = ([java, "-cp", classpath] + [a for a in java_flags if a != ""] + [ "-Densime.config={}".format(self._config_path), "org.ensime.server.Server" ]) process = subprocess.Popen(args, stdin=null, stdout=log, stderr=subprocess.STDOUT) pid_path = os.path.join(cache_dir, "server.pid") Util.write_file(pid_path, str(process.pid)) def on_stop(): log.close() null.close() with catch(Exception, lambda e: None): os.remove(pid_path) return EnsimeProcess(cache_dir, process, log_path, on_stop)
def start_process(self, classpath): cache_dir = self.config['cache-dir'] java_flags = self.config['java-flags'] Util.mkdir_p(cache_dir) log_path = os.path.join(cache_dir, "server.log") log = open(log_path, "w") null = open("/dev/null", "r") java = os.path.join(self.config['java-home'], 'bin', 'java') if not os.path.exists(java): raise InvalidJavaPathError(errno.ENOENT, 'No such file or directory', java) elif not os.access(java, os.X_OK): raise InvalidJavaPathError(errno.EACCES, 'Permission denied', java) args = ( [java, "-cp", classpath] + [a for a in java_flags if a != ""] + ["-Densime.config={}".format(self._config_path), "org.ensime.server.Server"]) process = subprocess.Popen( args, stdin=null, stdout=log, stderr=subprocess.STDOUT) pid_path = os.path.join(cache_dir, "server.pid") Util.write_file(pid_path, str(process.pid)) def on_stop(): log.close() with catch(Exception, lambda e: None): os.remove(pid_path) return EnsimeProcess(cache_dir, process, log_path, on_stop)
def __init__(self, vim, launcher, config_path): def setup_neovim(): """Set up neovim and execute global commands.""" self.vim = vim self.vim_command("highlight_enerror") if not self.vim_eval("exists_enerrorstyle"): self.vim_command("set_enerrorstyle") self.vim_command("set_updatetime") self.vim_command("set_ensime_completion") def setup_logger_and_paths(): """Set up paths and logger.""" osp = os.path self.config_path = osp.abspath(config_path) config_dirname = osp.dirname(self.config_path) self.ensime_cache = osp.join(config_dirname, ".ensime_cache") self.log_dir = self.ensime_cache \ if osp.isdir(self.ensime_cache) else "/tmp/" self.log_file = os.path.join(self.log_dir, "ensime-vim.log") setup_logger_and_paths() setup_neovim() self.log("__init__: in") self.ws = None self.ensime = None self.launcher = launcher self.ensime_server = None self.call_id = 0 self.call_options = {} self.refactor_id = 1 self.refactorings = {} self.receive_callbacks = {} self.matches = [] self.errors = [] self.queue = Queue() self.suggestions = None self.completion_timeout = 10 #seconds self.completion_started = False self.en_format_source_id = None self.enable_fulltype = False self.enable_teardown = True self.connection_attempts = 0 self.tmp_diff_folder = "/tmp/ensime-vim/diffs/" Util.mkdir_p(self.tmp_diff_folder) self.debug_thread_id = None self.running = True Thread(target=self.queue_poll, args=()).start() self.handlers = {} self.register_responses_handlers() self.websocket_exists = module_exists("websocket") if not self.websocket_exists: self.tell_module_missing("websocket-client")
def install(self): """Installs ENSIME server with a bootstrap sbt project and generates its classpath.""" project_dir = os.path.dirname(self.classpath_file) sbt_plugin = """addSbtPlugin("{0}" % "{1}" % "{2}")""" Util.mkdir_p(project_dir) Util.mkdir_p(os.path.join(project_dir, "project")) Util.write_file( os.path.join(project_dir, "build.sbt"), self.build_sbt()) Util.write_file( os.path.join(project_dir, "project", "build.properties"), "sbt.version={}".format(self.SBT_VERSION)) Util.write_file( os.path.join(project_dir, "project", "plugins.sbt"), sbt_plugin.format(*self.SBT_COURSIER_COORDS)) # Synchronous update of the classpath via sbt # see https://github.com/ensime/ensime-vim/issues/29 cd_cmd = "cd {}".format(project_dir) sbt_cmd = "sbt -Dsbt.log.noformat=true -batch saveClasspath" if int(self.vim.eval("has('nvim')")): import tempfile import re tmp_dir = tempfile.gettempdir() flag_file = "{}/ensime-vim-classpath.flag".format(tmp_dir) self.vim.command("echo 'Waiting for generation of classpath...'") if re.match(".+fish$", self.vim.eval("&shell")): sbt_cmd += "; echo $status > {}".format(flag_file) self.vim.command("terminal {}; and {}".format(cd_cmd, sbt_cmd)) else: sbt_cmd += "; echo $? > {}".format(flag_file) self.vim.command("terminal ({} && {})".format(cd_cmd, sbt_cmd)) # Block execution when sbt is run waiting_for_flag = True while waiting_for_flag: waiting_for_flag = not os.path.isfile(flag_file) if not waiting_for_flag: with open(flag_file, "r") as f: rtcode = f.readline() os.remove(flag_file) if rtcode and int(rtcode) != 0: # error self.vim.command( "echo 'Something wrong happened, check the " "execution log...'") return None else: time.sleep(0.2) else: self.vim.command("!({} && {})".format(cd_cmd, sbt_cmd)) success = self.reorder_classpath(self.classpath_file) if not success: self.vim.command("echo 'Classpath ordering failed.'") return True
def generate_classpath(self, scala_version, classpath_file): project_dir = self.classpath_project_dir(scala_version) Util.mkdir_p(project_dir) Util.mkdir_p(os.path.join(project_dir, "project")) Util.write_file( os.path.join(project_dir, "build.sbt"), self.build_sbt(scala_version, classpath_file)) Util.write_file( os.path.join(project_dir, "project", "build.properties"), "sbt.version={}".format(self.sbt_version)) Util.write_file( os.path.join(project_dir, "project", "plugins.sbt"), """addSbtPlugin("io.get-coursier" % "sbt-coursier" % "1.0.0-M11")""") # Synchronous update of the classpath via sbt # see https://github.com/ensime/ensime-vim/issues/29 cd_cmd = "cd {}".format(project_dir) sbt_cmd = "sbt -Dsbt.log.noformat=true -batch saveClasspath" inside_nvim = int(self.vim.eval("has('nvim')")) if inside_nvim: import tempfile import re tmp_dir = tempfile.gettempdir() flag_file = "{}/ensime-vim-classpath.flag".format(tmp_dir) self.vim.command("echo 'Waiting for generation of classpath...'") if re.match(".+fish$", self.vim.eval("&shell")): sbt_cmd += "; echo $status > {}".format(flag_file) self.vim.command("terminal {}; and {}".format(cd_cmd, sbt_cmd)) else: sbt_cmd += "; echo $? > {}".format(flag_file) self.vim.command("terminal ({} && {})".format(cd_cmd, sbt_cmd)) # Block execution when sbt is run waiting_for_flag = True while waiting_for_flag: waiting_for_flag = not os.path.isfile(flag_file) if not waiting_for_flag: with open(flag_file, "r") as f: rtcode = f.readline() os.remove(flag_file) if rtcode and int(rtcode) != 0: # error self.vim.command( "echo 'Something wrong happened, check the " "execution log...'") return None else: time.sleep(0.2) else: self.vim.command("!({} && {})".format(cd_cmd, sbt_cmd)) success = self.reorder_classpath(classpath_file) if not success: self.vim.command("echo 'Classpath ordering failed.'") return True
def generate_classpath(self, scala_version, classpath_file): project_dir = self.classpath_project_dir(scala_version) Util.mkdir_p(project_dir) Util.mkdir_p(os.path.join(project_dir, "project")) Util.write_file(os.path.join(project_dir, "build.sbt"), self.build_sbt(scala_version, classpath_file)) Util.write_file(os.path.join(project_dir, "project", "build.properties"), "sbt.version={}".format(self.sbt_version)) log_file = os.path.join(project_dir, "build.log") log = open(log_file, 'w') null = open("/dev/null", "r") # see https://github.com/ensime/ensime-vim/issues/29 on why we use this method self.vim.command("!(cd {};sbt -Dsbt.log.noformat=true -batch saveClasspath)".format(project_dir))
def _start_process(self, classpath): """Given a classpath prepared for running ENSIME, spawns a server process in a way that is otherwise agnostic to how the strategy installs ENSIME. Args: classpath (list of str): list of paths to jars or directories (Within this function the list is joined with a system dependent path separator to create a single string argument to suitable to pass to ``java -cp`` as a classpath) Returns: EnsimeProcess: A process handle for the launched server. """ cache_dir = self.config['cache-dir'] java_flags = self.config['java-flags'] Util.mkdir_p(cache_dir) log_path = os.path.join(cache_dir, "server.log") log = open(log_path, "w") null = open(os.devnull, "r") java = os.path.join(self.config['java-home'], 'bin', 'java' if os.name != 'nt' else 'java.exe') if not os.path.exists(java): raise InvalidJavaPathError(errno.ENOENT, 'No such file or directory', java) elif not os.access(java, os.X_OK): raise InvalidJavaPathError(errno.EACCES, 'Permission denied', java) args = ( [java, "-cp", (':' if os.name != 'nt' else ';').join(classpath)] + [a for a in java_flags if a] + [ "-Densime.config={}".format(self.config.filepath), "org.ensime.server.Server" ]) process = subprocess.Popen(args, stdin=null, stdout=log, stderr=subprocess.STDOUT) pid_path = os.path.join(cache_dir, "server.pid") Util.write_file(pid_path, str(process.pid)) def on_stop(): log.close() null.close() with catch(Exception): os.remove(pid_path) return EnsimeProcess(cache_dir, process, log_path, on_stop)
def _start_process(self, classpath): """Given a classpath prepared for running ENSIME, spawns a server process in a way that is otherwise agnostic to how the strategy installs ENSIME. Args: classpath (list of str): list of paths to jars or directories (Within this function the list is joined with a system dependent path separator to create a single string argument suitable to pass to ``java -cp`` as a classpath) Returns: EnsimeProcess: A process handle for the launched server. """ cache_dir = self.config['cache-dir'] java_flags = self.config['java-flags'] iswindows = os.name == 'nt' Util.mkdir_p(cache_dir) log_path = os.path.join(cache_dir, "server.log") log = open(log_path, "w") null = open(os.devnull, "r") java = os.path.join(self.config['java-home'], 'bin', 'java.exe' if iswindows else 'java') if not os.path.exists(java): raise InvalidJavaPathError(errno.ENOENT, 'No such file or directory', java) elif not os.access(java, os.X_OK): raise InvalidJavaPathError(errno.EACCES, 'Permission denied', java) args = ( [java, "-cp", (';' if iswindows else ':').join(classpath)] + [a for a in java_flags if a] + ["-Densime.config={}".format(self.config.filepath), "org.ensime.server.Server"]) process = subprocess.Popen( args, stdin=null, stdout=log, stderr=subprocess.STDOUT) pid_path = os.path.join(cache_dir, "server.pid") Util.write_file(pid_path, str(process.pid)) def on_stop(): log.close() null.close() with catch(Exception): os.remove(pid_path) return EnsimeProcess(cache_dir, process, log_path, on_stop)
def __init__(self, vim, launcher, config_path): def setup_vim(): """Set up vim and execute global commands.""" self.vim = vim if not int(self.vim_eval("exists_enerrorstyle")): self.vim_command("set_enerrorstyle") self.vim_command("highlight_enerror") self.vim_command("set_updatetime") self.vim_command("set_ensime_completion") self.vim.command( "autocmd FileType package_info nnoremap <buffer> <Space> :call EnPackageDecl()<CR>" ) self.vim.command( "autocmd FileType package_info setlocal splitright") super(EnsimeClient, self).__init__() def setup_logger_and_paths(): """Set up paths and logger.""" osp = os.path self.config_path = osp.abspath(config_path) config_dirname = osp.dirname(self.config_path) self.ensime_cache = osp.join(config_dirname, ".ensime_cache") self.log_dir = self.ensime_cache if not osp.isdir(self.ensime_cache): try: os.mkdir(self.ensime_cache) except OSError: self.log_dir = "/tmp/" self.log_file = os.path.join(self.log_dir, "ensime-vim.log") with open(self.log_file, "w") as f: now = datetime.datetime.now() tm = now.strftime("%Y-%m-%d %H:%M:%S.%f") f.write("{}: {} - {}\n".format(tm, "Initializing project", config_dirname)) def fetch_runtime_paths(): """Fetch all the runtime paths of ensime-vim plugin.""" paths = self.vim_eval("runtimepath") tag = "ensime-vim" ps = [p for p in paths.split(',') if tag in p] home = os.environ.get("HOME") if home: ps = map(lambda s: s.replace(home, "~"), ps) return ps setup_logger_and_paths() setup_vim() self.log("__init__: in") self.ws = None self.ensime = None self.launcher = launcher self.ensime_server = None self.call_id = 0 self.call_options = {} self.refactor_id = 1 self.refactorings = {} self.receive_callbacks = {} self.matches = [] self.errors = [] # Queue for messages received from the ensime server. self.queue = Queue() self.suggestions = None self.completion_timeout = 10 # seconds self.completion_started = False self.en_format_source_id = None self.full_types_enabled = False """Whether fully-qualified types are displayed by inspections or not""" self.toggle_teardown = True self.connection_attempts = 0 self.tmp_diff_folder = "/tmp/ensime-vim/diffs/" Util.mkdir_p(self.tmp_diff_folder) # Set the runtime path here in case we need # to disable the plugin. It needs to be done # beforehand since vim.eval is not threadsafe self.runtime_paths = fetch_runtime_paths() # By default, don't connect to server more than once self.number_try_connection = 1 self.debug_thread_id = None self.running = True thread = Thread(target=self.queue_poll, args=()) thread.daemon = True thread.start() self.handlers = {} self.register_responses_handlers() self.websocket_exists = module_exists("websocket") if not self.websocket_exists: self.tell_module_missing("websocket-client") if not module_exists("sexpdata"): self.tell_module_missing("sexpdata")
def __init__(self, vim, launcher, config_path): def setup_vim(): """Set up vim and execute global commands.""" self.vim = vim if not int(self.vim_eval("exists_enerrorstyle")): self.vim_command("set_enerrorstyle") self.vim_command("highlight_enerror") self.vim_command("set_updatetime") self.vim_command("set_ensime_completion") def setup_logger_and_paths(): """Set up paths and logger.""" osp = os.path self.config_path = osp.abspath(config_path) config_dirname = osp.dirname(self.config_path) self.ensime_cache = osp.join(config_dirname, ".ensime_cache") self.log_dir = self.ensime_cache \ if osp.isdir(self.ensime_cache) else "/tmp/" self.log_file = os.path.join(self.log_dir, "ensime-vim.log") def fetch_runtime_paths(): """Fetch all the runtime paths of ensime-vim plugin.""" paths = self.vim_eval("runtimepath") tag = "ensime-vim" ps = [p for p in paths.split(',') if tag in p] home = os.environ.get("HOME") if home: ps = map(lambda s: s.replace(home, "~"), ps) return ps setup_logger_and_paths() setup_vim() self.log("__init__: in") self.ws = None self.ensime = None self.launcher = launcher self.ensime_server = None self.call_id = 0 self.call_options = {} self.refactor_id = 1 self.refactorings = {} self.receive_callbacks = {} self.matches = [] self.errors = [] self.queue = Queue() self.suggestions = None self.completion_timeout = 10 # seconds self.completion_started = False self.en_format_source_id = None self.enable_fulltype = False self.toggle_teardown = True self.connection_attempts = 0 self.tmp_diff_folder = "/tmp/ensime-vim/diffs/" Util.mkdir_p(self.tmp_diff_folder) # Set the runtime path here in case we need # to disable the plugin. It needs to be done # beforehand since vim.eval is not threadsafe self.runtime_paths = fetch_runtime_paths() # By default, don't connect to server more than once self.number_try_connection = 1 self.debug_thread_id = None self.running = True Thread(target=self.queue_poll, args=()).start() self.handlers = {} self.register_responses_handlers() self.websocket_exists = module_exists("websocket") if not self.websocket_exists: self.tell_module_missing("websocket-client")
def __init__(self, vim, launcher, config_path): def setup_vim(): """Set up vim and execute global commands.""" self.vim = vim if not int(self.vim_eval("exists_enerrorstyle")): self.vim_command("set_enerrorstyle") self.vim_command("highlight_enerror") self.vim_command("set_updatetime") self.vim_command("set_ensime_completion") self.vim.command("autocmd FileType package_info nnoremap <buffer> <Space> :call EnPackageDecl()<CR>") self.vim.command("autocmd FileType package_info setlocal splitright") super(EnsimeClient, self).__init__() def setup_logger_and_paths(): """Set up paths and logger.""" osp = os.path self.config_path = osp.abspath(config_path) config_dirname = osp.dirname(self.config_path) self.ensime_cache = osp.join(config_dirname, ".ensime_cache") self.log_dir = self.ensime_cache if not osp.isdir(self.ensime_cache): try: os.mkdir(self.ensime_cache) except OSError: self.log_dir = "/tmp/" self.log_file = os.path.join(self.log_dir, "ensime-vim.log") with open(self.log_file, "w") as f: now = datetime.datetime.now() tm = now.strftime("%Y-%m-%d %H:%M:%S.%f") f.write("{}: {} - {}\n".format(tm, "Initializing project", config_dirname)) def fetch_runtime_paths(): """Fetch all the runtime paths of ensime-vim plugin.""" paths = self.vim_eval("runtimepath") tag = "ensime-vim" ps = [p for p in paths.split(',') if tag in p] home = os.environ.get("HOME") if home: ps = map(lambda s: s.replace(home, "~"), ps) return ps setup_logger_and_paths() setup_vim() self.log("__init__: in") self.ws = None self.ensime = None self.launcher = launcher self.ensime_server = None self.call_id = 0 self.call_options = {} self.refactor_id = 1 self.refactorings = {} self.receive_callbacks = {} self.matches = [] self.errors = [] # Queue for messages received from the ensime server. self.queue = Queue() self.suggestions = None self.completion_timeout = 10 # seconds self.completion_started = False self.en_format_source_id = None self.full_types_enabled = False """Whether fully-qualified types are displayed by inspections or not""" self.toggle_teardown = True self.connection_attempts = 0 self.tmp_diff_folder = "/tmp/ensime-vim/diffs/" Util.mkdir_p(self.tmp_diff_folder) # Set the runtime path here in case we need # to disable the plugin. It needs to be done # beforehand since vim.eval is not threadsafe self.runtime_paths = fetch_runtime_paths() # By default, don't connect to server more than once self.number_try_connection = 1 self.debug_thread_id = None self.running = True thread = Thread(target=self.queue_poll, args=()) thread.daemon = True thread.start() self.handlers = {} self.register_responses_handlers() self.websocket_exists = module_exists("websocket") if not self.websocket_exists: self.tell_module_missing("websocket-client") if not module_exists("sexpdata"): self.tell_module_missing("sexpdata")