示例#1
0
def openCommand(option, files, path):
    sublime_path = get_current_sublime_install_path()

    if not exists(as_url(sublime_path)):
        show_alert('Invalid Sublime Text path: ' + sublime_path)
        choice = show_alert('Update Path to Sublime Text?', buttons=YES | NO)

        if choice == YES:
            if not set_sublime_install_path():
                # user failed to set sublime install path. bail.
                show_alert(
                    'command failed because no valid path to Sublime Text given'
                )
                return

        else:
            # no path to use, user doesnt want to set one now. bail.
            show_alert(
                'command failed because no valid path to Sublime Text given')
            return

    _SUBLIMETEXTPATH = sublime_path

    args = [to_path(x) for x in files]
    cmd = [_SUBLIMETEXTPATH] + option + args
    env = create_clean_environment()
    Popen(cmd,
          shell=False,
          cwd=path,
          stdin=DEVNULL,
          stdout=DEVNULL,
          stderr=DEVNULL,
          env=env)
示例#2
0
    def __call__(self):
        # check file under cursor
        current_file = self.pane.get_file_under_cursor()
        # simply checking the file extension
        if re.compile(r'\.lnk$').search(current_file):
            # ok, let's receive the real folder containing the target of that shortcut
            shellscript = os.path.dirname(__file__) + "\link_target.ps1 "
            command = "powershell -ExecutionPolicy Bypass -NoLogo -Noninteractive -noprofile"
            command += ' -file "' + shellscript + '"'
            command += ' -link "' + as_human_readable(current_file) + '"'
            #show_status_message("Command: " + command) # temporary
            target = as_url(os.popen(command).read().strip())
            show_status_message("Target: " + target, 2)

            # what did we get?
            if False == exists(target):
                # target is not reachable...
                show_alert(target + " doesn't exist.")
            elif is_dir(target):
                # target is a folder, we go to it
                self.pane.set_path(target)
            else:
                # target is a file, we go to its directory
                self.pane.set_path(dirname(target))
        else:
            # nope, wrong thing
            show_alert(current_file + " is not a shortcut.")
def get_current_tortoisesvnproc_install_path():
    settings = load_json(_TORTOISEPROCCONFIGFILE,
                         default={'path': _TORTOISEPROCPATHDEFAULT})

    if settings['path'] and exists(as_url(settings['path'])):
        return settings['path']
    else:
        return _TORTOISEPROCPATHDEFAULT
示例#4
0
def get_current_sublime_install_path():
    settings = load_json(_SUBLIMETEXTCONFIGFILE,
                         default={'path': _SUBLIMETEXTPATHDEFAULT})

    if settings['path'] and exists(as_url(settings['path'])):
        return settings['path']
    else:
        return _SUBLIMETEXTPATHDEFAULT
示例#5
0
    def move(self, src_url, dst_url):
        # Rename on same server
        src_scheme, src_path = splitscheme(src_url)
        dst_scheme, dst_path = splitscheme(dst_url)
        if src_scheme == dst_scheme and commonprefix([src_path, dst_path]):
            # TODO avoid second connection
            with FtpWrapper(src_url) as src_ftp, \
                    FtpWrapper(dst_url) as dst_ftp:
                src_ftp.conn.rename(src_ftp.path, dst_ftp.path)
                return

        fs.copy(src_url, dst_url)
        if fs.exists(src_url):
            fs.delete(src_url)
def set_tortoisesvnproc_install_path():
    new_tortoisesvnproc_filepath, ok = show_prompt(
        'Enter full path to TortoiseSVNProc.exe program here',
        default=get_current_tortoisesvnproc_install_path(),
        selection_start=0,
        selection_end=None)

    if not ok:
        return False

    if not exists(as_url(new_tortoisesvnproc_filepath)):
        show_alert('Path to TortoiseSVNProc given is invalid')
        return False

    _TORTOISEPROCPATH = new_tortoisesvnproc_filepath
    save_json(_TORTOISEPROCCONFIGFILE, {'path': new_tortoisesvnproc_filepath})
    return True
示例#7
0
def set_sublime_install_path():
    new_sublime_filepath, ok = show_prompt(
        'Enter full path to Sublime Text program here',
        default=get_current_sublime_install_path(),
        selection_start=0,
        selection_end=None)

    if not ok:
        return False

    if not exists(as_url(new_sublime_filepath)):
        show_alert('Path to Sublime Text given is invalid')
        return False

    _SUBLIMETEXTPATH = new_sublime_filepath
    save_json(_SUBLIMETEXTCONFIGFILE, {'path': new_sublime_filepath})
    return True
