Configuration files

XYZCommander uses the two-layered scheme for configuration files:

System configuration files
XYZCommander relies on system configuration files to perform a correct initialization as almost all default values are kept in those configs and not hardcoded in XYZCommander itself. XYZCommander looks for system configs in the main installation directory (usualy /usr/local/share/xyzcmd/conf or /usr/share/xyzcmd/conf). System configs aren’t supposed to be edited by user.
User configuration files
All configuration is done in user configs. They can be held in user home dir: ~/.xyzcmd/conf. So if you need to make any change - just copy corresponding config from system configs or create an empty one and make all the neccessary changes.

At startup XYZCommander first reads default values from system configs and then tries to open and parse user’s ones.

DSL

XYZCommander configuration files are, in fact, just regular python scripts but in order to simplify configuration editing a bunch of useful functions are available:

let(variable, value, sect=”local”)

Set variable to hold a value. Variable will be available in xyz.conf[section][varname] If section is not provided - local will be used.

Example - Choose a desired skin:

let("skin", "seablue", sect="xyz")

val(variable, sect=”local”)

Retrieve variable value.

Example:

val("skin", sect="xyz")

section(sect=”local”)

Return whole configuration section contents as a dictionary or None if undefined

Example:

icmd("alias",
   lambda _: call(":core:shell:echo",
                  "\n".join(["alias %s='%s'" % (k, v)
                             for k, v in section("aliases").iteritems()
                             ])))

unlet(variable, sect=”local”)

Delete variable binding if exists.

Example:

unlet("myvar")

load(plugin)

Load method[s] from plugin.

Example - load all methods from :sys:cmd plugin:

load(":sys:cmd:*")

Example - load show_binds method from :core:bindlist plugin:

load(":core:bindlist:show_binds")

bind(method, shortcut, context=”DEFAULT”)

Bind method to be executed upon pressing shortcut. Method can be either full plugin method pass or python function/method/lambda object. If context is @ - use plugin full path as context. (See Contexts)

Example - run :sys:cmd:execute when ENTER is pressed:

bind(":sys:cmd:execute", kbd("ENTER"))

Example - use system pager to view files:

bind(lambda: shell(env("PAGER", "less"), macro("ACT_PATH")), kbd("F3"))

kbd(*args)

Transform a string shortcut description into internal representation object.

Example:

kbd("ENTER")

exec_file(filename)

Execute another configuration file

Example:

exec_file("custom.xyz")

action(rule, fn)

Set up an action to be taken upon pressing action key on file. Action key is by default - ENTER which is bound to :core:panel:action.

Example - when action is pressed on executable file - run it:

action(r'(type{file} and perm{+0111}) or '\
       r'(type{link} and link_type{file} and link_perm{+0111})',
       lambda obj: shell(obj.path))

macro(macroname)

Expand macro name.

Availbale macros:

ACT_CWD
Working directory in active panel
INACT_CWD
Working directory in inactive panel
ACT_PATH
Full selected object path in active panel
INACT_PATH
Full selected object path in inactive panel
ACT_BASE
Parent directory in active panel
INACT_BASE
Parent directory in inactive panel
ACT_TAGGED
List of tagged files in active panel
INACT_TAGGED
List of tagged files in inactive panel
ACT_UNTAGGED
List of not tagged files in active panel
INACT_UNTAGGED
List of not tagged files in inactive panel

Example - edit current file:

bind(lambda: shell(env("EDITOR", "vi"), macro("ACT_PATH")), kbd("F4"),
     ":sys:panel")

call(method, *args)

Call plugin method passing arguments to it.

Example - change directory:

action(r'type{dir} or (link_type{dir} and link_exists{?})',
       lambda obj: call(":sys:panel:chdir", obj.path))

env(variable, default=None)

Return environment variable or default if is not set

Example:

env("HOME", "/")

shell(cmd, *args, **kwargs)

Execute command using :core:shell plugin.

  • Optional boolean argument current can be provided to indicate that cmd is to be run from current directory.
  • Optional boolean argument bg can be provided to indicate that cmd must be executed in background.
  • Optional boolean argument reload can be provided to indicate that panel content should/should not be reloaded after execution.
  • Optional boolean argument wait can be provided to indicate that shell should/should not wait for user input after command executed The wait flag has higher priority than :core:shell’s wait configuration flag.

Example - run xpdf in background on .pdf files:

action(r'iname{".*\\.pdf$"}', lambda obj: shell("xpdf", obj.path, bg=True))

alias(alias, replace)

Set an alias which will be expanded in command line before execution. replace argument can be either string or function.

Example:

alias("ll", "ls -l")

icmd(command, object)

Set an internal command. Internal command do not get passed to shell, instead appropriate function is being called by XYZCommander.

Example:

icmd("cd", lambda path: call(":sys:panel:chdir", path))

plugins_on(*plugins)

Enable plugin[s].

Example:

