What is Clink?
Clink combines the native Windows shell cmd.exe with the powerful command line editing features of the GNU Readline library, which provides rich completion, history, and line-editing capabilities. Readline is best known for its use in the famous Unix shell Bash, the standard shell for Mac OS X and many Linux distributions.
Features
- The same line editing as Bash (from GNU's Readline library).
- History persistence between sessions.
- Context sensitive completion;
- Executables (and aliases).
- Directory commands.
- Environment variables
- Thirdparty tools; Git, Mercurial, SVN, Go, and P4.
- New keyboard shortcuts;
- Paste from clipboard (Ctrl+V).
- Incremental history search (Ctrl+R and Ctrl+S).
- Powerful completion (Tab).
- Undo (Ctrl+Z).
- Automatic
cd ..(Ctrl+PgUp). - Environment variable expansion (Ctrl+Alt+E).
- (press Alt+H for many more...)
- Scriptable completion with Lua.
- Colored and scriptable prompt.
- Auto-answering of the "Terminate batch job?" prompt.
By default Clink binds Alt+H to display the current key bindings. More features can also be found in GNU's Readline and History libraries' manuals.
Usage
There are three ways to use Clink the first of which is to add Clink to cmd.exe's autorun registry entry. This can be selected when installing Clink using the installer and Clink also provides the ability to manage this autorun entry from the command line. Running clink autorun --help has more information.
The second alternative is to manually run Clink using the command clink inject from within a command prompt session to run Clink in that session.
The last option is to use the Clink shortcut that the installer adds to Windows' start menu. This is in essence a shortcut to the command cmd.exe /k clink inject.
How Clink Works
When running Clink via the methods above, Clink checks the parent process is supported and injects a DLL into it. The DLL then hooks the WriteConsole() and ReadConsole() Windows functions. The former is so that Clink can capture the current prompt, and the latter hook allows Clink to provide it's own Readline-powered command line editing.
Configuring Clink
The easiest way to configure Clink is to use Clink's set command line option. This can list, query, and set Clink's settings. Run clink set --help from a Clink-installed cmd.exe process to learn more both about how to use it and to get descriptions for Clink's various options.
The following table describes the available Clink settings:
| Name | Default | Description |
|---|---|---|
clink.paste_crlf |
space |
What to do with CR and LF characters on paste. Set this to delete to delete them, or to space to replace them with spaces. |
clink.path |
A list of paths to load Lua scripts. Multiple paths can be delimited semicolons. | |
clink.promptfilter |
True | Enable prompt filtering by Lua scripts. |
cmd.auto_answer |
off |
Automatically answers cmd.exe's "Terminate batch job (Y/N)?" prompts. off = disabled, answer_yes = answer Y, answer_no = answer N. |
cmd.ctrld_exits |
True | Ctrl+D exits the process when it is pressed on an empty line. |
color.cmd |
bold |
Used when Clink displays shell (CMD.EXE) command completions. |
color.doskey |
bright cyan |
Used when Clink displays doskey alias completions. |
color.filtered |
bold |
The default color for filtered completions (see Filtering the Match Display). |
color.hidden |
Used when Clink displays file completions with the "hidden" attribute. | |
color.input |
Used when Clink displays the input line text. | |
color.interact |
bold |
Used when Clink displays text or prompts such as a pager's --More?-- prompt. |
color.modmark |
Used when Clink displays the * mark on modified history lines when Readline's mark-modified-lines variable and Clink's color.input setting are both set. Falls back to color.input if not set. |
|
color.readonly |
Used when Clink displays file completions with the "readonly" attribute. | |
doskey.enhanced |
True | Enhanced Doskey adds the expansion of macros that follow | and & command separators and respects quotes around words when parsing $1..$9 tags. Note that these features do not apply to Doskey use in Batch files. |
exec.cwd |
True | When matching executables as the first word (exec.enable), include executables in the current directory. (This is implicit if the word being completed is a relative path). |
exec.dirs |
True | When matching executables as the first word (exec.enable), also include directories relative to the current working directory as matches. |
exec.enable |
True | Match executables when completing the first word of a line. |
exec.path |
True | When matching executables as the first word (exec.enable), include executables found in the directories specified in the %PATH% environment variable. |
exec.space_prefix |
True | If the line begins with whitespace then Clink bypasses executable matching (exec.path) and will do normal files matching instead. |
files.hidden |
True | Includes or excludes files with the "hidden" attribute set when generating file lists. |
files.system |
False | Includes or excludes files with the "system" attribute set when generating file lists. |
files.unc_paths |
False | UNC (network) paths can cause Clink to stutter when it tries to generate matches. Enable this if matching UNC paths is required. |
history.dont_add_to_history_cmds |
exit history |
List of commands that aren't automatically added to the history. Commands are separated by spaces, commas, or semicolons. Default is exit history, to exclude both of those commands. |
history.dupe_mode |
erase_prev |
If a line is a duplicate of an existing history entry Clink will erase the duplicate when this is set erase_prev. Setting it to ignore will not add duplicates to the history, and setting it to add will always add lines. |
history.expand_mode |
not_quoted |
The ! character in an entered line can be interpreted to introduce words from the history. This can be enabled and disable by setting this value to on or off. Values of not_squoted, not_dquoted, or not_quoted will skip any ! character quoted in single, double, or both quotes respectively. |
history.ignore_space |
True | Ignore lines that begin with whitespace when adding lines in to the history. |
history.max_lines |
2500 | The number of history lines to save if history.save is enabled (1 to 50000). |
history.save |
True | Saves history between sessions. |
history.shared |
False | When history is shared, all instances of Clink update the master history list after each command and reload the master history list on each prompt. When history is not shared, each instance updates the master history list on exit. |
lua.break_on_error |
False | Breaks into Lua debugger on Lua errors. |
lua.break_on_traceback |
False | Breaks into Lua debugger on traceback(). |
lua.debug |
False | Loads a simple embedded command line debugger when enabled. Breakpoints can be added by calling pause(). |
lua.path |
Value to append to package.path. Used to search for Lua scripts specified in require() statements. |
|
lua.traceback_on_error |
False | Prints stack trace on Lua errors. |
match.ignore_case |
relaxed |
Controls case sensitivity in string comparisons. off = case sensitive, on = case insensitive, relaxed = case insensitive plus - and _ are considered equal. |
match.sort_dirs |
with |
How to sort matching directory names. before = before files, with = with files, after = after files. |
match.wild |
True | Matches ? and * wildcards when using any of the menu-complete commands. Turn this off to behave how bash does. |
readline.hide_stderr |
False | Suppresses stderr from the Readline library. Enable this if Readline error messages are getting in the way. |
terminal.emulation |
auto |
Clink can either emulate a virtual terminal and handle ANSI escape codes itself, or let the console host natively handle ANSI escape codes. native = pass output directly to the console host process, emulate = clink handles ANSI escape codes itself, auto = emulate except when running in ConEmu. |
terminal.modify_other_keys |
True | When enabled, pressing Space or Tab with modifier keys sends extended XTerm key sequences so they can be bound separately. |
Compatibility Notes:
- The
esc_clears_linesetting has been replaced by aclink-reset-linecommand that can be bound to Escape (or any other key).- The
use_altgr_substitutesetting has been removed. (If AltGr or lack of AltGr causes a problem, please visit the repo and open an issue with details about the problem.)
Color Settings
Friendly Color Names
The Clink color settings use the following syntax:
[attributes] [foreground_color] [on [background_color]]
Optional attributes (can be abbreviated to 3 letters):
boldordimadds or removes brightness (high intensity) to the default foreground color (if the default color is bright white, thendimuses normal white).underlineornounderlineadds or removes an underline.
Optional colors for foreground_color and background_color (can be abbreviated to 3 letters):
defaultornormaluses the default color as defined by the current color theme in the console window.black,red,green,yellow,blue,cyan,magenta,whiteare the basic colors names.brightcan be combined with any of the other color names to make them bright (high intensity).
Examples (specific results may depend on the console host program):
bri yelfor bright yellow foreground on default background color.boldfor bright default foreground on default background color.underline bright black on whitefor dark gray (bright black) foreground on light gray (white) background.default on bluefor default foreground color on blue background.
Alternative SGR Syntax
It's also possible to set any ANSI SGR escape code using sgr SGR_parameters (for example sgr 7 is the code for reverse video, which swaps the foreground and background colors).
Be careful, since some escape code sequences might behave strangely.
File Locations
Settings and history are persisted to disk from session to session. The location of these files depends on which distribution of Clink was used. If you installed Clink using the .exe installer then Clink uses the current user's non-roaming application data directory. This user directory is usually found in one of the following locations;
- Windows XP:
c:\Documents and Settings\<username>\Local Settings\Application Data\clink - Windows Vista onwards:
c:\Users\<username>\AppData\Local\clink
All of the above locations can be overridden using the --profile path command line option which is specified when injecting Clink into cmd.exe using clink inject.
Command Line Options
See
clink inject --help for more information.
See
clink autorun --help for more information.
clink set by itself lists all settings and their values.clink set setting_name describes the setting shows its current value.clink set setting_name clear resets the setting to its default value.clink set setting_name value sets the setting to the specified value.
See
clink history --help for more information.Also, Clink automatically defines
history as an alias for clink history.
Or
clink --version shows just the version number.
Configuring Readline
Readline itself can also be configured to add custom keybindings and macros by creating a Readline init file. There is excellent documentation for all the options available to configure Readline in Readline's manual.
Clink searches in the directories referenced by the following environment variables and loads any .inputrc or _inputrc files present, in the order listed here:
%CLINK_INPUTRC%%USERPROFILE%%LOCALAPPDATA%%APPDATA%%HOME%
Configuration in files loaded earlier can be overridden by files loaded later.
Other software that also uses Readline will also look for the .inputrc file (and possibly the _inputrc file too). To set macros and keybindings intended only for Clink one can use the Readline init file conditional construct like this; $if clink [...] $endif.
Compatibility Notes:
- The
clink_inputrc_basefile from v0.4.8 is no longer used.- For backward compatibility,
clink_inputrcis also loaded from the above locations, but it has been deprecated and may be removed in the future.
Clink also adds some new commands and configuration variables in addition to what's covered in the Readline documentation.
New Configuration Variables
| Name | Default | Description |
|---|---|---|
completion-auto-query-items |
on | Automatically prompts before displaying completions if they need more than half a screen page. |
history-point-at-end-of-anchored-search |
off | Puts the cursor at the end of the line when using history-search-forward or history-search-backward. |
search-ignore-case |
off | Controls whether the history search commands ignore case. |
New Commands
| Name | Description |
|---|---|
add-history |
Adds the current line to the history without executing it, and clears the editing line. |
clink-copy-cwd |
Copy the current working directory to the clipboard. |
clink-copy-line |
Copy the current line to the clipboard. |
clink-copy-word |
Copy the word at the cursor to the clipboard. |
clink-ctrl-c |
Discards the current line and starts a new one (like Ctrl+C in CMD.EXE). |
clink-exit |
Replaces the current line with exit and executes it (exits the shell instance). |
clink-expand-doskey-alias |
Expand the doskey alias (if any) at the beginning of the line. |
clink-expand-env-vars |
Expand the environment variable (e.g. %FOOBAR%) at the cursor. |
clink-insert-dot-dot |
Inserts ..\ at the cursor. |
clink-paste |
Paste the clipboard at the cursor. |
clink-popup-complete |
Show a popup window that lists the available completions. |
clink-popup-directories |
Show a popup window of recent current working directories. In the popup, use Enter to cd /d to the highlighted directory. See below more about the popup window. |
clink-popup-history |
Show a popup window that lists the command history (if any text precedes the cursor then it uses an anchored search to filter the list). In the popup, use Enter to execute the highlighted command. See below for more about the popup window. |
clink-reset-line |
Clears the current line. |
clink-scroll-bottom |
Scroll the console window to the bottom (the current input line). |
clink-scroll-line-down |
Scroll the console window down one line. |
clink-scroll-line-up |
Scroll the console window up one line. |
clink-scroll-page-down |
Scroll the console window down one page. |
clink-scroll-page-up |
Scroll the console window up one page. |
clink-scroll-top |
Scroll the console window to the top. |
clink-show-help |
Lists the currently active key bindings using friendly key names. |
clink-show-help-raw |
Lists the currently active key bindings using raw key sequences. |
clink-up-directory |
Changes to the parent directory. |
old-menu-complete-backward |
Like old-menu-complete, but in reverse. |
remove-history |
While searching history, removes the current line from the history. |
Completion Colors
When colored-completion-prefix is configured to on, then the "so" color from %LS_COLORS% is used to color the common prefix when displaying possible completions. The default for "so" is magenta, but for example set LS_COLORS=so=90 sets the color to bright black (which shows up as a dark gray).
When colored-stats is configured to on, then the color definitions from %LS_COLORS% (using ANSI escape codes) are used to color file completions according to their file type or extension. Each definition is a either a two character type id or a file extension, followed by an equals sign and then the SGR parameters for an ANSI escape code. Multiple definitions are separated by colons. Also, since %LS_COLORS% doesn't cover readonly files, hidden files, doskey aliases, or shell commands the color.readonly, color.hidden, color.doskey, and color.cmd Clink settings exist to cover those.
Here is an example where %LS_COLORS% defines colors for various types.
so=defines the color for the common prefix for possible completions.fi=defines the color for normal files.di=defines the color for directories.ex=defines the color for executable files.
set LS_COLORS=so=90:fi=97:di=93:ex=92:*.pdf=30;105:*.md=4
Let's break that down:
so=90uses bright black (dark gray) for the common prefix for possible completions.fi=97uses bright white for files.di=93uses bright yellow for directories.ex=92uses bright green for executable files.*.pdf=30;105uses black on bright magenta for .pdf files.*.md=4uses underline for .md files.
Popup window
The clink-popup-complete, clink-popup-directories, and clink-popup-history commands show a popup window that lists the available completions, directory history, or command history. Here's how it works:
| Key | Description |
|---|---|
| Escape | Cancels the popup. |
| Enter | Inserts the highlighted completion, changes to the highlighted directory, or executes the highlighted command. |
| Shift+Enter | Inserts the highlighted completion, inserts the highlighted directory, or jumps to the highlighted command history entry without executing it. |
| Ctrl+Enter | Same as Shift+Enter. |
| Typing | Typing does an incremental search. |
| F3 | Go to the next match. |
| Ctrl+L | Go to the next match. |
| Shift+F3 | Go to the previous match. |
| Ctrl+Shift+L | Go to the previous match. |
Extending Clink
The Readline library allows clients to offer an alternative path for creating completion matches. Clink uses this to hook Lua into the completion process making it possible to script the generation of matches with Lua scripts. The following sections describe this in more detail and show some examples.
The Location of Lua Scripts
Clink loads all Lua scripts it finds in these directories:
- All directories listed in the
clink.pathsetting, separated by semicolons. - If
clink.pathis not set, then the DLL directory and the profile directory are used (see File Locations for info about the profile directory). - All directories listed in the
%CLINK_PATH%environment variable, separated by semicolons.
Lua scripts are reloaded each time the edit prompt is activated.
Match Generators
These are Lua functions that are called as part of Readline's completion process.
First create a match generator object:
local my_generator = clink.generator(priority)
The priority argument is a number that influences when the generator gets called, with lower numbers going before higher numbers.
The :generate() Function
Next define a match generator function on the object, taking the following form:
function my_generator:generate(line_state, match_builder)
-- Use the line_state object to examine the current line and create matches.
-- Submit matches to Clink using the match_builder object.
-- Return true or false.
end
line_state is a line object that has information about the current line.
match_builder is a builder object to which matches can be added.
If no further match generators need to be called then the function should return true. Returning false or nil continues letting other match generators get called.
Here is an example script that supplies git branch names as matches for git checkout. It's based on git_branch_autocomplete.lua from collink.clink-git-extensions. The version here is updated for the new Clink Lua API, and for illustration purposes it's been simplified to not support git aliases.
local git_branch_autocomplete = clink.generator(1)
local function string.starts(str, start)
return string.sub(str, 1, string.len(start)) == start
end
local function is_checkout_ac(text)
if string.starts(text, "git checkout") then
return true
end
return false
end
local function get_branches()
-- Run git command to get branches.
local handle = io.popen("git branch -a 2>&1")
local result = handle:read("*a")
handle:close()
-- Parse the branches from the output.
local branches = {}
if string.starts(result, "fatal") == false then
for branch in string.gmatch(result, " %S+") do
branch = string.gsub(branch, " ", "")
if branch ~= "HEAD" then
table.insert(branches, branch)
end
end
end
return branches
end
function git_branch_autocomplete:generate(line_state, match_builder)
-- Check if it's a checkout command.
if not is_checkout_ac(line_state:getline()) then
return false
end
-- Get branches and add them (does nothing if not in a git repo).
local matchCount = 0
for _, branch in ipairs(get_branches()) do
match_builder:addmatch(branch)
matchCount = matchCount + 1
end
return matchCount > 0 -- If we found branches, then stop other match generators.
end
The :getwordbreakinfo() Function
A generator can influence word breaking for the end word by defining a :getwordbreakinfo() function. The function takes a line_state line object that has information about the current line. If it returns nil or 0, the end word is truncated to 0 length. This is the normal behavior, which allows Clink to collect and cache all matches and then filter them based on typing. Or it can return two numbers: word break length and an optional end word length. The end word is split at the word break length: one word contains the first word break length characters from the end word (if 0 length then it's discarded), and the next word contains the rest of the end word truncated to the optional word length (0 if omitted).
For example, when the environment variable match generator sees the end word is abc%USER it returns 3,1 so that the last two words become "abc" and "%" so that its generator knows it can do environment variable matching. But when it sees abc%FOO%def it returns 8,0 so that the last two words become "abc%FOO%" and "" so that its generator won't do environment variable matching, and also so other generators can produce matches for what follows, since "%FOO%" is an already-completed environment variable and therefore should behave like a word break. In other words, it breaks the end word differently depending on whether the number of percent signs is odd or even, to account for environent variable syntax rules.
And when an argmatcher sees the end word begins with a flag character it returns 0,1 so the end word contains only the flag character in order to switch from argument matching to flag matching.
local envvar_generator = clink.generator(10)
function envvar_generator:generate(line_state, match_builder)
-- Does the word end with a percent sign?
local word = line_state:getendword()
if word:sub(-1) ~= "%" then
return false
end
-- Add env vars as matches.
for _, i in ipairs(os.getenvnames()) do
match_builder:addmatch("%"..i.."%", "word")
end
match_builder:setsuppressappend() -- Don't append a space character.
match_builder:setsuppressquoting() -- Don't quote envvars.
return true
end
function envvar_generator:getwordbreakinfo(line_state)
local word = line_state:getendword()
local in_out = false
local index = nil
-- Paired percent signs denote already-completed environment variables.
-- So use envvar completion for abc%foo%def%USER but not for abc%foo%USER.
for i = 1, #word do
if word:sub(i, i) == "%" then
in_out = not in_out
if in_out then
index = i - 1
else
index = i
end
end
end
-- If there were any percent signs, return word break info to influence the
-- match generators.
if index then
return index, (in_out and 1) or 0
end
end
Argument Completion
Clink provides a framework for writing complex argument match generators in Lua. It works by creating a parser object that describes a command's arguments and flags and then registering the parser with Clink. When Clink detects the command is being entered on the current command line being edited, it uses the parser to generate matches.
Here is an example of a simple parser for the command foobar;
clink.argmatcher("foobar")
:addflags("-foo", "-bar")
:addarg(
{ "hello", "hi" },
{ "world", "wombles" }
)
This parser describes a command that has two positional arguments each with two potential options. It also has two flags which the parser considers to be position independent meaning that provided the word being completed starts with a certain prefix the parser with attempt to match the from the set of flags.
On the command line completion would look something like this:
C:\>foobar hello -foo wo
world wombles
C:\>foobar hello -foo wo_
When displaying possible completions, flag matches are only shown if the flag character has been input (so command and Alt+= would list only non-flag matches, or command - and Alt+= would list only flag matches).
More Advanced Stuff
Linking Parsers
There are often situations where the parsing of a command's arguments is dependent on the previous words (git merge ... compared to git log ... for example). For these scenarios Clink allows you to link parsers to arguments' words using Lua's concatenation operator. Parsers can also be concatenated with flags too.
a_parser = clink.argmatcher():addarg({ "foo", "bar" })
b_parser = clink.argmatcher():addarg({ "abc", "123" })
c_parser = clink.argmatcher()
c_parser:addarg({ "foobar" .. b_parser })
c_parser:addarg({ c_parser })
As the example above shows, it is also possible to use a parser without concatenating it to a word. When Clink follows a link to a parser it is permanent and it will not return to the previous parser.
Functions As Argument Options
Argument options are not limited solely to strings. Clink also accepts functions too so more context aware argument options can be used.
function rainbow_function(word)
return { "red", "white", "blue" }
end
the_parser = clink.argmatcher()
the_parser:addarg({ "zippy", "bungle", "george" })
the_parser:addarg({ rainbow_function, "yellow", "green" })
The functions take a single argument which is a word from the command line being edited (or partial word if it is the one under the cursor). Functions should return a table of potential matches.
Some built-in matcher functions are available:
| Function | Description |
|---|---|
| clink.dirmatches | Generates directory matches. |
| clink.filematches | Generates file matches. |
Shorthand
It is also possible to omit the addarg and addflags function calls and use a more declarative shorthand form:
-- Shorthand form; requires tables.
clink.argmatcher()
{ "one", "won" }
{ "two", "too" }
{ "-a", "-b", "/?", "/h" }
-- Normal form:
clink.argmatcher()
:addarg(
{ "one", "won" }
{ "two", "too" }
)
:addflags("-a", "-b", "/?", "/h")
With the shorthand form flags are implied rather than declared. When a shorthand table's first value is a string starting with - or / then the table is interpreted as flags. Note that it's still possible with shorthand form to mix flag prefixes, and even add additional flag prefixes, such as { '-a', '/b', '=c' }.
Filtering The Match Display
In some instances it may be preferable to display potential matches in an alternative form than the generated matches passed to and used internally by Readline. For example, it might be desirable to display a * next to some matches, or to show additional information about each match. Filtering the match display only affects what is displayed; it doesn't affect completing matches.
To facilitate custom match generators that may wish to do this there is the clink.match_display_filter variable. This can be set to a function that will then be called before matches are to be displayed.
function my_display_filter(matches)
new_matches = {}
for _, m in ipairs(matches) do
local _, _, n = m:find("\\([^\\]+)$")
table.insert(new_matches, n)
end
return new_matches
end
function my_match_generator(text, first, last)
...
clink.match_display_filter = my_display_filter
return true
end
The function's single argument matches is a table containing what Clink is going to display. The return value is a table with the input matches filtered as required by the match generator. The value of clink.match_display_filter is reset every time match generation is invoked.
Compatibility Note: When a match display filter has been set, it changes how match generation behaves.
- Normally match generation only happens at the start of a new word. The full set of potential matches is remembered and dynamically filtered based on further typing.
- When a match display filter is set, then match generation is also re-run whenever matches are displayed. This is necessary for backward compatibility with how generators and match display filters were able to influence each other.
- This means if a match generator made contextual decisions other than just filtering then it could potentially behave differently in Clink v1.x than it did in v0.x.
Customising The Prompt
Before Clink displays the prompt it filters the prompt through Lua so that the prompt can be customised. This happens each and every time that the prompt is shown which allows for context sensitive customisations (such as showing the current branch of a git repository).
Writing a prompt filter is straightforward:
- Create a new prompt filter by calling
clink.promptfilter()along with a priority id which dictates the order in which filters are called. Lower priority ids are called first. - Define a
filter()function on the returned prompt filter.
The filter function takes a string argument that contains the filtered prompt so far. If the filter function returns nil, it has no effect. If the filter function returns a string, that string is used as the new filtered prompt (and may be further modified by other prompt filters with higher priority ids). If the filter function returns a string and a boolean, then if the boolean is false the prompt filtering is done and no further filter functions are called.
local p = clink.promptfilter(30)
function p:filter(prompt)
return "new prefix "..prompt.." new suffix" -- Add ,false to stop filtering.
end
The following example illustrates setting the prompt, modifying the prompt, using ANSI escape code for colors, running a git command to find the current branch, and stopping any further processing.
local green = "\x1b[92m"
local yellow = "\x1b[93m"
local cyan = "\x1b[36m"
local normal = "\x1b[m"
-- A prompt filter that discards any prompt so far and sets the
-- prompt to the current working directory. An ANSI escape code
-- colors it yellow.
local cwd_prompt = clink.promptfilter(30)
function cwd_prompt:filter(prompt)
return yellow..os.getcwd()..normal
end
-- A prompt filter that inserts the date at the beginning of the
-- the prompt. An ANSI escape code colors the date green.
local date_prompt = clink.promptfilter(40)
function date_prompt:filter(prompt)
return green..os.date("%a %H:%M")..normal.." "..prompt
end
-- A prompt filter that may stop further prompt filtering.
-- This is a silly example, but on Wednesdays, it stops the
-- filtering, which in this example prevents git branch
-- detection and the line feed and angle bracket.
local wednesday_silliness = clink.promptfilter(45)
function wednesday_silliness:filter(prompt)
if os.date("%a") == "Wed" then
-- The ,false stops any further filtering.
return prompt.." HAPPY HUMP DAY! ", false
end
end
-- A prompt filter that appends the current git branch.
local git_branch_prompt = clink.promptfilter(50)
function git_branch_prompt:filter(prompt)
for line in io.popen("git branch 2>nul"):lines() do
local branch = line:match("%* (.+)$")
if branch then
return prompt.." "..cyan.."["..branch.."]"..normal
end
end
end
-- A prompt filter that adds a line feed and angle bracket.
local bracket_prompt = clink.promptfilter(150)
function bracket_prompt:filter(prompt)
return prompt.."\n> "
end
The resulting prompt will look like this:
Wed 12:54 c:\dir [master]
> _
...except on Wednesdays, when it will look like this:
Wed 12:54 c:\dir HAPPY HUMP DAY! _
Miscellaneous
Key bindings
Binding special keys
Due to differences between Windows and Linux, escape codes for keys like PageUp/Down and the arrow keys are different in Clink.
| Normal | Shift | Ctrl | Ctrl+Shift | Alt | Alt+Shift | Ctrl+Alt | Ctrl+Alt+Shift | |
|---|---|---|---|---|---|---|---|---|
| Up | \e[A |
\e[1;2A |
\e[1;5A |
\e[1;6A |
\e[1;3A |
\e[1;4A |
\e[1;7A |
\e[1;8A |
| Down | \e[B |
\e[1;2B |
\e[1;5B |
\e[1;6B |
\e[1;3B |
\e[1;4B |
\e[1;7B |
\e[1;8B |
| Left | \e[D |
\e[1;2D |
\e[1;5D |
\e[1;6D |
\e[1;3D |
\e[1;4D |
\e[1;7D |
\e[1;8D |
| Right | \e[C |
\e[1;2C |
\e[1;5C |
\e[1;6C |
\e[1;3C |
\e[1;4C |
\e[1;7C |
\e[1;8C |
| Insert | \e[2~ |
\e[2;2~ |
\e[2;5~ |
\e[2;6~ |
\e[2;3~ |
\e[2;4~ |
\e[2;7~ |
\e[2;8~ |
| Delete | \e[3~ |
\e[3;2~ |
\e[3;5~ |
\e[3;6~ |
\e[3;3~ |
\e[3;4~ |
\e[3;7~ |
\e[3;8~ |
| Home | \e[H |
\e[1;2H |
\e[1;5H |
\e[1;6H |
\e[1;3H |
\e[1;4H |
\e[1;7H |
\e[1;8H |
| End | \e[F |
\e[1;2F |
\e[1;5F |
\e[1;6F |
\e[1;3F |
\e[1;4F |
\e[1;7F |
\e[1;8F |
| PgUp | \e[5~ |
\e[5;2~ |
\e[5;5~ |
\e[5;6~ |
\e[5;3~ |
\e[5;4~ |
\e[5;7~ |
\e[5;8~ |
| PgDn | \e[6~ |
\e[6;2~ |
\e[6;5~ |
\e[6;6~ |
\e[6;3~ |
\e[6;4~ |
\e[6;7~ |
\e[6;8~ |
| Tab | \t |
\e[Z |
\e[27;5;9~ |
\e[27;6;9~ |
- | - | - | - |
| Space | Space |
- | \e[27;5;32~ |
\e[27;6;32~ |
- | - | \e[27;7;32~ |
\e[27;8;32~ |
| Backspace | ^h |
- | Rubout |
- | \e^h |
- | \eRubout |
- |
| Escape | \e[27;27~ |
- | - | - | - | - | - | - |
Here is an example line from an inputrc file that binds Shift-End to the Readline transpose-word function;
"\e[1;2F": transpose-word
Binding function keys
For function keys the full escape sequences are listed. The last four columns (Alt+) are the same as the first four columns prefixed with an extra \e.
| Normal | Shift | Ctrl | Ctrl+Shift | Alt | Alt+Shift | Alt+Ctrl | Alt+Ctrl+Shift | |
|---|---|---|---|---|---|---|---|---|
| F1 | \eOP |
\e[1;2P |
\e[1;5P |
\e[1;6P |
\e\eOP |
\e\e[1;2P |
\e\e[1;5P |
\e\e[1;6P |
| F2 | \eOQ |
\e[1;2Q |
\e[1;5Q |
\e[1;6Q |
\e\eOQ |
\e\e[1;2Q |
\e\e[1;5Q |
\e\e[1;6Q |
| F3 | \eOR |
\e[1;2R |
\e[1;5R |
\e[1;6R |
\e\eOR |
\e\e[1;2R |
\e\e[1;5R |
\e\e[1;6R |
| F4 | \eOS |
\e[1;2S |
\e[1;5S |
\e[1;6S |
\e\eOS |
\e\e[1;2S |
\e\e[1;5S |
\e\e[1;6S |
| F5 | \e[15~ |
\e[15;2~ |
\e[15;5~ |
\e[15;6~ |
\e\e[15~ |
\e\e[15;2~ |
\e\e[15;5~ |
\e\e[15;6~ |
| F6 | \e[17~ |
\e[17;2~ |
\e[17;5~ |
\e[17;6~ |
\e\e[17~ |
\e\e[17;2~ |
\e\e[17;5~ |
\e\e[17;6~ |
| F7 | \e[18~ |
\e[18;2~ |
\e[18;5~ |
\e[18;6~ |
\e\e[18~ |
\e\e[18;2~ |
\e\e[18;5~ |
\e\e[18;6~ |
| F8 | \e[19~ |
\e[19;2~ |
\e[19;5~ |
\e[19;6~ |
\e\e[19~ |
\e\e[19;2~ |
\e\e[19;5~ |
\e\e[19;6~ |
| F9 | \e[20~ |
\e[20;2~ |
\e[20;5~ |
\e[20;6~ |
\e\e[20~ |
\e\e[20;2~ |
\e\e[20;5~ |
\e\e[20;6~ |
| F10 | \e[21~ |
\e[21;2~ |
\e[21;5~ |
\e[21;6~ |
\e\e[21~ |
\e\e[21;2~ |
\e\e[21;5~ |
\e\e[21;6~ |
| F11 | \e[23~ |
\e[23;2~ |
\e[23;5~ |
\e[23;6~ |
\e\e[23~ |
\e\e[23;2~ |
\e\e[23;5~ |
\e\e[23;6~ |
| F12 | \e[24~ |
\e[24;2~ |
\e[24;5~ |
\e[24;6~ |
\e\e[24~ |
\e\e[24;2~ |
\e\e[24;5~ |
\e\e[24;6~ |
Here is an example line from an inputrc file that binds Alt+Shift+F3 to the Readline history-substring-search-backward function;
"\e\e[1;2R": history-substring-search-backward
Discovering Clink key sequences
An easy way to find the key sequence for any key combination that Clink supports is to use Clink's echo command line option. Run clink echo and then press key combinations; the associated key binding sequence is printed to the console output.
Saved command history
Here's how the saved history works:
When the history.saved setting is enabled, then the command history is loaded and saved as follows (or when the setting is disabled, then it isn't saved between sessions).
Every time a new input line starts, Clink reloads the master history list and prunes it not to exceed the history.max_lines setting.
For performance reasons, deleting a history line marks the line as deleted without rewriting the history file. When the number of deleted lines gets too large (exceeding the max lines or 200, which is larger) then the history file is compacted: the file is rewritten with the deleted lines removed.
When the history.shared setting is enabled, then all instances of Clink update the master history file and reload it every time a new input line starts. This gives the effect that all instances of Clink share the same history -- a command entered in one instance will appear in other instances' history the next time they start an input line. When the setting is disabled, then each instance of Clink loads the master file but doesn't append its own history back to the master file until after it exits, giving the effect that once an instance starts its history is isolated from other instances' history.
Lua API Reference
This section describes the Clink Lua API extensions. Also see Lua Documentation for more information about the Lua programming language._argmatcher
This adds argument matches. Arguments can be a string, a string linked to another parser by the concatenation operator, a table of arguments, or a function that returns a table of arguments. See Argument Completion for more information.
local my_parser = clink.argmatcher("git")
:addarg("add", "status", "commit", "checkout")This adds flag matches. Flags are separate from arguments: When listing possible completions for an empty word, only arguments are listed. But when the word being completed starts with the first character of any of the flags, then only flags are listed. See Argument Completion for more information.
local my_parser = clink.argmatcher("git")
:addarg({ "add", "status", "commit", "checkout" })
:addflags("-a", "-g", "-p", "--help")This makes the parser loop back to argument position index when it runs out of positional sets of arguments (if index is omitted it loops back to argument position 1).
clink.argmatcher("xyzzy")
:addarg("zero", "cero") -- first arg can be zero or cero
:addarg("one", "uno") -- second arg can be one or uno
:addarg("two", "dos") -- third arg can be two or dos
:loop(2) -- fourth arg loops back to position 2, for one or uno, and so onThis makes the parser prevent invoking match generators. You can use it to "dead end" a parser and suggest no completions.
Deprecated; don't use this. See _argmatcher:addflags for more information.
This overrides the default flag prefix (-). The flag prefixes are used to switch between matching arguments versus matching flags. When listing possible completions for an empty word (e.g. command _ where the cursor is at the _), only arguments are listed. And only flags are listed when the word starts with one of the flag prefixes. Each flag prefix must be a single character, but there can be multiple prefixes.
This is no longer needed because :addflags() does it automatically.
local my_parser = clink.argmatcher()
:setflagprefix("-", "/", "+")
:addflags("--help", "/?", "+mode")builder
Adds a match. If match is a string, it's added as a match and type is the optional match type.
Or match can be a table with the following scheme: { match:string, [type:string] }. If a table element is missing the type field, then the type argument is used for that element.
If the type argument is omitted, "none" is assumed.
The match type can affect how the match is inserted, displayed, and colored:
| Type | Description |
|---|---|
| "word" | Shows the whole word even if it contains slashes. |
| "arg" | Avoids appending a space if the match ends with a colon or equal sign. |
| "command" | Displays the match using color.cmd. |
| "alias" | Displays the match using color.doskey. |
| "file" | Shows only the last path component, with appropriate file coloring. |
| "dir" | Shows only the last path component and adds a trailing path separator, with appropriate directory coloring. |
| "link" | Shows only the last path component, with appropriate symlink coloring. Not supported yet. |
| "none" | For backward compatibility the match is treated like "file", unless it ends with a path separator in which case it's treated like "dir". |
| Modifier | Description |
|---|---|
| "hidden" | This can be combined with "file" or "dir" to use color.hidden (e.g. "file,hidden"). |
| "readonly" | This can be combined with "file" or "dir" to use color.readonly (e.g. "file,readonly"). |
See Completion Coloring and Color Settings for more information about colors.
builder:addmatch("hello") -- type is "none"
builder:addmatch("some_word", "word")
builder:addmatch("/flag", "arg")
builder:addmatch("abbrev", "alias")
builder:addmatch({ match="foo.cpp", type="file" })
builder:addmatch({ match="bar", type="dir" })
builder:addmatch({ match=".git", type="dir hidden" })This is the equivalent of calling builder:addmatch() in a for-loop. Returns the number of matches added and a boolean indicating if all matches were added successfully.
matches can be a table of match strings, or a table of tables describing the matches.
type is used as the type when a match doesn't explicitly include a type, and is "none" if omitted.
builder:addmatches({"abc", "def"}) -- Adds two matches of type "none"
builder:addmatches({"abc", "def"}, "file") -- Adds two matches of type "file"
builder:addmatches({
-- Same table scheme per entry here as in builder:addmatch()
{ match="remote/origin/master", type="word" },
{ match="remote/origin/topic", type="word" }
})Sets character to append after matches. For example the set match generator uses this to append "=" when completing matches, so that completing set USER becomes set USERDOMAIN= (rather than set USERDOMAIN ).
Sets whether to suppress appending anything after the match except a possible closing quote. For example the env var match generator uses this.
Sets whether to suppress quoting for the matches. Set to 0 for normal quoting, or 1 to suppress quoting, or 2 to suppress end quotes. For example the env var match generator sets this to 1 to overcome the quoting that would normally happen for "%" characters in filenames.
clink
Deprecated; don't use this. See builder:addmatch for more information.
This is a shim that lets clink.register_match_generator continue to work for now, despite being obsolete.
Creates and returns a new argument matcher parser object. Use :addarg() and etc to add arguments, flags, other parsers, and more. See Argument Completion for more information.
If one command is provided and an argument matcher parser object is already associated with the command, this returns the existing parser rather than creating a new parser. Using :addarg() starts at arg position 1, making it possible to merge new args and etc into the existing parser.
You can use this function in an argmatcher to supply directory matches. This automatically handles Readline tilde completion.
-- Make "cd" generate directory matches (no files).
clink.argmatcher("cd")
:addflags("/d")
:argarg(({ clink.dirmatches })You can use this function in an argmatcher to supply file matches. This automatically handles Readline tilde completion.
Argmatchers default to matching files, so it's unusual to need this function. However, some exceptions are when a flag needs to accept file matches but other flags and arguments don't, or when matches need to include more than files.
-- Make "foo --file" generate file matches, but other flags and args don't.
-- And the third argument can be a file or $stdin or $stdout.
clink.argmatcher("foo")
:addflags(
"--help",
"--file"..clink.argmatcher():addarg({ clink.filematches })
)
:addarg({ "one", "won" })
:addarg({ "two", "too" })
:addarg({ clink.filematches, "$stdin", "$stdout" })Creates and returns a new match generator object. Define on the object a generate() function which gets called in increasing priority order (low values to high values) when generating matches for completion. See Match Generators for more information.
Deprecated; don't use this. See clink.generator for more information.
This returns true if needle is a prefix of candidate with a case insensitive comparison.
Normally in Clink v1.x and higher the needle will be an empty string because the generators are no longer responsible for filtering matches. The match pipeline itself handles that internally now.
This API correctly converts UTF8 strings to lowercase, with international linguistic awareness.
clink.lower("Hello World") -- returns "hello world"Deprecated; don't use this. See builder:addmatch for more information.
This is no longer used.
clink.match_display_filter = function(matches)
-- Transform matches.
return matches
endThis variable can be set to a filter function. See Filtering the Match Display for more information.
Deprecated; don't use this. See builder:addmatch for more information.
This is no longer needed, because now it's inferred from the match type when adding matches.
Creates and returns a new promptfilter object that is applied in increasing priority order (low values to high values). Define on the object a filter() function that takes a string argument which contains the filtered prompt so far. The function can return nil to have no effect, or can return a new prompt string. It can optionally stop further prompt filtering by also returning false. See Customising The Prompt for more information.
local foo_prompt = clink.promptfilter(80)
function foo_prompt:filter(prompt)
-- Insert the date at the beginning of the prompt.
return os.date("%a %H:%M").." "..prompt
endDeprecated; don't use this. See clink.generator for more information.
Registers a generator function for producing matches. This behaves similarly to v0.4.8, but not identically. The Clink schema has changed significantly enough that there is no direct 1:1 translation; generators are called at a different time than before and have access to more information than before.
-- Deprecated form:
local function match_generator_func(text, first, last, match_builder)
-- `text` is the line text.
-- `first` is the index of the beginning of the end word.
-- `last` is the index of the end of the end word.
-- `clink.add_match()` is used to add matches.
-- return true if handled, or false to let another generator try.
end
clink.register_match_generator(match_generator_func, 10)
-- Replace with new form:
local g = clink.generator(10)
function g:generate(line_state, match_builder)
-- `line_state` is a line object.
-- `match_builder:addmatch()` is used to add matches.
-- return true if handled, or false to let another generator try.
endThis API correctly converts UTF8 strings to uppercase, with international linguistic awareness.
clink.upper("Hello World") -- returns "HELLO WORLD"The commit part of the Clink version number. For v1.2.3.a0f14d the commit part is a0f14d.
The Clink version number encoded as a single integer following the format Mmmmpppp where M is the major part, m is the minor part, and p is the patch part of the version number.
For example, Clink v95.6.723 would be 950060723.
This format makes it easy to test for feature availability by encoding version numbers from the release notes.
-- Make sure the version is high enough to support the "color.filtered" setting.
local color_filtered = ""
if clink.version_encoded ~= nil and clink.version_encoded >= 10010009 then
color_filtered = "\x1b["..settings.get("color.filtered").."m"
endThe major part of the Clink version number. For v1.2.3.a0f14d the major version is 1.
The minor part of the Clink version number. For v1.2.3.a0f14d the minor version is 2.
The patch part of the Clink version number. For v1.2.3.a0f14d the patch version is 3.
clink.arg
Deprecated; don't use this. See clink.argmatcher for more information.
Creates a new parser and adds ... to it.
-- Deprecated form:
local parser = clink.arg.new_parser(
{ "abc", "def" }, -- arg position 1
{ "ghi", "jkl" }, -- arg position 2
"--flag1", "--flag2" -- flags
)
-- Replace with form:
local parser = clink.argmatcher()
:addarg("abc", "def") -- arg position 1
:addarg("ghi", "jkl") -- arg position 2
:addflags("--flag1", "--flag2") -- flagsDeprecated; don't use this. See clink.argmatcher for more information.
Adds parser to the first argmatcher for cmd. This behaves similarly to v0.4.8, but not identically. The Clink schema has changed significantly enough that there is no direct 1:1 translation. Calling clink.arg.register_parser repeatedly with the same command to merge parsers is not supported anymore.
-- Deprecated form:
local parser1 = clink.arg.new_parser("abc", "def")
local parser2 = clink.arg.new_parser("ghi", "jkl")
clink.arg.register_parser("foo", parser1)
clink.arg.register_parser("foo", parser2)
-- Replace with new form:
clink.argmatcher("foo"):addarg(parser1, parser2)
-- Warning: Note that the following are NOT the same as above!
-- This replaces parser1 with parser2:
clink.argmatcher("foo"):addarg(parser1)
clink.argmatcher("foo"):addarg(parser2)
-- This uses only parser2 if/when parser1 finishes parsing args:
clink.argmatcher("foo"):addarg(parser1):addarg(parser2)clink.prompt
Deprecated; don't use this. See clink.promptfilter for more information.
Registers a prompt filter function. The capabilities are the same as before but the syntax is changed.
-- Deprecated form:
function foo_prompt()
clink.prompt.value = "FOO "..clink.prompt.value.." >>"
--return true -- Returning true stops further filtering.
end
clink.prompt.register_filter(foo_prompt, 10)
-- Replace with new form:
local foo_prompt = clink.promptfilter(10)
function foo_prompt:filter(prompt)
return "FOO "..prompt.." >>" --,false -- Adding ,false stops further filtering.
endline
Returns the offset to the start of the delimited command in the line that's being effectively edited. Note that this may not be the offset of the first command of the line unquoted as whitespace isn't considered for words.
-- Given the following line; abc& 123
-- where commands are separated by & symbols.
line:getcommandoffset() == 4Returns the position of the cursor.
Returns the last word of the line. This is the word that matches are being generated for.
line:getword(line:getwordcount()) == line:getendword()Returns the current line in its entirety.
Returns the word of the line at index.
Returns the number of words in the current line.
Returns a table of information about the Nth word in the line. The table returned has the following scheme:
{
offset, -- [integer] offset where the word starts in the line:getline() string.
length, -- [integer] length of the word.
quoted, -- [boolean] indicates whether the word is quoted.
delim, -- [string] the delimiter character, or an empty string.
}log
Writes info message to the Clink log file. Use this sparingly, or it could cause performance problems or disk space problems.
os
Changes the current directory to path and returns whether it was successful.
Copies the src file to the dest file.
Returns command string for doskey alias name.
Returns doskey aliases in a table with the following scheme: { {name:string, command:string}, ... }.
Returns the current directory.
Returns the value of the named environment variable, or nil if it doesn't exist.
Returns all environment variables in a table with the following scheme: { {name:string, value:string}, ... }.
Returns the fully qualified file name of the host process. Currently only CMD.EXE can host Clink.
Returns dimensions of the terminal's buffer and visible window. The returned table has the following scheme:
{
bufwidth, -- [integer] width of the screen buffer
bufheight, -- [integer] height of the screen buffer
winwidth, -- [integer] width of the visible window
winheight, -- [integer] height of the visible window
}Collects directories matching globpattern and returns them in a table of strings.
When extrainfo is true, then the returned table has the following scheme: { {name:string, type:string}, ... }.
The type string can be "file" or "dir", and may also contain ",hidden" and ",readonly" depending on the attributes (making it usable as a match type for builder:addmatch()).
Collects files and/or directories matching globpattern and returns them in a table of strings.
When extrainfo is true, then the returned table has the following scheme: { {name:string, type:string}, ... }.
The type string can be "file" or "dir", and may also contain ",hidden" and ",readonly" depending on the attributes (making it usable as a match type for builder:addmatch()).
Returns whether path is a directory.
Returns whether path is a file.
Returns whether path has the hidden attribute set.
Creates the directory path and returns whether it was successful.
Moves the src file to the dest file.
Removes the directory path and returns whether it was successful.
Sets the name environment variable to value and returns whether it was successful.
Deletes the file path and returns whether it was successful.
path
path.getbasename("/foo/bar.ext") -- returns "bar"path.getdirectory("/foo/bar") -- returns "/foo/"
path.getdirectory("bar") -- returns nilpath.getdrive("e:/foo/bar") -- returns "e:"
path.getdrive("foo/bar") -- returns nilpath.getextension("bar.ext") -- returns ".ext"
path.getextension("bar") -- returns ""path.getname("/foo/bar.ext") -- returns "bar.ext"Examines the extension of the path name. Returns true if the extension is listed in %PATHEXT%. This caches the extensions in a map so that it's more efficient than getting and parsing %PATHEXT% each time.
path.isexecext("program.exe") -- returns true
path.isexecext("file.doc") -- returns falsepath.join("/foo", "bar") -- returns "/foo\bar"Cleans path by normalising separators and removing "." and ".." elements. If separator is provided it is used to delimit path elements, otherwise a system-specific delimiter is used.
path.normalise("a////b/\\/c/") -- returns "a\b\c\"rl
Undoes Readline tilde expansion. See rl.expandtilde for more information.
rl.collapsetilde("C:\Users\yourusername\Documents")
-- The return value depends on the expand-tilde configuration variable:
-- When "on", the function returns "C:\Users\yourusername\Documents".
-- When "off", the function returns "~\Documents".
-- Or when force is true, the function returns "~\Documents".Performs Readline tilde expansion.
When generating filename matches for a word, use the rl.expandtilde and rl.collapsetilde helper functions to perform tilde completion expansion according to Readline's configuration.
Use rl.expandtilde to do tilde expansion before collecting file matches (e.g. via os.globfiles). If it indicates that it expanded the string, then use rl.collapsetilde to put back the tilde before returning a match.
local result, expanded = rl.expandtilde("~\Documents")
-- result is "C:\Users\yourusername\Documents"
-- expanded is true
-- This dir_matches function demonstrates efficient use of rl.expandtilde()
-- and rl.collapsetilde() to generate directory matches from the file system.
function dir_matches(match_word, word_index, line_state)
-- Expand tilde before scanning file system.
local word = line_state:getword(word_index)
local expanded
word, expanded = rl.expandtilde(word)
-- Get the directory from 'word', and collapse tilde before generating
-- matches. Notice that collapsetilde() only needs to be called once!
local root = path.getdirectory(word) or ""
if expanded then
root = rl.collapsetilde(root)
end
local matches = {}
for _, d in ipairs(os.globdirs(word.."*", true)) do
-- Join the filename with the input directory (might have a tilde).
local dir = path.join(root, d.name)
table.insert(matches, { match = dir, type = d.type })
end
return matches
endReturns the value of the named Readline configuration variable as a string, or nil if the variable name is not recognized.
Returns a boolean value indicating whether the named Readline configuration variable is set to true (on), or nil if the variable name is not recognized.
settings
Adds a setting to the list of Clink settings and includes it in clink set. The new setting is named name and has a default value default when the setting isn't explicitly set.
The type of default determines what kind of setting is added: boolean, integer, and string values add the corresponding setting type. Or if the type is table then an enum setting is added: the table defines the accepted values, and the first value is the default value. Or if it's a string type and the name starts with "color." then a color setting is added.
name can't be more than 31 characters.
short_desc is an optional quick summary description and can't be more than 47 characters.
long_desc is an optional long description.
settings.add("myscript.myabc", true, "Boolean setting")
settings.add("myscript.mydef", 100, "Number setting")
settings.add("myscript.myghi", "abc", "String setting")
settings.add("myscript.myjkl", {"x","y","z"}, "Enum setting")
settings.add("color.mymno", "bright magenta", "Color setting")Returns the current value of the name Clink setting.
If it's a color setting and the optional descriptive parameter is true then the user friendly color name is returned.
Sets the name Clink setting to value and returns whether it was successful.
string
Splits text delimited by delims (or by spaces if not provided) and returns a table containing the substrings.
Returns a hash of the input text.
[other]
Deprecated; don't use this. See line for more information.
This is an obsolete global variable that was set while running match generators. It has been superseded by the line type parameter passed into match generator functions when using the new clink.generator API.
Changes
Releases from chrisant996/clink fork
v1.1.10
- Fixed #32 hooking
ReadConsoleWon Windows 7.
v1.1.9
- Added backward compatibility for
clink.match_display_filter. The clink-completions/git.lua script uses it a lot, and that should all be working now. settings.addadds a color setting when the type is string and the name starts with "color.".settings.getnow has an extra parameter to request the user friendly color name when getting a color setting.- Added
clink.version_encodedvariable with the Clink version number as MMmmmpppp (e.g. v1.1.9 is10010009) to make it easy for scripts to check for feature availability. - The
clink infocommand now shows Lua script paths as well. - Fixed backward compatibility for loading scripts from the profile directory (if
clink.pathisn't set, then load scripts from the DLL directory and the profile directory). - Fixed some
color.inputbleed through to other things (introduced in v1.1.5). - Fixed scroll commands (regression introduced by input line color in v1.1.5).
- Fixed horizontally sorted match display and re-enabled the performance fix from v1.1.4.
- Fixed wildcard evaluation with non-file and non-directory matches (e.g. a branch name
origin/masteraccidentally didn't matchoror*mabecause of the/). - Fixed sort order of
foo\vsfoo.bar\when displaying matches or using themenu-completefamily of commands. - Fixed potentially-missing trailing path separator when
menu-completecompletes a directory match (regression introduced by wildcard matching in v1.1.5). - Other obscure minor fixes.
v1.1.8
- Fixed file match completions when an argmatcher only generates flag matches.
- Fixed automatic inferring whether Readline should use filename completion and/or display rules (regression introduced by backward compatibility in v1.1.3-alpha).
- Fixed backward compatibility for
clink.find_files()andclink.find_dirs()(regression introduced by performance improvement in v1.1.7).- Ignore extra arguments after the first one (the performance improvement in v1.1.7 revealed that some scripts call
clink.find_files()with extra invalid arguments; e.g. clink-completions/modules/matchers.lua). - Don't append a trailing path separator on directory names returned by these functions (the new
os.globfiles()andos.globdirs()functions do, but the oldclink.find_files()andclink.find_dirs()functions should not).
- Ignore extra arguments after the first one (the performance improvement in v1.1.7 revealed that some scripts call
- Fixed backward compatibility for coloring matches (regression introduced by backward compatibility changes in v1.1.4).
v1.1.7
- Performance improvement when displaying matches: When enumerating files and dirs, the
os.globfilesandos.globdirsfunctions have all the info about each file. Now they can return that info in a table. This frees the match display function from needing to do any further file system IO. The performance boost is noticeable. - Rewrote the color settings: the .fg and .bg sub-settings are gone, and the main setting now uses a more natural syntax (e.g.
clink set color.input bright yelloworclink set color.modmark bright cyan on blue). - Added "cmd" match type for shell (CMD.EXE) command completions.
- Added VT emulation for the reverse video SGR parameters.
- Fixed tab completion for
clink set setting, and also handle the new color setting syntax. - Fixed confusing behavior if multiple scripts try to add settings with the same name (now the first one succeeds and the rest report errors).
v1.1.6
- Hooked up tilde completion in the
cd,md, andrdcommand argmatchers. - Hooked up tilde completion with the
exec.enablesetting ("~\pro" matches "C:\Users\myusername\program.exe"). - When
terminal.emulationisauto, now it also detects ANSI{32|64}.DLL just like Clink 0.4.8 did.
v1.1.5
- The
menu-completefamily of commands now support matching?and*wildcards when thematch.wildsetting is enabled. - Added
colour.inputandcolour.modmarksettings for coloring Readline's input line. - Added
clink.upper()Lua function, and bothclink.lower()andclink.upper()are properly UTF8 aware now. - Added
clink-copy-wordcommand that copies the word at the cursor to the clipboard. - Added
clink.promptfiltersetting to control whether to filter the prompt with Lua scripts. - Renamed
terminal.emulatesetting toterminal.emulation. - Improved executable file extension logic to consistently use %PATHEXT% (and efficiently).
- Improved file extension logic (e.g. "file.foo bar" has no extension because of the space).
- Updated arg matcher for
clinkitself (was missing some flags). - Changed
colour.hiddensetting to not be set by default. - Fixed #28 Tab completion for "~" does not work.
- Fixed #25 Unicode surrogate pairs (and emoji) input isn't working -- Microsoft Terminal renders the text correctly, but ConEmu and the default conhost still don't (and that isn't a Clink issue).
- Fixed screen size bug in Readline on Windows.
- Fixed the backwards values in the
terminal.emulationsetting. - Fixed
....so it works properly again. - Fixed case sensitive sorting of matches.
- Fixed script error when %PATHEXT% is empty.
- Fixed the
exec.cwdClink setting to default to true, so that the default behavior is consistent with how v0.4.x behaved. - Fixed the
cd,md,rd, etc argmatchers to only match one argument to be consistent with the actual command syntax.
v1.1.4
- Automatically detect when running inside ConEmu and disable Clink's Virtual Terminal emulation.
- Added
search-ignore-caseinputrc variable that makes the history search commands case insensitive. - Suppress adding a space after completing a flag match that ends with
:or=(e.g.msbuild -maxCpuCount:). - Report any errors while loading Lua scripts.
- Report an error if a Lua script tries to add a flag string that begins with a letter.
- Fixed slow printing of possible matches. Readline is inefficient about emitting output, so Clink supplies a custom implementation.
- Fixed some bugs in auto detection of flag prefix characters.
- Fixed backward compatibility for flags, and for args when merging two parsers by calling
clink.arg.register_parser('foo')multiple times for the same command string. - Fixed truncated message when the last line of a prompt exceeds 128 characters.
- Fixed abort (Ctrl+G or Esc) in non-incremental history search mode.
- Fixed saved values for settings added by Lua scripts; now the saved value is available to the script immediately on adding the setting, and saved values are retained even if the setting isn't always added by the script.
- Fixed (and documented) shorthand form for defining an argmatcher.
- Fixed length of colored match prefix after a path separator.
- Fixed normalizing a slash by itself (
command /mustn't becomecommand \since that can interfere with completing flags). - Fixed the
completion-auto-query-itemsinputrc variable. - Fixed the key binding list to correctly respect
completion-display-width. - No visible effect yet: internal change that parses the input line to identify colors to use for each word (command, argument, flag, etc), but the colors aren't yet applied to the input line.
v1.1.3-alpha
- Fixed argmatcher lookup to be more strict, like in Clink 0.4.9 (match exact names, or name plus an extension from %PATHEXT%).
- Backward compatibility:
- Most things should work now.
- Dropping the new Clink on top of the vendor\clink directory in Cmder seems to work -- but make a backup before you try this at home!
- API changes:
- Added
log.info()function. - Added Clink version numbers in
clink.version_major, etc. - Added
_argmatcher:getwordbreakinfo()callback; removed_argmatcher:setprefixincluded()(it was a mess, and it was new to v1.x, so there's no compatibility concern with removing it). - Deprecated
_argmatcher:setflagprefix(); now it happens automagically when using_argmatcher:addflags(). - Introduced several deprecated functions to support backward compatibility.
- Added
- Improvements to Lua debugger:
- Added
lua.traceback_on_error,lua.break_on_error, andlua.break_on_tracebacksettings to make debugging script errors easier. - Made
pause()consistent about pausing in the caller (rather than sometimes inside the pause command itself). - The debugger automatically shows the stack trace when entering debug mode, and on every pause.
- Show 3 lines of source context by default.
- The help list is sorted now.
- Fixed the
setcommand in the debugger to behave as documented.
- Added
v1.1.2-alpha
- Documentation is mostly updated; just the argmatcher Lua API and Clink command line options are left to be documented.
- Added
history.max_linessetting that controls how many lines of command history to save (1 to 50000, default is 2500). - Added
readline.hide_stderrsetting that can suppress stderr output from the Readline library. - For backward compatibility with 0.4.8,
clink_inputrcfiles are loaded as well. - Lua script API changes:
addmatch()in Lua scripts takes an optional match type argument.- Removed
displayable,aux, andsuffixfields in matches. - Revert the change to disallow mixing file/directory/symlink with other match types (it broke the tests and certain completion scenarios).
- Fixed issues:
- Other fixes:
- There should be no more problems running on Windows Insider builds because Clink now uses Detours for hooking APIs.
- Fixed crash in
insert-completionsdue to heap failure (introduced by the performance changes for displaying matches). - Fixed
clinkandhistorybuilt-in aliases (solve glitchy path problem). - Fixed scrolling to top of screen buffer.
- Fixed env var and
setcompletions. - Fixed
tilde-expandfor quoted text. - Fixed Esc in Readline's digit argument input mode (it doesn't try to cancel the mode, because that's not how Readline is documented to work).
- Fixed exit code from some
clinkcommand line options.
- Set locale to UTF8 much earlier to avoid quirky behavior early in script processing.
v1.1.1-alpha
- Exclusively use Readline's completion implementation. This (with fixes and enhancements in Readline itself) makes the completion experience much nicer and more sophisticated, and removes a lot of code that was added in v1.0.0a0.
- Exclusively use Readline's key binding implementation. This makes it possible to have a single consistent way to set key bindings (inputrc) and for
clink-show-helpto list all key bindings, and removes a lot of code that was added in v1.0.0a0. - Converted all of Clink's internal key behaviors to be implemented as commands that can be bound in the inputrc file.
- Rewrote and refactored the pagination routine to be used in multiple places.
- Fixed prompt filtering to correctly use the specified priority order.
- Readline library:
- Updated the Readline library from v6.2 to v8.0. This picked up lots of bug fixes and new capabilities (for example colored completions).
- Changed Readline to support backslash as a path separator.
- The pager prompt in Readline is optionally colored, controlled by the
colour.interactClink setting. - Added
completion-auto-query-itemsconfig variable (on by default) which asks whether to list possible matches when the number of lines listed will fill one screen page. - Added
history-point-at-end-of-anchored-searchconfig variable in inputrc to make the cursor point behave like 4Dos/4NT/TakeCommand when searching forward and backward through command history. - Fixed prev history at top of history.
- Fixed to get the current values of environment variables when needed, rather than always getting the value from whenever Clink was started.
- Fixed coloring directory completions.
- Fixed
menu-completefor\dirand.and... - Fixed slow performance when displaying matches. Readline was calling stat() at least once per match (!!). A new match type field enables faster performance, coloring readonly and hidden file matches, applying filename completion rules only to filenames (vs branch names or other text strings), correct match de-duplication, and more. The Lua match APIs can supply the new match type.
- Fixed inserting a completion to happen as a single undo group.
- Fixed tilde to map to
%USERPROFILE%instead of%APPDATA%on Windows.
- Typing a directory by itself uses
cd /dto change to the directory:- Typing a directory with a trailing path separator changes to the directory.
- Typing
..\changes to the parent directory. - Typing
...or....etc moves up an extra parent directory level for each extra dot (2 dots move up one parent, 3 dots moves up two parents, etc). A trailing path separator is optional when there are more than 2 dots. - Typing
-orcd -orchdir -changes to the previous directory.
- Commands that are new, enhanced, or fixed:
- Added
add-historyandremove-historycommands (similar to 4Dos/4NT/TakeCommand). - Got the
menu-complete,menu-complete-backward, andold-menu-completecommands working (they never worked properly before in Clink).- Also added a corresponding
old-menu-complete-backwardcommand for reverse order. - All of the
*-menu-complete-*commands support wildcards (*and?).
- Also added a corresponding
- Added
clink-show-helpcommand (Alt+H). The help now lists all key bindings, and it shows user-friendly key names (likeA-UporC-x,C-rorC-S-PgUporA-C-S-F3). - Added
clink-popup-completionscommand that shows a popup window listing possible completions. Enter inserts the highlighted completion. - Added
clink-popup-directoriescommand that shows a popup window listing recent directories. Enter changes to the highlighted directory, or Shift+Enter inserts the highlighted directory in the editing line (or Ctrl+Enter). - Added
clink-popup-historycommand that shows a popup window listing command history. Enter executes the highlighted command, or Shift+Enter jumps to the highlighted command in the history (or Ctrl+Enter). - Added
clink-scroll-lineup,clink-scroll-linedown,clink-scroll-page-up,clink-scroll-page-down,clink-scroll-top, andclink-scroll-bottomcommands that do what it looks like they'd do and are bound to the keys it looks like they'd be. - Added
clink-expand-doskeycommand (Ctrl+Alt+f) that expands the current line according to the current doskey aliases. - Added
clink-expand-env-varcommand (Ctrl+Alt+e) that expands the environment variable at the cursor point. - Added
clink-exitcommand (Alt+F4) that exits CMD.
- Added
- Fixed keyboard input issues:
- Esc is a bindable key now (
\e[27;27~). - Added more bindable key combinations (run
clink echothen press keys to see the key sequence to use in the inputrc file). - Ctrl+@ (NUL) didn't work.
- Ins toggles insert/overwrite mode.
- Unbound keys are ignored now, instead of inserting gibberish characters (part of the terminal internal key sequence).
- Fixed input handling so the
quoted-insertcommand can work properly. - Fixed Esc while searching.
- Fixed vi mode (was working in v0.4.9, but not in v1.0.x).
- Esc is a bindable key now (
- Fixed command history issues:
- The
dont_add_to_history_cmdsClink setting is a space-delimited list of commands to not add to history. - Fixed bleeding between history banks.
- Fixed uninitialized variable that made history updates intermittently do nothing or corrupt the other history bank.
- Fixed output from
clink historyto convert to UTF16 when writing to the console (but write UTF8 when output is redirected).
- The
- Fixed terminal output issues:
- Added
terminal.emulateClink setting that controls whether Clink does VT emulation or passes all ANSI escape codes directly to the console host. For example, this lets the prompt and completion coloring take advantage of more sophisticated ANSI escape codes such as XTerm 256 color and 16 bit color support. - Added back support for the
prefer-visible-bellconfig variable. - Fixed underline support.
- Fixed handling for UTF8 output from Readline.
- Fixed invisible cursor point in Lua debugger.
- Added
- Completions:
- Added
match.sort_dirsClink setting that specifies where to sort directories in the list of possible completions: before files, mixed in with files, or after files. - Don't attempt completing incomplete UNC paths: at least the
\\server\share\path components are required (for anything shorter the OS APIs are guaranteed to fail, but will fail slowly). - Fixed sorting to use Unicode aware locale based sorting (like Windows does) instead of dumb UTF8 byte comparisons.
- Fixed arbitrary limit on completions (had been limited to 64KB worth of completions).
- Fixed quoting spaces in completions.
- Fixed to use the same list as CMD for characters that require quoting.
- Fixed normalizing UNC paths.
- Fixed volume relative completions (e.g.
x:foo). - Disallow mixing file/directory/symlink with other match types. This was to avoid a confusing/malfunctioning case in match display and prefix highlighting.
- Added
- Fixed UTF8 encoding in various Lua functions.
- Fixed printing stderr output from Readline, Lua, and Clink.
- Fixed crashes and other failures when starting Clink in 32 bit CMD.
- Fixed some memory leaks that accumulated with each new line of input.
- Fixed prompt filtering API to be backward compatible with v0.4.9 scripts.
- Fixed Lua errors from
clink set(it neglected to fully initialize Clink's Lua integration before loading Lua scripts). - Fixed UTF8 conversion bug that could truncate a string without fully converting it.
- Fixed serious rampant memory corruption bug in v1.0.x (not present in v0.4.9), which had been causing intermittent malfunctions and data corruption and crashes.
- Fixed multi-line doskey macros to show the prompt in between lines, like CMD does.
- Removed the 4096 byte limit on input.
- Renamed the Clink DLL back to what it was in v0.4.x, to fix compile time problems.
- Other fixed issues:
- mridgers #544 Clink v1.0.0.a1 doesn't support cyrillic characters keyboard input on Windows 10 with console V2.
- mridgers #543 Not compatible with Windows Insider Build 20150.
- mridgers #537 Clink breaks the CMDS tool.
- mridgers #520 Clink 1.0.0.a1 -
clink set history_io 1Error. - mridgers #519 Clink v1.0.0.a1 -
-s|--scripts [path]command line arg removed? - mridgers #516 Doskey $T not handled properly.
- mridgers #512 Command history missing in .history.
- mridgers #503 Keyboard shortcut for scrolling.
- mridgers #501 Ctrl+Backspace works now.
- mridgers #487 Clink breaks ConEmu-specific Escape codes.
- mridgers #480 History never saved.
- mridgers #465 Using LuaJIT (FFI).
- mridgers #456 Clear-screen not working properly when PROMPT is two lines long.
- mridgers #453 Wrong cursor position when a line contains non-printable characters.
- mridgers #442 Unable to paste more than 1024 characters using Ctrl+V.
- mridgers #422 Problem with filename modifiers.
- mridgers #420 Use NtSuspendProcess instead of CreateToolhelp32Snapshot to freeze the threads.
- mridgers #372 Provide a way to select a previous directory.
- mridgers #365 history-search behavior.
- mridgers #342 Clink_inputrc not being processed if it the clink_inputrc is a link (created via mklink).
- Fixed many other bugs.
Releases from mridgers/clink original repo
v1.0.0a1 (alpha test release)
- Improve terminal integration with the Readline library.
- Internal improvements to the built-in ecma48 terminal emulator.
- Fixed use after free in Doskey emulation.
- Fixed dash-dash flag completion.
- Search ancestors for a compatible target process (for when cmd.exe starts another process that subsequently starts clink; especially useful during development).
- Use clink/terminal's wcwidth() implementation.
- screen_buffer::set_cursor() should be relative to the visible area.
- Try to adjust the cursor position better when resizing the terminal.
- Some internal Lua functions needed the unquoted clink exe path.
- The origin path now affects the hash in the dll cache, to guard against directory moves.
- More code reorganization.
v1.0.0a0 (alpha test release)
- Extensive code reorganization, refactoring, and rewriting -- multiple times -- almost everything was touched.
- OS integration:
- Fixed Doskey macros on Win8, and on Win10.
- Fixed
clink_x??.exestartup stall on Windows 10. - Removed XP support. It doesn't load DLLs like Clink uses them.
- Removed Powershell support.
- Readline integration:
- Search for multiple places for [.|_]inputrc (fixes mridgers #258).
- Disabled Readline's completion code, and only use the clink alternative code.
- Removed redundant slash translation and shims to make it happen.
- Removed control of Readline's suffix appending and disabled it.
clinkcommands and flags:- Changed
--cfgdirto--profile, it's no longer required, and added help about it. - Added a
--versionoption to print Clink's version. - Added
clink infoto print information about Clink. - Added
clink echocommand to echo input key sequences to stdout. - Added
clink historycommand (fixes mridgers #172). - Added 'history' as an alias for
clink history. - Added internal
--listflag toclink setfor match generation. - Removed '--scripts' argument (fixes mridgers #206).
- Updated
clink autoruncommand's help text.
- Changed
- Lua scripts:
- Prefer
userprofileover other standard environment variables for where to look for lua scripts. - New API for argument style completion scripts.
- Refactored prompt filtering, and introduced new prompt filtering API.
- Refactored generating matches, and introduced new match generator API.
- Removed built in completions scripts for git, go, hg, and p4. There's better ones.
- Renamed many of clink's Lua functions.
- Moved functions from
clinktoosin Lua. - Removed
clink.is_match()in Lua; don't presume anything on anyone's behalf about matches. - Added some current dir functions in Lua.
- Added some env/dir functions in Lua.
- Exposed path manipulation functions to Lua.
- Embed the core Lua scripts instead of loading them from files.
- Prefer
- Terminal IO:
- Added a module for scrolling the screen.
- Rewrote the terminal emulation module, and all Readline IO goes through it.
- Use VT220-style control codes for special keys.
- If Alt is pressed send ESC in the input stream rather than setting meta bit.
- Replaced wcwidth() with a more complete and correct version.
- Settings:
- Added
clink_pathsetting for where to look for lua scripts. - Added
match.ignore_casesetting. - Added
files.unc_pathssetting for optional matching from UNC paths. - Added a setting to skip adding lines that start with
history. - Removed
esc_clears_linesetting. - Pasting CRLFs doesn't really make sense.
- Don't write out settings that are set to default.
- Added
- Make sure Ctrl-C doesn't modify history.
- Make a cached copy of Clink's DLL when injecting so as to not lock the master.
- Guard against Readline's writes to stderr.
- Remove
clink_inputrc_basefile and embed its content (fixes mridgers #257). - Include more metadata in the Clink's executables.
v0.4.9
- Fixed broken Doskey on Win10 (#438, #451)
v0.4.8
- Environment variable 'clink_profile' overrides Clink's profile path (#390).
- Load a clink_inputrc file from Clink's profile directory (fixes #406).
- Bug fixes;
- Redraw issues when prompts end in OSC ANSI codes (#387, #384).
- Fixed 'clink autorun --help' crash.
v0.4.7
- Bug fixes;
- Sometimes autorun tries to run clink.exe (#374).
- Autorun would cause cmd.exe to return an error if it wasn't interactive (#373).
v0.4.6
- HOME is only set if it is currently unset.
- Readline can be initialised with .inputrc and _inputrc files too (#258).
- Bug fixes;
- Executable completion;
- Paths from PATH were checked twice.
- Incorrect results were returned for words ending in '.' or '-'.
- Directories . and .. were incorrectly displayed.
- Fixed a crash if .bat script's stdout is redirected (#366).
- Occasional crash when injecting Clink (#351).
- Display errors;
- When editing near the window's right-hand edge (#347).
- Double display of multi-line prompts when resizing the terminal (#352).
- Very rare wrap artefacts when making the terminal window larger.
- Doskey emulation (#344).
- Improved 'clink autorun' help (#348).
- Fixed launching Clink when clink.bat is renamed (#357).
- Executable completion;
v0.4.5
- Improved 'clink autorun'. It now defaults to the Current User registry hive.
- 'clink set' gives more details for enumeration-type settings.
- Tab completion for p4vc.
- New settings 'history_expand_mode' to control history expansion in quotes (#317).
- Bug fixes;
- Use full width of the terminal (#337).
- Fixed MinGW compile error (#335).
- Autorun now defaults to the current user's hive (#332).
- Creating clink.html no longer needs Pandoc, plus it looks a bit better (#331).
- Added settings to control history expansion (#326).
- Correct fallback when 'use_altgr_substitute' is off (#325).
- Load history prior to saving it on shutdown (#318).
- Added Shift-Tab documentation and menu completion example (#190).
- Added shim for backwards menu completion (#190).
- Input handling now outputs '\e`Z' for Shift-Tab (#190).
- Updated Readme with current Premake info (#310).
- Guard against there being no buffer to read from (#304).
- Fixed artefacts when resizing conhost's buffer (#139).
- Clear remaining characters if scroll window was too small (#301)
- Escape % characters when expanding aliases (#280).
- Fixed leaking exception filters.
- Clearing the screen doesn't leave artefacts behind.
v0.4.4
- Completing .. behaves more like Bash (#277).
- Escape from yes/no question when Ctrl+C is pressed.
- Valid XP executables (#278, #289).
- Fixed n-th argument yank not working as expected (#254).
- Fixed prompt colours sometimes not working (#279, #286).
- Fixed '!0' causing Clink to crash.
- Save/restore cursor position in case Readline moves it.
v0.4.3
- Localised Y/N when auto-answering 'terminate?' prompt.
- $* would early out if there was no arguments.
- Disable ANSI code support if third party provides it.
- Installer can now set %CLINK_DIR% to install location.
- Improved output from 'clink set'.
- Support for Windows 10 Technical Preview.
- Ctrl-L now scrolls last line to the top of the window rather than clearing.
- New option to control how newline characters are pasted to the line.
- New options to control history;
- 'history_file_lines' - maximum lines saved to disk.
- 'history_ignore_space' - ignore lines prefixed with whitespace.
- 'history_dupe_mode' - how duplicate entries are handled.
- 'history_io' - load/save history from disk every line.
- Fixed nonfunctional numpad keys.
- Fixed missing WINCH signals if other processes resize the buffer.
- Support Alt codes sent from Conhost.
v0.4.2
- Prompt colouring no longer requires third party ANSI code utility.
- Override settings with environment variables prefixed with 'clink'.
- Ctrl-PgUp goes up a directory.
- Updated Go completions (by matrixik).
- Arguments to clink.arg.new_parser() now initialise parser's flags/args (from vladimir-kotikov).
- New clink.arg.add_flags() and clink.arg.add_arguments() functions.
- Removed footer and Alt-H tip for more succinct stdout output.
- Bug fixes;
- Windows XP works again.
- Fixed race condition in lua_execute().
v0.4.1
- Bug fixes;
- Various Unicode fixes causing corrupt environment variables.
- Fixed thread resume/suspend causing rare system-wide deadlock.
- Fixed incorrect translation of suffixed slash when completing flags.
- Add --nolog argument to disable file logging. Fix #187 Fix #154
- Added missing escape sequences from doskey emulation.
- Reinstated unix-kill-line key binding.
- Mapped PgUp/Down to search history using line typed so far.
- Added documentation covering escape codes for special keys.
- Added support for Windows' AltGr substitute Ctrl-Alt.
- Support for Readline's 'menu' style completion (see docs).
v0.4
- New features;
- Better 'clink.arg' API. Easier, more intuitive, and more powerful.
- Whitespace prefix skips exec matching.
- Added a 'set' verb to easily change settings from the command line.
- Basic support for a shells other than cmd.exe.
- Completion for Go (contributed by Dobroslaw Zybort).
- Setting 'exec_match_style' to -1 disables it entirely.
- Make history persistence optional.
- Alias/doskey completion.
- Very basic support for Powershell.
- View cmd.exe's autorun entry without needing admin rights.
- New key bindings;
- Ctrl-Alt-C : Copy command line to the clipboard.
- Ctrl-Alt-E : Expand environment variable under cursor.
- Ctrl-Alt-U : 'up directory' (formerly Shift-Up).
- Ctrl-U : Adds '..' to the command line.
- Alt-H : Shows active keymap's key bindings.
- New Lua functions;
- clink.execute().
- clink.get_host_process().
- clink.match_files().
- clink.match_words().
- clink.get_console_aliases().
- Lots of bug fixes, including;
- Better command extraction.
- Fixed cmd.exe command paging and Ctrl-C/Ctrl-Break handling.
- Multiple locale fixes.
- Use localised text for 'Terminate batch job?' prompt.
v0.3
- Automatic answering of cmd.exe's 'Terminate batch script?' prompt.
- Coloured prompts (requires ANSICON or ConEmu).
- Added Shift-Up keyboard shortcut to automatically execute 'cd ..'
- Mapped Ctrl-Z to undo, Microsoft style.
- Improved integration of Readline;
- New input handling code (Ctrl-Alt combos now work).
- An implementation of the Termcap library.
- Fully functional Vi-mode support.
- Support for resizable consoles.
- Line wrapping now works correctly (issue 50).
- Adjustable executable match style (issue 65).
- Improved environment variable completion.
- Added settings file to customise Clink.
- New Lua features and functions;
- Matches can now be filtered in Lua before they are display.
- clink.quote_split().
- clink.arg.node_merge().
- clink.get_screen_info() (issue 71).
- clink.split() (for splitting strings).
- clink.chdir().
- clink.get_cwd().
- Functions to query Clink's settings.
- New command line options;
- '--profile
' to override default profile directory. - '--nohostcheck' disables verification that host is cmd.exe.
- '--pid' specifies the process to inject into.
- '--profile
- Update Mercurial completion (issue 73).
- Start menu shortcut starts in USERPROFILE, like cmd.exe
- Zip distribution is now portable.
v0.2.1
- The .history file now merges multiple sessions together.
- Fixed missing y/n, pause, and other prompts.
- Fixed segfault in loader executable.
- Better ConEmu compatibility.
v0.2
- Basic argument completion for 'git', 'hg', 'svn', and 'p4'.
- Traditional Bash clear screen ('Ctrl-L') and exit shortcuts ('Ctrl-D').
- Scrollable command window using 'PgUp'/'PgDown' keys.
- Doskey support.
- Automatic quoting of file names with spaces.
- Scriptable custom prompts.
- New argument framework to ease writing context-sensitive match generators.
- History and log file is now saved per-user rather than globally.
- Improved Clink's command line interface ('clink --help').
- More reliable handling of cmd.exe's autorun entry.
- General improvements to executable and directory-command completion.
- Symbolic link support.
- Documentation.
- Windows 8 support.
- Improved hooking so Clink can be shared with other thirdparty utilities that also hook cmd.exe (ConEmu, ANSICon, etc.).
v0.1.1
- Fixed AltGr+
on international keyboards. - Fixed broken completion when directories have a '-' in their name (Mark Hammond)
- The check for single match scenarios now correctly handles case-insensitivity.
v0.1
- Initial release.
License
Clink is distributed under the terms of the GNU General Public License, version 3.
Credits
Clink
Clink was originally built by Martin Ridgers (https://github.com/mridgers/clink).
Copyright (c) 2012-2018 by Martin Ridgers.
Clink has been forked and renovated by Christopher Antos (https://github.com/chrisant996/clink).
Portions Copyright (c) 2020 by Christopher Antos.
Libraries
GNU Readline library version 8.0 (https://tiswww.case.edu/php/chet/readline/rltop.html).
GNU Readline is distributed under the terms of the GNU General Public License, version 3.
Lua 5.2 (https://www.lua.org).
getopt library.
Copyright (c) 1997 Gregory Pietsch, placed in the public domain.
Detours library version 4.0.1 (https://github.com/microsoft/detours).
Copyright (c) Microsoft Corporation. All rights reserved.
Licensed under the MIT license.
Clink documentation embeds the highlight.js library (https://highlightjs.org).
Highlight.js is released under the BSD License.