def openCommand(option, files, path):
    tortoisesvnproc_path = get_current_tortoisesvnproc_install_path()

    if not exists(as_url(tortoisesvnproc_path)):
        show_alert('Invalid TortoiseSVNProc.exe path: ' + tortoisesvnproc_path)
        choice = show_alert('Update Path to TortoiseSVNProc.exe?',
                            buttons=YES | NO)

        if choice == YES:
            if not set_tortoisesvnproc_install_path():
                # user failed to set sublime install path. bail.
                show_alert(
                    'command failed because no valid path to TortoiseSVNProc.exe given'
                )
                return

        else:
            # no path to use, user doesnt want to set one now. bail.
            show_alert(
                'command failed because no valid path to TortoiseSVNProc.exe given'
            )
            return

    # _TORTOISEPROCPATH = as_human_readable('file://'+ tortoisesvnproc_path)
    _TORTOISEPROCPATH = tortoisesvnproc_path

    # TODO: Check if quoting is working for other platforms
    args = [shlex.quote(to_path(x)) for x in files]
    cmd = _TORTOISEPROCPATH + " " + option + " ".join(args)

    env = create_clean_environment()
    Popen(cmd,
          shell=False,
          cwd=path,
          stdin=DEVNULL,
          stdout=DEVNULL,
          stderr=DEVNULL,
          env=env)
示例#9
0
 def __call__(self):
     # get as list of all chosen filenames that need to be attached
     chosenFiles = self.get_chosen_files()
     # create the string for the attachment
     attachment_string = ''
     for it in chosenFiles:
         # human readable file name
         ithr = as_human_readable(it)
         foldername = ithr.split('/')[-1]
         # check if folder, if so, create a zip file of the folder and add that one to the filename list!
         if is_dir(it):
             # create zipname
             zipname = 'zip://' + ithr + '.zip'
             # make sure the sip file does not exist yet
             if exists(zipname):
                 choice = show_alert(
                     'The zip file already exists. Do you want to overwrite it?',
                     buttons=YES | NO,
                     default_button=NO)
                 if choice == NO:
                     return
             # create a zip file, pack the folder into the zip file
             copy(it, zipname + '/' + foldername)
             # inform fman that the zip file exists now
             notify_file_added(zipname)
             # now we want to add the zip file instead of the selected file, so change it before adding it to the string
             ithr = zipname.replace('zip://', '')
         # attach the file to the string of what to attach to the e-mail message
         attachment_string += ithr
         if it is not chosenFiles[-1]:
             attachment_string += ','
     # set up the command to start a new e-mail message and attach it
     cmd = 'thunderbird -compose \"attachment=\'' + attachment_string + '\'\"'
     # print the command - untoggle for checking before sending
     # show_alert(cmd)
     # send the command
     os.system(cmd)
示例#10
0
    def __call__(self, url=None):

        sourceDirUrl = self.pane.get_path()
        archiveName = basename(sourceDirUrl) + '.7z'

        oppositePane = _get_opposite_pane(self.pane)
        oppositePaneUrl = oppositePane.get_path()

        archiveUrl = join(oppositePaneUrl, archiveName)

        sourceDir = as_human_readable(sourceDirUrl)
        archive = as_human_readable(archiveUrl)

        if exists(archiveUrl):

            if is_dir(archiveUrl):
                message = archiveName + " exists and is a directory, aborting!"
                show_alert(message)
                return

            choice = show_alert("Archive exists!\nReplace?",
                                buttons=YES | CANCEL,
                                default_button=CANCEL)
            if choice == YES:
                try:
                    move_to_trash(archiveUrl)
                except NotImplementedError:
                    show_alert("Failed to delete archive, aborting!")
                    return

            elif choice == CANCEL:
                return

        submit_task(CreateArchive(archive, sourceDir))
        oppositePane.reload()

        return
示例#11
0
_CHECK_EXTENSION = True
_COMPRESS_ARGS = ['a']
_HASH = 'sha256'

settings = load_json('SevenZipTools.json', default={})
result = settings.get('7zip', {})
with open('R:/out.txt', 'w') as myfile:
    myfile.write(str(settings) + '\n')
if result:
    try:
        exePath = result['path']
    except (KeyError, TypeError):
        pass
    else:
        exePathUrl = as_url(exePath)
        if exists(exePathUrl) and not is_dir(exePathUrl):
            _USER_7ZIP = exePath
            _SUPPORTED_EXTENSIONS += ['.rar']

result = settings.get('additional extensions', [])
if result and isinstance(result, list):
    _SUPPORTED_EXTENSIONS += result

result = settings.get('ignore extension', None)
if result:
    _CHECK_EXTENSION = False

result = settings.get('compress args', [])
if result and isinstance(result, list):
    _COMPRESS_ARGS += result
示例#12
0
from fman import DirectoryPaneCommand, show_alert, show_prompt, load_json, save_json, YES, NO
from fman.fs import is_dir, exists
from fman.url import splitscheme, as_url, as_human_readable
from subprocess import DEVNULL, Popen

import os
import shlex

_TORTOISEPROCPATHDEFAULT = 'C:/Program Files/TortoiseSVN/bin/TortoiseProc.exe'
_TORTOISEPROCCONFIGFILE = 'TortoiseSVNHelper Config.json'
_TORTOISEPROCPATH = ''

settings = load_json(_TORTOISEPROCCONFIGFILE,
                     default={'path': _TORTOISEPROCPATHDEFAULT})

if settings['path'] and exists(as_url(settings['path'])):
    _TORTOISEPROCPATH = settings['path']

else:
    _TORTOISEPROCPATH = _TORTOISEPROCPATHDEFAULT


class SVNSwtich(DirectoryPaneCommand):
    aliases = ('Svn: Switch', 'SVN: SWITCH')

    def __call__(self):
        url = self.pane.get_path()
        scheme, path = splitscheme(url)

        paths = []
        paths.append(as_url(path))
示例#13
0
    def __call__(self, url=None):

        # This will get set if the automagically determined destination
        #  directory exists, and will always be the default name when prompted
        #  to manually choose a destination directory name.
        originalName = None

        if url is None:
            workingFile = self.pane.get_file_under_cursor()
            if workingFile:
                url = workingFile

        fileName = basename(url)

        if _CHECK_EXTENSION:

            try:
                extension = fileName[fileName.rindex('.'):]
            except ValueError:
                show_alert("Failed to determine extension, aborting!")
                return

            if not extension in _SUPPORTED_EXTENSIONS:
                show_alert("Unsupported extension, aborting!")
                return

            newDirName = fileName[0:fileName.rindex('.')]

        else:

            try:
                newDirName = fileName[0:fileName.rindex('.')]

            except ValueError:

                message = "Archive has no extension.\n"
                message += "Click 'YES' to enter a name "
                message += "for the destination directory.\n"
                message += "Click 'NO' to use the archive name.\n"
                message += "Click 'ABORT' to abort extraction."

                choice = show_alert(message,
                                    buttons=YES | NO | ABORT,
                                    default_button=ABORT)

                if choice == YES:
                    newDirName, ok = show_prompt("Destination directory:",
                                                 default=fileName)
                    if not (newDirName and ok):
                        return

                elif choice == NO:
                    newDirName = fileName

                else:
                    return

        oppositePane = _get_opposite_pane(self.pane)
        oppositePaneUrl = oppositePane.get_path()
        oppositePaneScheme, _ = splitscheme(resolve(oppositePaneUrl))
        if oppositePaneScheme != 'file://':
            show_alert("Can't extract to %s, aborting!" % oppositeScheme)
            return

        newDirUrl = join(oppositePaneUrl, newDirName)

        while exists(newDirUrl):
            if not originalName:
                originalName = newDirName
            message = newDirName + " already exists!\nEnter a different name?"
            choice = show_alert(message,
                                buttons=YES | ABORT,
                                default_button=ABORT)
            if choice == YES:
                newDirName, ok = show_prompt("Destination directory:",
                                             default=newDirName)
                if not (newDirName and ok):
                    continue
                else:
                    newDirUrl = join(oppositePaneUrl, newDirName)

        try:
            mkdir(newDirUrl)
        except (FileNotFoundError, NotImplementedError):
            message = "Failed to create directory '"
            message += newDirName + "', aborting!"
            show_alert(message)
            return

        archive = as_human_readable(url)
        destDir = as_human_readable(newDirUrl)

        submit_task(ExtractArchive(archive, destDir))

        return