plugins_on(":sys:run",
           ":sys:cmd",
           ":sys:panel",
           ":sys:logger")

plugins_off(*plugins)

Disable plugin[s].

Example:

plugins_off(":misc:about")

plugin_conf(plugin, opts)

Configure plugin.

Where:

  • plugin: Plugin name
  • opts: dict {var1: val1, var2: var2,..}

In fact, plugin_conf is only a shortened form of let(plugin, opts, sect="plugins").

Example:

plugin_conf(":sys:cmd", {
            # Command line prompt
            "prompt": "$ ",

            # Size of undo buffer
            "undo_depth": 10,

            # Size of typed commands history buffer
            "history_depth": 50})

prefix(shortcut)

Set new prefix key.

Example:

prefix(kbd("CTRL-x"))

vfs(prefix, vfs_class)

Set prefix and VFSObject class for VFS dispatching.

Example:

# Set tar VFS handler
vfs("tar", TarVFSObject)

hook(event, proc)

Register a new hook. Event is an event string and proc is a procedure to be called.

Example:

hook("event:sys:cmd:execute",
     lambda cmd: xyzlog.info("About to execute %s" % cmd))

uhook(event)

Remove all hooks for the event.

fsrule(rule)

Convert string rule to libxyz.core.FSRule instance. This method primarily used in skin files, where matching fsrules are defined.

Example:

"fs.rules": [
     (
         # Broken links
         fsrule(r'type{link} and not link_exists{?}'),
         BG_PALETTE({"foreground": "DARK_RED"})
     ),

palette(config)

Create internal palette object. It is primarily used in skin files.

Config is a dictionary of form:

{
   'foreground': COLOR,
   'background': COLOR,
   'fg_attributes': [ATTR],
   'mono': [ATTR],
   'foreground_high': HG_COLOR,
   'background_high': HG_COLOR
}

Example:

palette({
    "foreground": "DARK_BLUE",
    "background": "LIGHT_GRAY",
    "fg_attributes": ["BOLD", "UNDERLINE"]
})

skin(**kwargs)

Create and register new skin.

kwargs include:

name (string)
Skin name
author (string)
Skin author
version (string)
Skin version
description (string)
Skin description
colors (tuple)
Tuple of color modes skin is compatible with. If not set, skin is considered to be compatible with any color mode.
rules (dict)
Skin rulesets

Example (part of XYZCommander default skin):

skin(name="seablue",
     author="Max E. Kuznecov <syhpoon@syhpoon.name>",
     version="0.3",
     description="XYZCommander Seablue skin",

     rules = {
         "fs.rules": [
             (
                 # Broken links
                 fsrule(r'type{link} and not link_exists{?}'),
                 BG_PALETTE({"foreground": "DARK_RED"})
             )
         ]
     }
)

Files

Although any XYZCommander configuration file can contain any (or all) of the above functions, it is better to logically separate definitions.

Here’s the list of XYZCommander system configuration files:

actions.xyz
Contains action definitions.
aliases.xyz
Contains aliases.
icmd.xyz
Contains internal commands definitions.
keys.xyz
keys configuration file is used to bind methods, exported by plugins to keyboard shortcuts.
main.xyz
Main configuration files. Contains miscellaneous configuration directives.
plugins.xyz
Plugins configuration.
vfs.xyz
VFS configuration.
hooks.xyz
Hooks configuration.
skins/
Skin files.

Shortcuts

Shortcut is a combination of keys pressed. It is specifed as a list of special (libxyz.ui.Keys attributes) and regular keys separated by hiphen:

CTRL-x  means Control + x key
META-L  means Escape + SHIFT + l key

Note

Please note that not all of the possible combinations make sense.

There is a standard plugin :ui:testinput which can be usefull to determine what kind of shortcuts are corresponding to pressed keys.

Contexts

When a focus widget receives keyboard input it looks for matching key pressed in KeyManager object accessible as km attribute of XYZData class.

But for different widgets the same keys/shortcuts can have different meanings. For intance key UP pressed while Panel widget is active will move the cursor one entry up. But for BoxYesNo dialog the same key changes the button focus. To handle such a problem a concept of context is introduced. Context is simply a set which shares the shortcuts defined within it. Context has a name and may include an arbritrary amount of widgets. Context named DEFAULT used unless other provided. For example, consider the part of keys configuration file:

# 1.
bind(":sys:cmd:undo", kbd("META-P"))
# 2.
bind(":sys:cmd:undo", kbd("META-P"), "CMD")

In 1. we’ve bound Meta+Shift+p shortcut to undo method of :sys:cmd plugin. As we haven’t provided context name, DEFAULT will be used.

In 2. we’ve explicitly provided CMD context. So box_action will only be executed when a widget with context CMD will be in focus receiving input.

One can provide a special context name: @ to make context name equal to plugin full namespace path:

bind(":sys:cmd:execute", kbd("ENTER"), "@")

In this case, the bind will be saved to context :sys:cmd.