================================== Welcome to MagicInvoke! ================================== **MagicInvoke** is an `invoke `_ extension that adds support for lots of goodies: * ``*args`` **and** ``**kwargs`` **support!** See how easy it is here: :ref:`args-kwargs`. * **Automatic parameter defaults from ctx!** Have you ever wondered why you can put ``'run': {'echo': True}`` in ``invoke.yaml`` and suddenly ``echo=True`` gets passed to all ``ctx.run`` s, but you can't do the same for your own tasks? Wonder no longer with :meth:`magicinvoke.get_params_from_ctx`! Here's how you would implement a task like ctx.run:: @magictask def myrun(ctx, cmd, echo=False): pass * **Make-like caching, file dependency recognition, and work-avoidance!** Cache the results of expensive functions on disk:: @magictask(skippable=True) # Caches to /tmp/.minv/tasks.expensive_task/xyz123 def expensive_task(ctx, url): return ctx.run('wget {}'.format(url)).stdout Also works with input/output file based functions:: @skippable def compile(ctx, input_c_files, output_executable, debug=False): # Will not run if all input_c_files are older than output file and output # file was last generated with same 'flag' values like 'debug' arg. ctx.run('gcc {} -o {}'.format(' '.join(input_c_files), output_executable)) For API doc, see :meth:`magicinvoke.skippable`. Note that aside from re-running based on input/output file timestamps, ``@skippable`` also attempts to detect changes to the source of your function. We cannot catch all changes that affect your function output, but we record the hash of two things to determine that your function has remained unchanged since last run: The compiled bytecode and the number of parsed characters on each line of the source. So, if you want to ensure a function is re-run, just add a comment within it on a new line! For more examples, check out a basic :ref:`data-pipeline`. or a Py3-specific, more advanced :ref:`make-replacement`. Note that chaining these is safer with pre/post feature of tasks, see :ref:`skippable-warning`. * **Arbitrary task filtering!** Implements the ``skip_ifs`` argument for tasks, a rename of ``checks`` from `from this issue `_. Basically, you can add your own functions that decide whether or not your task should run:: @task def always_skip(ctx): return True @task(skip_ifs=[always_skip]) def never_runs(ctx): print("Never happens!") * **Autoprint styles + overriding from cmd-line**:: @task(autoprint='unix') # Prints lists new-line-separated, dicts tab-separated @task(autoprint='json') # Pretty-printed json Includes ability to set autoprint without modifying tasks: `inv -D autoprint=unix my-task-name` * **Better error messages for end-users (see bugfixes for more)**:: inv testing arg0 old: 'testing' did not receive required positional arguments: 'important_arg1'. new: 'testing' did not receive required positional arguments: 'important_arg1'. Signature: testing --output-file * **Single-step namespaced tasks!** Merges the very helpful `patch `_ written by @judy2k. No longer need to manually add each function to the current namespace, making it easier to switch over to explicit namespaces. See his GitHub issue for usage. * **Program.invoke, thanks @rectalogic!** Example usage:: @task def infinite_recursing_task(c, recursed=False): program.invoke(c, "infinite-recursing-task", recursed=True) `Longer explanation here. `_ * **Bugfixes** * Fix cryptic error when doing ``ctx.cd(pathlib.Path)`` (#454). * Fix help documentation for misspelled variable names silently being ignored (#409). * Fix help documentation with - instead of _ being silently being ignored (#398). * Fix silently ignoring config file path (#560). * Fix cryptic error when task passed ``pre=func`` instead of ``pre=[func]``. * Fix cryptic error when ``@task('func')`` instead of ``@task(func)`` (#598). * Private tasks (starting with ``_``) no longer show up in task list. Get Started ----------- ``pip install magicinvoke`` Beginner's Note: `Invoke's documentation `_ is the best place to start, as the majority of using this library is just like using regular ``invoke``. You should still install ``pip install magicinvoke`` to get the improved error messages. Examples --------- .. toctree:: :maxdepth: 1 :glob: examples/** .. _api: API Documentation ----------------- .. toctree:: :maxdepth: 2 :glob: api/* Thanks to Invoke ----------------- This module is 95% ``invoke`` code. All praise for the extensibility, durability and readability of ``invoke``-using code goes to ``bitprophet`` and friends. It's a fun library to use, and here's hoping ``magicinvoke`` gives it the little boost it needs for big, monolithic projects, and serves as a testing-grounds for potentially breaking features like ``**kwargs`` on tasks, since I'm too lazy to write enough tests to get into the real ``invoke`` library! If you enjoy them (but not too often), you should also thank Anton Backer for the very handy ``colored-traceback``, which will be automatically activated if installed.