Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Exceptions from executing commands with wrong arguments cannot be caught #1359

Open
1 of 3 tasks
evandrocoan opened this issue Sep 13, 2016 · 3 comments
Open
1 of 3 tasks

Comments

@evandrocoan
Copy link

evandrocoan commented Sep 13, 2016

Sublime Text Python's Interpreter for packages is not catching an exception throwed by sublime.py

This was migrated from http://stackoverflow.com/questions/39461428/how-to-catch-sublime-text-exceptions-on-their-python-interpreter.

I am trying to catch this exception:

    try:

        print( 'RUNNING' )
        sublime.active_window().run_command( "side_bar_update_sync" )
        isNotSyncedSideBarEnabled = False
        print( 'RUNNING THIS' )

    except BaseException:

        isNotSyncedSideBarEnabled = True
        print( 'RUNNING THIS ALSO' )

But when it is ran, it just does not catches it. Does not matter if I try it within TypeError, Exception or BaseException classes. This below is the full exception output.

reloading plugin SublimeDefaultSyntax.default_syntax
READ_PREF_ASYNC!!!!
    updateIsSyncedSideBarEnabled!!!!
RUNNING
Traceback (most recent call last):
  File "D:\User\Dropbox\Applications\SoftwareVersioning\SublimeText\sublime_plugin.py", line 538, in run_
    return self.run()
TypeError: run() missing 1 required positional argument: 'enable'
RUNNING THIS
isNotSyncedSideBarEnabled: False

The problem is, the python cannot catch the exception throwed by run_command( "side_bar_update_sync" ). The exception catching for errors like trying to call self.view, when there is no self passed by, are working fine. This is the full code:

def plugin_loaded():

    global isNotSyncedSideBarEnabled

    packageControlSettings = sublime.load_settings('Package Control.sublime-settings')
    userSettings           = sublime.load_settings('Preferences.sublime-settings')

    def updateIsSyncedSideBarEnabled():

        global isNotSyncedSideBarEnabled

        print('    updateIsSyncedSideBarEnabled!!!!')
        sublime.active_window().run_command( "reveal_in_side_bar" )

        try:

            print( 'RUNNING' )
            sublime.active_window().run_command( "side_bar_update_sync" )
            isNotSyncedSideBarEnabled = False
            print( 'RUNNING THIS' )

        except BaseException:

            isNotSyncedSideBarEnabled = True
            print( 'RUNNING THIS ALSO' )

        print( 'isNotSyncedSideBarEnabled: ' + str( isNotSyncedSideBarEnabled ) )



    def read_pref_async():

        print('READ_PREF_ASYNC!!!!')
        updateIsSyncedSideBarEnabled()


    def read_pref_package():

        print('READ_PREF_PACKAGE!!!!')
        updateIsSyncedSideBarEnabled()


    def read_pref_preferences():

        print('READ_PREF_PREFERENCES!!!!')
        updateIsSyncedSideBarEnabled()


    # read initial setting, after all packages being loaded
    sublime.set_timeout_async( read_pref_async, 1000 )

    # listen for changes
    packageControlSettings.add_on_change( "Package Control", read_pref_package )
    userSettings.add_on_change( "Preferences", read_pref_preferences )

    #print( userSettings.get( "ignored_packages" ) )
    #print( packageControlSettings.get( "installed_packages" ) )

This discussion may be followed by this Sublime Text Forum's thread: https://forum.sublimetext.com/t/how-to-add-remove-a-default-menu-entry-when-a-x-package-is-isnt-enabled-installed/22753?u=addons_zz

This are the lines from the file showed on the exception:

532 class ApplicationCommand(Command):
533     def run_(self, edit_token, args):
534         args = self.filter_args(args)
535         if args:
536             return self.run(**args)
537         else:
538             return self.run()
539
540    def run(self):
541        pass1
542
543 ... other classes

Environment

  • Operating system and version:
    • Windows 10 ...
    • Mac OS ...
    • Linux ...
  • Sublime Text:
    • Build 3114
@FichteFoll FichteFoll changed the title Sublime Text Python's Interpreter for packages is not catching an exception throwed by sublime.py Exceptions from executing commands with wrong arguments cannot be caught Sep 14, 2016
@FichteFoll
Copy link
Collaborator

FichteFoll commented Sep 14, 2016

Here's a smaller repro:

import sublime_plugin

class TestCommandCommand(sublime_plugin.TextCommand):
    def run(self, edit):
        try:
            ret = self.view.window().run_command("toggle_comment", {"fuck": "no"})
        except:
            print("an exception")
        else:
            print(ret)

Console:

reloading plugin User.test
command: test_command
Traceback (most recent call last):
  File "C:\Program Files\Sublime Text 3\sublime_plugin.py", line 792, in run_
    return self.run(edit, **args)
TypeError: run() got an unexpected keyword argument 'fuck'
None

Needless to say, this only happens for Python commands and not internal commands since those do not error at all.

@wbond
Copy link
Member

wbond commented Oct 9, 2019

I tend to doubt this will really change. When you try to run a command, the request is sent to the sublime_text executable. If it is an internal command, it is executed in C++. If it is implemented in Python, sublime_text sends a message to plugin_host to execute the command. If there is an error in running the command, there is no way to throw the exception back through sublime_text and then back into plugin_host.

It will also be made even further more complicated by future changes to how the plugin_host works.

@FichteFoll
Copy link
Collaborator

While catching the exact exception may not be important, what about giving run_command a boolean return value indicating whether the command was executed properly? Currently you receive absolutely zero feedback from your code whether a command did its work, failed somewhere or outright doesn't exist (I believe we had an issue for that but can't find it).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants