def run(self, **kwargs): with self.chdir(kwargs.get('working_dir')): p = os.path.join(os.getcwd(), 'tests') patt = kwargs.get('loader_pattern', 'test*.py',) # TODO(guillermooo): I can't get $file to expand in the build # system. It should be possible to make the following code simpler # with it. if kwargs.get('active_file_only') is True: patt = os.path.basename(self.window.active_view().file_name()) suite = unittest.TestLoader().discover(p, pattern=patt) file_regex = r'^\s*File\s*"([^.].*?)",\s*line\s*(\d+),.*$' display = OutputPanel('fs.tests', file_regex=file_regex) display.show() runner = unittest.TextTestRunner(stream=display, verbosity=1) def run_and_display(): runner.run(suite) threading.Thread(target=run_and_display).start()
def run(self, **kwargs): with self.chdir(kwargs.get('working_dir')): p = os.path.join(os.getcwd(), 'tests') patt = kwargs.get( 'loader_pattern', 'test*.py', ) # TODO(guillermooo): I can't get $file to expand in the build # system. It should be possible to make the following code simpler # with it. if kwargs.get('active_file_only') is True: patt = os.path.basename(self.window.active_view().file_name()) suite = unittest.TestLoader().discover(p, pattern=patt) file_regex = r'^\s*File\s*"([^.].*?)",\s*line\s*(\d+),.*$' display = OutputPanel('fs.tests', file_regex=file_regex) display.show() runner = unittest.TextTestRunner(stream=display, verbosity=1) def run_and_display(): runner.run(suite) threading.Thread(target=run_and_display).start()
def process_resp(data): _logger.debug ('processing response data: %s', data) if data ['Kind'] == 'compilerlocation': r = CompilerLocationResponse (data) editor_context.compilers_path = r.compilers_path return if data['Kind'] == 'project': r = ProjectResponse(data) panel = OutputPanel (name='fs.out') panel.write ("Files in project:\n") panel.write ("\n") panel.write ('\n'.join(r.files)) panel.show() return if data['Kind'] == 'errors' and data['Data']: panel = OutputPanel (name='fs.out') panel.write (str(data)) panel.write ("\n") panel.show() return if data['Kind'] == 'INFO' and data['Data']: print(str(data)) return if data['Kind'] == 'declarations' and data['Data']: decls = DeclarationsResponse(data) its = [decl.to_menu_data() for decl in decls.declarations] w = sublime.active_window() w.run_command ('fs_show_menu', {'items': its}) return
def run( self, cmd=None, shell_cmd=None, file_regex="", line_regex="", working_dir="", encoding="utf-8", env={}, quiet=False, kill=False, word_wrap=True, syntax="Packages/Text/Plain text.tmLanguage", preamble="", panel_name="fs.out", # Catches "path" and "shell" **kwargs ): if kill: if hasattr(self, "proc") and self.proc: self.proc.kill() self.proc = None self.append_string(None, "[Cancelled]") return # TODO(guillermooo): We cannot have multiple processes running at the # same time, or processes that use separate output panels. if not hasattr(self, "out_panel"): # Try not to call get_output_panel until the regexes are assigned self.out_panel = OutputPanel(panel_name) # Default to the current files directory if no working directory was given if not working_dir and self.window.active_view() and self.window.active_view().file_name(): working_dir = os.path.dirname(self.window.active_view().file_name()) self.out_panel.set("result_file_regex", file_regex) self.out_panel.set("result_line_regex", line_regex) self.out_panel.set("result_base_dir", working_dir) self.out_panel.set("word_wrap", word_wrap) self.out_panel.set("line_numbers", False) self.out_panel.set("gutter", False) self.out_panel.set("scroll_past_end", False) self.out_panel.view.assign_syntax(syntax) self.encoding = encoding self.quiet = quiet self.proc = None if not self.quiet: if shell_cmd: print("Running " + shell_cmd) else: print("Running " + " ".join(cmd)) sublime.status_message("Building") if preamble: self.append_string(self.proc, preamble) show_panel_on_build = sublime.load_settings("Dart - Plugin Settings.sublime-settings").get( "show_panel_on_build", True ) if show_panel_on_build: self.out_panel.show() merged_env = env.copy() if self.window.active_view(): user_env = self.window.active_view().settings().get("build_env") if user_env: merged_env.update(user_env) # Change to the working dir, rather than spawning the process with it, # so that emitted working dir relative path names make sense if working_dir: os.chdir(working_dir) self.debug_text = "" if shell_cmd: self.debug_text += "[shell_cmd: " + shell_cmd + "]\n" else: self.debug_text += "[cmd: " + str(cmd) + "]\n" self.debug_text += "[dir: " + str(os.getcwd()) + "]\n" if "PATH" in merged_env: self.debug_text += "[path: " + str(merged_env["PATH"]) + "]" else: self.debug_text += "[path: " + str(os.environ["PATH"]) + "]" try: # Forward kwargs to AsyncProcess self.proc = AsyncProcess(cmd, shell_cmd, merged_env, self, **kwargs) except Exception as e: self.append_string(None, str(e) + "\n") self.append_string(None, self.debug_text + "\n") if not self.quiet: self.append_string(None, "[Finished]")
class fs_exec(sublime_plugin.WindowCommand, ProcessListener): def run( self, cmd=None, shell_cmd=None, file_regex="", line_regex="", working_dir="", encoding="utf-8", env={}, quiet=False, kill=False, word_wrap=True, syntax="Packages/Text/Plain text.tmLanguage", preamble="", panel_name="fs.out", # Catches "path" and "shell" **kwargs ): if kill: if hasattr(self, "proc") and self.proc: self.proc.kill() self.proc = None self.append_string(None, "[Cancelled]") return # TODO(guillermooo): We cannot have multiple processes running at the # same time, or processes that use separate output panels. if not hasattr(self, "out_panel"): # Try not to call get_output_panel until the regexes are assigned self.out_panel = OutputPanel(panel_name) # Default to the current files directory if no working directory was given if not working_dir and self.window.active_view() and self.window.active_view().file_name(): working_dir = os.path.dirname(self.window.active_view().file_name()) self.out_panel.set("result_file_regex", file_regex) self.out_panel.set("result_line_regex", line_regex) self.out_panel.set("result_base_dir", working_dir) self.out_panel.set("word_wrap", word_wrap) self.out_panel.set("line_numbers", False) self.out_panel.set("gutter", False) self.out_panel.set("scroll_past_end", False) self.out_panel.view.assign_syntax(syntax) self.encoding = encoding self.quiet = quiet self.proc = None if not self.quiet: if shell_cmd: print("Running " + shell_cmd) else: print("Running " + " ".join(cmd)) sublime.status_message("Building") if preamble: self.append_string(self.proc, preamble) show_panel_on_build = sublime.load_settings("Dart - Plugin Settings.sublime-settings").get( "show_panel_on_build", True ) if show_panel_on_build: self.out_panel.show() merged_env = env.copy() if self.window.active_view(): user_env = self.window.active_view().settings().get("build_env") if user_env: merged_env.update(user_env) # Change to the working dir, rather than spawning the process with it, # so that emitted working dir relative path names make sense if working_dir: os.chdir(working_dir) self.debug_text = "" if shell_cmd: self.debug_text += "[shell_cmd: " + shell_cmd + "]\n" else: self.debug_text += "[cmd: " + str(cmd) + "]\n" self.debug_text += "[dir: " + str(os.getcwd()) + "]\n" if "PATH" in merged_env: self.debug_text += "[path: " + str(merged_env["PATH"]) + "]" else: self.debug_text += "[path: " + str(os.environ["PATH"]) + "]" try: # Forward kwargs to AsyncProcess self.proc = AsyncProcess(cmd, shell_cmd, merged_env, self, **kwargs) except Exception as e: self.append_string(None, str(e) + "\n") self.append_string(None, self.debug_text + "\n") if not self.quiet: self.append_string(None, "[Finished]") def append_data(self, proc, data): if proc != self.proc: # a second call to exec has been made before the first one # finished, ignore it instead of intermingling the output. if proc: proc.kill() return try: str_ = data.decode(self.encoding) except UnicodeEncodeError: str_ = "[Decode error - output not " + self.encoding + "]\n" proc = None return # Normalize newlines, Sublime Text always uses a single \n separator # in memory. str_ = str_.replace("\r\n", "\n").replace("\r", "\n") self.out_panel.write(str_) def append_string(self, proc, str): self.append_data(proc, str.encode(self.encoding)) def finish(self, proc): if not self.quiet: elapsed = time.time() - proc.start_time exit_code = proc.exit_code() if (exit_code == 0) or (exit_code == None): self.append_string(proc, "[Finished in %.1fs]" % (elapsed)) else: self.append_string(proc, "[Finished in %.1fs with exit code %d]\n" % (elapsed, exit_code)) self.append_string(proc, self.debug_text) if proc != self.proc: return # XXX: What's this for? errs = self.out_panel.view.find_all_results() if len(errs) == 0: sublime.status_message("Build finished") else: sublime.status_message(("Build finished with %d errors") % len(errs)) def on_data(self, proc, data): after(0, functools.partial(self.append_data, proc, data)) def on_finished(self, proc): after(0, functools.partial(self.finish, proc))
def process_resp(data): _logger.debug('processing response data: %s', data) if data['Kind'] == 'compilerlocation': r = CompilerLocationResponse(data) raise_event(ON_COMPILER_PATH_AVAILABLE, {'response': r}) return if data['Kind'] == 'project': r = ProjectResponse(data) _logger.debug('\n'.join(r.files)) return if data['Kind'] == 'errors': # todo: enable error navigation via standard keys v = sublime.active_window().active_view() v.erase_regions('fs.errs') if not data['Data']: return v.add_regions( 'fs.errs', [ErrorInfo(e).to_region(v) for e in data['Data']], 'invalid.illegal', 'dot', sublime.DRAW_SQUIGGLY_UNDERLINE | sublime.DRAW_NO_FILL | sublime.DRAW_NO_OUTLINE) return if data['Kind'] == 'ERROR': _logger.error(str(data)) return if data['Kind'] == 'tooltip' and data['Data']: v = sublime.active_window().active_view() word = v.substr(v.word(v.sel()[0].b)) panel = OutputPanel('fs.out') panel.write(data['Data']) panel.show() return if data['Kind'] == 'INFO' and data['Data']: _logger.info(str(data)) print("FSharp:", data['Data']) return if data['Kind'] == 'finddecl' and data['Data']: fname = data['Data']['File'] row = data['Data']['Line'] col = data['Data']['Column'] + 1 w = sublime.active_window() # todo: don't open file if we are looking at the requested file target = '{0}:{1}:{2}'.format(fname, row, col) w.open_file(target, sublime.ENCODED_POSITION) return if data['Kind'] == 'declarations' and data['Data']: decls = DeclarationsResponse(data) its = [decl.to_menu_data() for decl in decls.declarations] w = sublime.active_window() w.run_command('fs_show_menu', {'items': its}) return if data['Kind'] == 'completion' and data['Data']: _logger.error( 'unexpected "completion" results - should be handled elsewhere') return
def run( self, cmd=None, shell_cmd=None, file_regex="", line_regex="", working_dir="", encoding="utf-8", env={}, quiet=False, kill=False, word_wrap=True, syntax="Packages/Text/Plain text.tmLanguage", preamble='', panel_name='fs.out', # Catches "path" and "shell" **kwargs): if kill: if hasattr(self, 'proc') and self.proc: self.proc.kill() self.proc = None self.append_string(None, "[Cancelled]") return # TODO(guillermooo): We cannot have multiple processes running at the # same time, or processes that use separate output panels. if not hasattr(self, 'out_panel'): # Try not to call get_output_panel until the regexes are assigned self.out_panel = OutputPanel(panel_name) # Default to the current files directory if no working directory was given if (not working_dir and self.window.active_view() and self.window.active_view().file_name()): working_dir = os.path.dirname( self.window.active_view().file_name()) self.out_panel.set("result_file_regex", file_regex) self.out_panel.set("result_line_regex", line_regex) self.out_panel.set("result_base_dir", working_dir) self.out_panel.set("word_wrap", word_wrap) self.out_panel.set("line_numbers", False) self.out_panel.set("gutter", False) self.out_panel.set("scroll_past_end", False) self.out_panel.view.assign_syntax(syntax) self.encoding = encoding self.quiet = quiet self.proc = None if not self.quiet: if shell_cmd: print("Running " + shell_cmd) else: print("Running " + " ".join(cmd)) sublime.status_message("Building") if preamble: self.append_string(self.proc, preamble) show_panel_on_build = sublime.load_settings( "Dart - Plugin Settings.sublime-settings").get( "show_panel_on_build", True) if show_panel_on_build: self.out_panel.show() merged_env = env.copy() if self.window.active_view(): user_env = self.window.active_view().settings().get('build_env') if user_env: merged_env.update(user_env) # Change to the working dir, rather than spawning the process with it, # so that emitted working dir relative path names make sense if working_dir: os.chdir(working_dir) self.debug_text = "" if shell_cmd: self.debug_text += "[shell_cmd: " + shell_cmd + "]\n" else: self.debug_text += "[cmd: " + str(cmd) + "]\n" self.debug_text += "[dir: " + str(os.getcwd()) + "]\n" if "PATH" in merged_env: self.debug_text += "[path: " + str(merged_env["PATH"]) + "]" else: self.debug_text += "[path: " + str(os.environ["PATH"]) + "]" try: # Forward kwargs to AsyncProcess self.proc = AsyncProcess(cmd, shell_cmd, merged_env, self, **kwargs) except Exception as e: self.append_string(None, str(e) + "\n") self.append_string(None, self.debug_text + "\n") if not self.quiet: self.append_string(None, "[Finished]")
class fs_exec(sublime_plugin.WindowCommand, ProcessListener): def run( self, cmd=None, shell_cmd=None, file_regex="", line_regex="", working_dir="", encoding="utf-8", env={}, quiet=False, kill=False, word_wrap=True, syntax="Packages/Text/Plain text.tmLanguage", preamble='', panel_name='fs.out', # Catches "path" and "shell" **kwargs): if kill: if hasattr(self, 'proc') and self.proc: self.proc.kill() self.proc = None self.append_string(None, "[Cancelled]") return # TODO(guillermooo): We cannot have multiple processes running at the # same time, or processes that use separate output panels. if not hasattr(self, 'out_panel'): # Try not to call get_output_panel until the regexes are assigned self.out_panel = OutputPanel(panel_name) # Default to the current files directory if no working directory was given if (not working_dir and self.window.active_view() and self.window.active_view().file_name()): working_dir = os.path.dirname( self.window.active_view().file_name()) self.out_panel.set("result_file_regex", file_regex) self.out_panel.set("result_line_regex", line_regex) self.out_panel.set("result_base_dir", working_dir) self.out_panel.set("word_wrap", word_wrap) self.out_panel.set("line_numbers", False) self.out_panel.set("gutter", False) self.out_panel.set("scroll_past_end", False) self.out_panel.view.assign_syntax(syntax) self.encoding = encoding self.quiet = quiet self.proc = None if not self.quiet: if shell_cmd: print("Running " + shell_cmd) else: print("Running " + " ".join(cmd)) sublime.status_message("Building") if preamble: self.append_string(self.proc, preamble) show_panel_on_build = sublime.load_settings( "Dart - Plugin Settings.sublime-settings").get( "show_panel_on_build", True) if show_panel_on_build: self.out_panel.show() merged_env = env.copy() if self.window.active_view(): user_env = self.window.active_view().settings().get('build_env') if user_env: merged_env.update(user_env) # Change to the working dir, rather than spawning the process with it, # so that emitted working dir relative path names make sense if working_dir: os.chdir(working_dir) self.debug_text = "" if shell_cmd: self.debug_text += "[shell_cmd: " + shell_cmd + "]\n" else: self.debug_text += "[cmd: " + str(cmd) + "]\n" self.debug_text += "[dir: " + str(os.getcwd()) + "]\n" if "PATH" in merged_env: self.debug_text += "[path: " + str(merged_env["PATH"]) + "]" else: self.debug_text += "[path: " + str(os.environ["PATH"]) + "]" try: # Forward kwargs to AsyncProcess self.proc = AsyncProcess(cmd, shell_cmd, merged_env, self, **kwargs) except Exception as e: self.append_string(None, str(e) + "\n") self.append_string(None, self.debug_text + "\n") if not self.quiet: self.append_string(None, "[Finished]") def append_data(self, proc, data): if proc != self.proc: # a second call to exec has been made before the first one # finished, ignore it instead of intermingling the output. if proc: proc.kill() return try: str_ = data.decode(self.encoding) except UnicodeEncodeError: str_ = "[Decode error - output not " + self.encoding + "]\n" proc = None return # Normalize newlines, Sublime Text always uses a single \n separator # in memory. str_ = str_.replace('\r\n', '\n').replace('\r', '\n') self.out_panel.write(str_) def append_string(self, proc, str): self.append_data(proc, str.encode(self.encoding)) def finish(self, proc): if not self.quiet: elapsed = time.time() - proc.start_time exit_code = proc.exit_code() if (exit_code == 0) or (exit_code == None): self.append_string(proc, "[Finished in %.1fs]" % (elapsed)) else: self.append_string( proc, "[Finished in %.1fs with exit code %d]\n" % (elapsed, exit_code)) self.append_string(proc, self.debug_text) if proc != self.proc: return # XXX: What's this for? errs = self.out_panel.view.find_all_results() if len(errs) == 0: sublime.status_message("Build finished") else: sublime.status_message( ("Build finished with %d errors") % len(errs)) def on_data(self, proc, data): after(0, functools.partial(self.append_data, proc, data)) def on_finished(self, proc): after(0, functools.partial(self.finish, proc))
def process_resp(data): _logger.debug ('processing response data: %s', data) if data ['Kind'] == 'compilerlocation': r = CompilerLocationResponse (data) raise_event(ON_COMPILER_PATH_AVAILABLE, {'response': r}) return if data['Kind'] == 'project': r = ProjectResponse(data) _logger.debug('\n'.join(r.files)) return if data['Kind'] == 'errors': # todo: enable error navigation via standard keys v = sublime.active_window().active_view() v.erase_regions ('fs.errs') if not data['Data']: return v.add_regions('fs.errs', [ErrorInfo(e).to_region(v) for e in data['Data']], 'invalid.illegal', 'dot', sublime.DRAW_SQUIGGLY_UNDERLINE | sublime.DRAW_NO_FILL | sublime.DRAW_NO_OUTLINE ) return if data['Kind'] == 'ERROR': _logger.error(str(data)) return if data['Kind'] == 'tooltip' and data['Data']: v = sublime.active_window().active_view() word = v.substr(v.word(v.sel()[0].b)) panel = OutputPanel('fs.out') panel.write(data['Data']) panel.show() return if data['Kind'] == 'INFO' and data['Data']: _logger.info(str(data)) print("FSharp:", data['Data']) return if data['Kind'] == 'finddecl' and data['Data']: fname = data['Data']['File'] row = data['Data']['Line'] col = data['Data']['Column'] + 1 w = sublime.active_window() # todo: don't open file if we are looking at the requested file target = '{0}:{1}:{2}'.format(fname, row, col) w.open_file(target, sublime.ENCODED_POSITION) return if data['Kind'] == 'declarations' and data['Data']: decls = DeclarationsResponse(data) its = [decl.to_menu_data() for decl in decls.declarations] w = sublime.active_window() w.run_command ('fs_show_menu', {'items': its}) return if data['Kind'] == 'completion' and data['Data']: _logger.error('unexpected "completion" results - should be handled elsewhere') return