1.5.0 • Published 9 months ago

ssed v1.5.0

Weekly downloads
-
License
MIT
Repository
github
Last release
9 months ago

Usage

> ssed --help
> something | ssed [commands]
> <input ssed --explain [commands]
> ssed [commands] <file

All commands use a "g/re/p"-like syntax:

cmd/match[/replace][/flags]

About

ssed is an alternative to 'sed'. Not a drop-in replacement, but used for similar tasks. I wanted more familiar and modern Regex support, and have kept adding more functions as ssed became more and more my go-to text manipulation tool.

Line rules transform on a line-by-line basis and, if only line rules are employed, support STDIN streaming.

Document rules transform the entire document. STDIN is read to completion before document rules are executed.

Like sed, and symbol can be used to separate the rule arguments, but unlike sed some separators change the behaviour of the command. The special separators *are ':' and '`'.

Separators

The separator can change the behaviour of the line rule. Rules that support pattern matches likely also support line and literal matches.

/  Default separator, indicates Regex. Supports flags.
:  Indicates a line-number rule
\`  Indicates a literal string match
   All other delimiters indicate Regex

s/\\w+/bar      regex match
s|\\w+|bar      alternative separator
s|\\w+|bar|i    with case insensitive flag enabled

s\`foo\`bar      literal match against 'foo'
s:1:bar        matches line 1

s{\\w+}bar      brackets can also be used (regex match)
s{\\w+}bar}i    but they don't have to match

Options

--explain                    Explains what the command will do.

--diff                       Only show differences
--no-diff                    Do not show differences

--color                      Enable ANSI colors (true if stdout is a TTY)
--no-color                   Disable ANSI colors

--ls                         Read file names from standard input (\`ls | ssed --ls\`)

--input=fromfile             Use 'fromfile' as input.
--input fromfile

--input=fromfile1,fromfile2  Run against multiple files.
--input fromfile1 --input fromfile2

--no-input                   Do not use any file as input.

--write                      Write each changed file in place.
--write=tofile               Provide a destination file name.
--write-rename=%.backup      Use the input filename in place of '%'
--no-write                   Do not write each changed file in place.

--interactive                Ask before writing the file
--no-interactive             Do not ask before writing the file

--dry-run (-n)               Show which files would be affected.
--no-dry-run                 Do not show which files would be affected.

Line Rules

Line rules operate on every line. Commands 'on', 'after' and 'off' share the on/off state.

s/$search/$replace                Replace the first instance of 'search' with 'replace'
(aka sub/…/…)
g/$search/$replace                Replace every instance of 'search' with 'replace'
(aka gsub/…/…)
t/$pattern (aka take/…)         Only print the matching part of the line, or print the entire line if 'pattern' doesn't match
r/$pattern (aka rm/…)           Remove the matching part of the line, or print the entire line if 'pattern' doesn't match
1/$pattern                      Only print the first group of the match
1                               Only print the first "column" (columns are separated by whitespace)
cols/$pattern/$columns          Split the line by 'pattern' (default is /\\s+/) and print columns (joined by ' ')
cols/$pattern/$columns/$joiner  Same, but columns are joiner by $joiner

on/$pattern                     Start printing on the line where 'pattern' is matched
off/$pattern                    Stop printing on the line where 'pattern' is matched
after/$pattern                  Start printing on the line *after* 'pattern' is matched
toggle/$pattern                 Turn printing off at the matching line, then off, then on...

p/$pattern (aka print/…)        Only print lines that match 'pattern'
d/$pattern (aka del/…)          Do not print lines that match 'pattern'
!p/$pattern (aka !print/…)      Alias for d/del because I can't remember one (d) and always remember the other (p)

prepend/$text (aka prefix/…)
append/$text (aka suffix/…)     Adds text to the beginning (prepend) or end (append) of the line
surround/$prefix/$suffix

uniq (aka unique)               Only print unique lines
uniq/$pattern                   Only print matching lines, and only unique matches (uniqueness is determined by the matching regex)

Document Rules

sublines/$pattern/$replace    For every line that matches, insert one line from replace. Remaining lines will
     (aka sl/…)               be inserted into the last matched line. Does not do regex replacement.

sort  sort/$pattern           Sort the lines alphabetically using localeCompare.
                              If a pattern is provided, the matching part of the line will be used, but the
                              entire line will be printed.
sortn   sortn/$pattern        Sort the lines numerically. If no pattern is given, it matches the *first* number.
reverse                       Obvious
line                          Prepend each line with the line number

begin:$prepend
border:$prepend:$append       Prepend, append, or surround the document (add header/footer)
end:$append
join     join/$separator      Join lines with a space (or optional separator)

Conditions

You can apply rules only under certain conditions, e.g. 'if/{pattern} {rule}' only runs `rule` only lines that match `pattern`.

You can even group rules using `{ rules… }`, and rules can be negated with a preceding '!'.

if/$pattern $rule
!if/$pattern $rule
between/$onPattern/$offPattern $rule

Example: ssed 'if/first-name|last-name' { s/colin/REDACTED/i s/gray/REDACTED/i }

Line Number rules

Using the special delimiter ':' you can apply most rules on line numbers instead of line content. In the case of the 'sub' command, the entire line will be replaced with the literal text.

For example s:1:replace Replaces line 1 with the word "replace" p:1 Only print line 1

Not all rules support this feature, but typically any rule that could support it, does

Line numbers can be expressed as a single number, a range, an open range, a modulo operation (with offset), and a comma-separated list of line rules. p:1 Only matches the line number (only matches line 1) p:%2 Matches lines that are modulo-N (even lines) p:%2-1 Matches lines that are modulo-N minus Y (odd lines) p:1,3,5 Matches the listed line numbers (and only these) p:1-5 Matches the range of number, inclusive (1,2,3,4,5) p:9- Matches the line number and all subsequent lines (lines 9 and onward) p:-9 Matches lines up to and including the line number (lines 1-9) p:1-5,10-15,20,30+ Line rules can be mixed and matched

1.2.0

10 months ago

1.4.5

9 months ago

1.4.4

9 months ago

1.4.2

9 months ago

1.5.0

9 months ago

1.4.1

9 months ago

1.4.0

9 months ago

1.3.0

10 months ago

1.1.1

1 year ago

1.1.0

1 year ago

1.0.0

2 years ago