Show HN: Murex – non-Posix shell designed for productivity - 7 minutes read


murex shell guide

murex is a shell, like bash / zsh / fish / etc. It follows a similar syntax to POSIX shells like Bash however supports more advanced features than you'd typically expect from a $SHELL.

It aims to be similar enough to traditional shells that you can retain most of your muscle memory, while not being afraid to make breaking changes where "bash-isms" lead to unreadable, hard to maintain, or unsafe code.

murex is designed for DevOps productivity so it isn't suited is high performance workloads beyond what you'd typically run in Bash (eg pipelines forked as concurrent processes).

The language employs a relatively simple syntax modelled loosely on functional and stack-based programming paradigms (albeit without the LISP-style nested parentheses that scare a lot of developers) while maintaining compatibility with POSIX-like shells (eg Bash) wherever sensible. For example, a program structure could look like the following:

However where murex differs is that, while the pipe token, is supported for compatibility with existing shells, murex idioms prefer used for readability as it clearly demonstrates the direction of the data flow. eg

The language supports multiple data types natively; such as JSON, YAML, CSV, S-Expressions and even loosely tabulated terminal output (eg , ). This makes passing data through the pipeline and parsing output easier when dealing with more complex arrangements of data than a simple byte stream in traditional shells like Bash.

Aside the murex being carefully designed with scripting in mind, the interactive shell itself is also built around productivity. To achieve this, we wrote our own readline library. Below is an example of that library in use:

The above demo includes the following features of murex's bespoke readline library:

Despite the amount of features added to shell, we have tried to keep the amount of "magic" to a minimum and follow a pretty standard structure so the language is predictable. However there are times when a little magic goes a long way. For example murex's support for complex data objects of differing formats is managed in the pipeline so you don't need to think about the data format when querying data from them.

The index function () alters its matching algorithm depending on the piped data type and sets the data type depending on the file extension or MIME type.

Sometimes you will want fewer guesswork or just the robustness of a forced behavior. On those occasions you can remove one layer of magic by casting the data type:

This awareness of data structures is also utilised in (which will cycle through each index in an array) and (key/value iteration against complex objects). See GUIDE.control-structures for more details on these and other control structures.

murex employs a few methods to make shell scripting more robust:

Bash, for all it's power, is littered with hidden traps. The aim of murex is to address as many of them as we can without taking the flexibility nor power away from the interactive command line. This is achieved through a couple of key concepts:

The biggest breaking change from regular shells is how globbing isn't expanded by the shell by default. This is instead done by inlining functions as arrays:

The advantage of murex's method is that we can now offer other ways of matching file system objects that follows the same idiomatic pattern:

(more information on , and are available in GUIDE.quick-start).

However there will be occasions when you just want an inlined expansion (eg when using an interactive shell) and that can be achieved via the command prefix:

murex takes a slightly different approach to command line autocompletion, both from a usability perspective as well as defining completion rules.

Inspired by IDEs, murex queries man pages directly for flags as well as "tooltip" descriptions. Custom completions are defined via JSON meaning simple commands are much easier to define and complex commands can still fallback to using dynamic shell code just like they are in other shells.

This makes it easier to write completion rules as well as making the code more readable. An example of s autocompletion definition:

murex also supports several different styles of completion suggestion "popups" to cater for different scenarios (demo above) as well as built in support for jumping to files within nested directories quickly and easily:

Like traditional shells, murex is verbose with errors by default with options to mute them. However murex also supports cleaner decision structures for when you want you want errors captured in a useful way:

As well as a saner syntax:

Unlike traditional shells, murex is designed with a test and debugging modes baked into the shell language. This means you can write tests against your shell scripts as part of the shell scripts itself.

If test mode isn't enabled then any commands are skipped without being executed so you can liberally include test cases throughout your functions without worrying about any performance impact.

Or if you're already a seasoned Bash developer then you read the Quick Start Guide, GUIDE.quick-start, to jump straight into using murex.

There are various ways you can load murex on to your system. See INSTALL for details.

murex makes heavy use of testing and CI/CD to ensure the latest builds are safe for use.

Each push to and also creates a new docker container, and (for the branch).

Source: Murex.rocks

Powered by NewsAPI.org

Keywords:

Bash (Unix shell)Z shellSyntax (programming languages)POSIXShell (computing)Bash (Unix shell)Shell (computing)Muscle memoryBackward compatibilityBash (Unix shell)Real-time computingDevOpsProductivity improving technologiesSupercomputerBash (Unix shell)Pipeline (computing)Fork (software development)Concurrent computingProcess (computing)Programming languageGraph (discrete mathematics)SyntaxMathematical modelFunctional programmingStack-oriented programming languageProgramming paradigmLisp (programming language)Nested functionBracketSoftware developerBackward compatibilityPOSIXShell (computing)Bash (Unix shell)Structured programmingPipeline (Unix)Lexical analysisBackward compatibilityShell (computing)Programming languageData typeJSONYAMLComma-separated valuesS-expressionComputer terminalInput/outputDataPipeline (software)Input/outputDataBitstreamShell (computing)Bash (Unix shell)Scripting languageShell (computing)Productivity improving technologiesGNU ReadlineLibrary (computing)Library (computing)Technology demonstrationGNU ReadlineLibrary (computing)Shell (computing)Programming languageObject (computer science)Pipeline (software)Data typeInformation retrievalArray data structureFunction (mathematics)Pattern matchingAlgorithmPipeline (Unix)Data typeData typeFilename extensionMedia typeAbstraction layerData typeData structureArray data structureArray data structureAttribute–value pairMarkov decision processObject (computer science)Control flowControl flowMethod (computer programming)Shell scriptBash (Unix shell)Command-line interfaceBackward compatibilityShell (computing)Glob (programming)Shell (computing)CONFIG.SYSInline expansionSubroutineArray data structureSubroutinePattern matchingFile systemObject (computer science)Inline expansionShell (computing)Command-line interfaceAutocompleteUsabilityAutocompleteIntegrated development environmentSQLMan pageTooltipJSONCommand-line interfaceCommand-line interfaceType systemShellcodeShell (computing)AutocompletePop-up adSharewareComputer fileDirectory (computing)Shell (computing)Software bugSyntaxShell (computing)Test (Unix)DebuggingMode (computer interface)Scripting languageShell scriptShell scriptSubroutineBash (Unix shell)Software developmentSoftware testingContinuous integrationDocker (software)