示例#14
0
    def loadConfig(cls):
        """Check StatusBarExtended.json for consistency/completeness, restore defaults on fail"""
        msg_t = cls.msgTimeout
        if hasattr(cls, 'locked_update'):
            show_status_message(
                "StatusBarExtended: waiting for the config files to be updated, try again later..."
            )
            return None, 'UpdateInProgress'
        cls.locked_update = True  # ensure globally unique 'loadConfig' run so that e.g. we don't ask a user multiple times to delete corrupted configs

        cfgCurrent = load_json(
            'StatusBarExtended.json'
        )  # within one fman session, it is guaranteed that multiple calls to load_json(...) with the same JSON name always return the same object, so save {} when deleting the files to force reload
        if type(cfgCurrent) not in (type(dict()), type(None)):
            # delete config files, fman's save_json can't replace types
            config_files = ['StatusBarExtended.json']
            config_files.append('StatusBarExtended (' + PLATFORM + ').json')
            user_settings_url = join(as_url(DATA_DIRECTORY), 'Plugins', 'User',
                                     'Settings')
            user_input_allow = ''
            prompt_msg_full = ''
            corrupt_config = []
            for f in config_files:
                f_url = join(user_settings_url, f)
                f_path = as_path(f_url)

                if not exists(f_url):
                    continue

                excerpt = str(load_json(f_path))[:100]
                prompt_msg = f_path \
                    + "\n  that begins with:"\
                    + "\n  " + excerpt
                corrupt_config.append({})
                corrupt_config[-1]['url'] = f_url
                corrupt_config[-1]['path'] = f_path
                corrupt_config[-1]['prompt_msg'] = prompt_msg

            corrupt_count = len(corrupt_config)
            if corrupt_count:  # delete corrupt config files with the user's permission
                prompt_msg_full += "Please enter 'y' or 'yes' or '1' (without the quotes) to delete " + str(corrupt_count) + " corrupt plugin config file" \
                    + ("\n" if corrupt_count==1 else "s\n") \
                    + "with incompatible data type " + str(type(cfgCurrent)) + '\n'\
                    + "(all settings will be reset to their defaults)\n"
                for corrupt_file_dict in corrupt_config:
                    prompt_msg_full += '\n' + corrupt_file_dict[
                        'prompt_msg'] + '\n'
                user_input_allow, ok = show_prompt(prompt_msg_full,
                                                   default=user_input_allow)
                if ok and user_input_allow in ('y', 'yes', '1'):
                    _reset = False
                    for corrupt_file_dict in corrupt_config:
                        f_url = corrupt_file_dict['url']
                        f_path = corrupt_file_dict['path']
                        try:
                            move_to_trash(f_url)
                        except Exception as e:
                            show_status_message(
                                "StatusBarExtended: failed to move to trash — "
                                + f_path + " — with exception " + repr(e),
                                msg_t)
                            pass

                        if not exists(f_url):
                            show_status_message(
                                "StatusBarExtended: moved to trash — " +
                                f_path, msg_t)
                            _reset = True
                        else:
                            show_status_message(
                                "StatusBarExtended: failed to move to trash, deleting — "
                                + f_path, msg_t)
                            try:
                                delete(f_url)
                            except Exception as e:
                                show_status_message(
                                    "StatusBarExtended: failed to delete — " +
                                    f_path + " — with exception " + repr(e),
                                    msg_t)
                                pass

                            if not exists(f_url):
                                show_status_message(
                                    "StatusBarExtended: deleted — " + f_path,
                                    msg_t)
                                _reset = True
                            else:
                                show_alert(
                                    "StatusBarExtended: failed to move to trash or delete — "
                                    + f_path + "\nPlease, delete it manually")
                                del cls.locked_update
                                return None, 'ConfigDeleteFail'
                    if _reset == True:  # can save_json only when both files are deleted, otherwise there is a format mismatch ValueError
                        cls.saveConfig({})
                        cfgCurrent = load_json('StatusBarExtended.json')
                else:  # user canceled or didn't enter y/1
                    show_status_message(
                        "StatusBarExtended: you canceled the deletion of the corrupted config files",
                        msg_t)
                    del cls.locked_update
                    return None, 'Canceled'
            else:  # can't find the config files
                show_alert("StatusBarExtended: can't find the corrupt config files:\n" \
                    + str(config_files) + "\n @ " + as_path(user_settings_url) \
                    + "\nMaybe their default location changed, please, delete them manually")
                del cls.locked_update
                return None, 'CorruptConfigNotFound'

        reload = False
        if (cfgCurrent is None) or (
                cfgCurrent == {}
        ):  # empty file or empty dictionary (corrupt configs deleted and replaced with {}), save defaults to the config file
            cfgCurrent = dict()
            for key in cls.Default:
                cfgCurrent[key] = cls.Default[key]
            reload = True

        if type(cfgCurrent) is dict:
            for key in cls.Default:  # Fill in missing default values (e.g. in older installs)
                if key not in cfgCurrent:
                    cfgCurrent[key] = cls.Default[key]
                    reload = True
        if reload:
            cls.saveConfig(cfgCurrent)
            cfgCurrent = load_json('StatusBarExtended.json')

        if type(cfgCurrent) is dict:  # check for still missing keys
            missing_keys = []
            for key in cls.Default:
                if key in cfgCurrent:
                    continue
                missing_keys.append(key)
            if len(missing_keys):
                show_status_message(
                    "StatusBarExtended: config files are missing some required keys:"
                    + str(missing_keys) + " Maybe try to reload?", msg_t)
                del cls.locked_update
                return None, 'MissingKeys'
            else:
                del cls.locked_update
                return cfgCurrent, 'Success'
        else:
            show_status_message(
                "StatusBarExtended: couldn't fix config files, maybe try to reload?",
                msg_t)
            del cls.locked_update
            return None, 'UnknownError'