## dist_cpan-RBT-LogP6-Writer-StackDriver.md
# NAME

**LogP6::Writer::StackDriver** - writer implementation for local `stackdriver` logging

# SYNOPSIS

Useful for logging within the Google Cloud environment where fluentd will pickup logs
and feed them into StackDriver.

Use of this module ensures your messages are treated as single entries (no multi-line issues)
and enables use of triggers/calculations on special fields via MDC.

# CONFIGURATION

You can configure the writer from code by instantiating object of
`LogP6::WriterConf::StackDriver` class. It takes the following parameters:

* `name` - name of the writer configuration
* `handle` - location to write the json formatted log lines; STDOUT by default.
* `use-mdc` - boolean property. Enabled by default. All content of LogP6 `MDC`
  will be passed to `stackdriver` as json fields.
* `use-mdc-cro` - boolean property. Enabled by default. Will look for and use the
  CRO request/response objects in the MDC information to fill out various HTTP related
  fields including `requestMethod`, `requestURL`, `userAgent`, `referer`, `remoteIp`,
  and `status`.
* `mdc-key-cro-request` - string property. `cro-request` by default. Tells the logger
  which field may provide the CRO request object.
* `mdc-key-cro-response` - string property. `cro-response` by default. Tells the logger which
  field may provde the CRO response object.
* `use-source-location` - boolean property, True by default. Will include the source
  location in the log entry. Use of this functionalty may slow down your porgram as it requires a `callframe` call
  for each log entry.

# EXAMPLE

```
use LogP6 :configure;   # use library in configure mode
use LogP6::WriterConf::StackDriver;
use Cro::HTTP::Router;

my $sd = LogP6::WriterConf::StackDriver.new(
  :handle($*ERR), # Change to use STDERR
  :name<audit>

  use-source-location => False,  # Disable source location

  mdc-key-cro-request => 'webapp-request',
);

cliche(
  :name<cl>,
  :matcher<audit>,
  grooves => ( writer($sd), filter(:level($debug)) ) # Debug level to $sd
);

my $app = route {
  get -> 'healthz' {

    # Note, only that instance of $log will have the MDC information. Consider creating
    # a context object for the request and passing it along the work pipeline.
    my $log = get-logger('audit');
    $log.mdc-put('webapp-request', request());
    $log.debug('Request for healthz');

    content 'text/plain', 'READY';
  }
}

$!cro-service = Cro::HTTP::Server.new(:host<0.0.0.0>, :port<10000>, :$app);
$!cro-service.start;

```

# AUTHOR

Rod Taylor [rbt@cpan.org](mailto:rbt@cpan.org)

Source can be located at:
[github](https://github.com/rbt/raku-LogP6-Writer-StackDriver). Comments and
Pull Requests are welcome.

# COPYRIGHT AND LICENSE

Copyright 2020 Rod Taylor

This library is free software; you can redistribute it and/or modify it under
the Artistic License 2.0.


## dist_zef-jonathanstowe-EventSource-Client.md
# EventSource::Client

A Raku client for [Server-Sent Events](https://www.w3.org/TR/eventsource/)

![Build Status](https://github.com/jonathanstowe/EventSource-Client/workflows/CI/badge.svg)

## Synopsis

```
use EventSource::Client;

react {
    whenever EventSource::Client.new(source => "http://127.0.0.1:7798/") -> $event {
        say "> " ~ $event.data;
    }
}

```

## Description

[Server-Sent Events](https://www.w3.org/TR/eventsource/) provide a mechanism for
timely delivery of server to client events over HTTP and can in some use-cases
be more convenient than a similar pattern implemented using Web Sockets and is
easier on the network than, for instance, HTTP polling by the client.

This library allows you to consume server sent events in a Raku program in
a reasonably idiomatic and reactive fashion.

## Installation

Assuming you have a working Rakudo installation then you should be able to
install this with `zef` :

```
zef install EventSource::Client

# Or from a local clone

zef install .

```

## Support

Please post any bugs, feature requests or patches at [github](https://github.com/jonathanstowe/EventSource-Client/issues)

## Copyright & Licence

This is free software, please see the <LICENCE> for details.

© Jonathan Stowe 2020-2021


## is-20nodal.md
is nodal

Combined from primary sources listed below.

# [In Type system](#___top "go to top of document")[§](#(Type_system)_trait_is_nodal "direct link")

See primary documentation
[in context](/language/typesystem#trait_is_nodal)
for **trait is nodal**.

Marks a [`List`](/type/List) method to indicate to hyperoperator to not descend into inner [`Iterable`](/type/Iterable)s to call this method. This trait generally isn't something end users would be using, unless they're subclassing or augmenting core [`List`](/type/List) type.

In order to demonstrate the difference consider the following examples, the first using a method (`elems`) that `is nodal` and the second using a method ([`Int`](/type/Int)) which is not nodal.

```raku
say ((1.0, "2", 3e0), [^4], '5')».elems; # OUTPUT: «(3, 4, 1)␤»
say ((1.0, "2", 3e0), [^4], '5')».Int    # OUTPUT: «((1 2 3) [0 1 2 3] 5)␤»
```


## dist_zef-dwarring-LibXSLT.md
[![Actions Status](https://github.com/libxml-raku/LibXSLT-raku/workflows/test/badge.svg)](https://github.com/libxml-raku/LibXSLT-raku/actions)

[[Raku LibXML Project]](https://libxml-raku.github.io)
/ [[LibXSLT Module]](https://libxml-raku.github.io/LibXSLT-raku)

# NAME

LibXSLT - Interface to the GNOME libxslt library

# SYNOPSIS

```
use LibXSLT;
use LibXML::Document;

# process a document with an internal '<?xml-stylesheet ..>' processing-instruction
my LibXML::Document $doc .= parse(location => 'foo.xml');
my Str $result = LibXSLT.process: :$doc;

# provide an external style-sheet
my LibXML::Document $xsl .= parse(location => 'bar.xsl', :!cdata);
my Str $result = LibXSLT.process: :$doc, :$xsl;

# OO interface
use LibXSLT::Document;
use LibXSLT::Stylesheet;
my LibXSLT $xslt .= new();

my LibXSLT::Stylesheet $stylesheet;
$stylesheet = $xslt.parse-stylesheet($xsl);
# -OR-
# get the stylesheet from a document's '<?xml-stylesheet ..>' processing-instruction
$stylesheet .= load-stylesheet-pi(:$doc);

my LibXSLT::Document::Xslt() $results = $stylesheet.transform(:$doc);
say $results.Str;

```

# DESCRIPTION

This module is an interface to the GNOME project's libxslt.

# OPTIONS

LibXSLT has some global options. Note that these are probably not thread or even fork safe - so only set them once per process. Each one of these options can be called either as class methods, or as instance methods. However either way you call them, it still sets global options.

Each of the option methods returns its previous value, and can be called without a parameter to retrieve the current value.

* max-depth

  ```
  LibXSLT.max-depth = 1000;

  ```

  This option sets the maximum recursion depth for a stylesheet. See the very end of section 5.4 of the XSLT specification for more details on recursion and detecting it. If your stylesheet or XML file requires seriously deep recursion, this is the way to set it. Default value is 250.
* max-vars

  ```
  LibXSLT.max-vars = 100_000;

  ```

  This option sets the maximum number of variables for a stylesheet. If your stylesheet or XML file requires many variables, this is the way to increase their limit. Default value is system-specific and may vary.
* set-debug-callback

  ```
  LibXSLT.set-debug-callback(&func ($fmt, *@args) );

  ```

  Sets a callback to be used for debug messages. If you don't set this, debug messages will be ignored.
* register-function

  ```
  LibXSLT.register-function($uri, $name, &func (|c) );
  $stylesheet.register-function($uri, $name, &func (|c) );

  ```

  Registers an XSLT extension function mapped to the given URI. For example:

  ```
  LibXSLT.register-function("urn:foo", "date",
    sub { now.Date.Str });

  ```

  Will register a `date` function in the `urn:foo` name-space (which you have to define in your XSLT using `xmlns:...`) that will return the current date and time as a string:

  ```
  <xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:foo="urn:foo">
  <xsl:template match="/">
    The date is: <xsl:value-of select="foo:date()"/>
  </xsl:template>
  </xsl:stylesheet>

  ```

  Parameters can be in whatever format you like. If you pass in a node-list it will be a [LibXML::Node::List](https://libxml-raku.github.io/LibXML-raku/Node/List) object in your Raku code, but ordinary values (strings, numbers and booleans) may be passed. Return values can be a node-list or a plain value - the code will just do the right thing. But only a single return value is supported (a list is not converted to a node-list).
* register-extension

  ```
  use LibXSLT::ExtensionContext;

  $stylesheet.register-extension($uri, $name, &func (LibXSLT::ExtensionContext) )

  ```

  Registers an XSLT extension element $name mapped to the given URI. For example:

  ```
  use LibXSLT::ExtensionContext;
  $stylesheet.register-element("urn:foo", "hello", sub (LibXSLT::ExtensionContext $ctx) {
          my LibXML::Node $style = $ctx.style-node;
          my LibXML::Node $insert = $ctx.insert-node;

  my $name = $style.getAttribute( "name" );

  $insert.addChild: LibXML::Text.new( "Hello, $name!" );

  });

  ```

  Will register a `hello` element in the `urn:foo` name-space that inserts a "Hello, X!" text node. You must define this name-space in your XSLT and include its prefix in the `extension-element-prefixes` list:

  ```
  <xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:foo="urn:foo"

  extension-element-prefixes="foo">

  <xsl:template match="/">
    <foo:hello name="bob"/>
  </xsl:template>
  </xsl:stylesheet>

  ```

  A `LibXSLT::ExtensionContext` object is passed, with three attributes:

  * style-node() - The current input node from the stylesheet document
  * source-node() - The current input node from the source document
  * insert-node() - The current output node in the transformed document

# API

The following methods are available on the LibXSLT class or object:

* process()

  ```
  my Str:D $result = LibXSLT.process: :$doc;
  my Str:D $result = LibXSLT.process: :$doc, :$xsl;

  ```

  Processes a document using the document's `<?xml-stylesheet ... ?>` processing instruction to locate and load a stylesheet.

  Security handlers may be used to intercept access to external documents on the file-system or network (see below).
* load-stylesheet-pi()

  ```
  my LibXSLT::Stylesheet $xslt .= load-stylesheet-pi: :$doc;

  ```

  Loads, but doesn't execute the stylesheet associated with the given document.
* parse-stylesheet($stylesheet-doc)

  `$stylesheet-doc` here is an [LibXML::Document](https://libxml-raku.github.io/LibXML-raku/Document) object (see [LibXML](https://libxml-raku.github.io/LibXML-raku)) representing an XSLT file. This method will return a [LibXSLT::Stylesheet](https://libxml-raku.github.io/LibXSLT-raku/Stylesheet) object. If the XSLT is invalid, an exception will be thrown, so wrap the call to parse\_stylesheet in a try{} block to trap this.

  IMPORTANT: `$stylesheet-doc` should not contain CDATA sections, otherwise libxslt may misbehave. The best way to assure this is to load the stylesheet with `:!cdata` flag, e.g.

  ```
  my LibXML::Document $stylesheet-doc .= parse(location => "some.xsl", :!cdata);

  ```
* parse-stylesheet(file => $filename)

  Exactly the same as the above, but parses the given filename directly.

# Input Callbacks

To define LibXSLT or LibXSLT::Stylesheet specific input callbacks, reuse the LibXML input callback API as described in [LibXML::InputCallback](https://libxml-raku.github.io/LibXML-raku/InputCallback).

* input-callbacks = $icb

  Enable the callbacks in `$icb` only for this LibXSLT object. `$icb` should be a [LibXML::InputCallback](https://libxml-raku.github.io/LibXML-raku/InputCallback) object. This will call `init_callbacks` and `cleanup_callbacks` automatically during parsing or transformation.

# Security Callbacks

To create security preferences for the transformation see [LibXSLT::Security](https://libxml-raku.github.io/LibXSLT-raku/Security). Once the security preferences have been defined you can apply them to an LibXSLT or LibXSLT::Stylesheet instance using the `security-callbacks()` method.

* LibXSLT.have-exslt()

  Returns True if the module was compiled with libexslt, False otherwise.

# PREREQUISITES

This module requires the libxslt native library to be installed. Please follow the instructions below based on your platform:

## Debian Linux

```
sudo apt-get install libxslt-dev

```

## Mac OS X

```
brew update
brew install libxslt

```

# VERSION

0.1.0

# LICENSE

This is free software, you may use it and distribute it under the same terms as Perl itself.

Copyright 2001-2009, AxKit.com Ltd.

# ACKNOWLEDGEMENTS

This Raku module is based on the Perl 5 XML::LibXSLT module. The `process()` method has been adapted from the Perl 5 XML::LibXSLT::Easy module.

With thanks to: Matt Sergeant, Shane Corgatelli, Petr Pal's, Shlomi Fish, יובל קוג'מן (Yuval Kogman)

# SEE ALSO

[LibXML](https://libxml-raku.github.io/LibXML-raku)


## dist_zef-lizmat-Ecosystem-Cache.md
[![Actions Status](https://github.com/lizmat/Ecosystem-Cache/actions/workflows/linux.yml/badge.svg)](https://github.com/lizmat/Ecosystem-Cache/actions) [![Actions Status](https://github.com/lizmat/Ecosystem-Cache/actions/workflows/macos.yml/badge.svg)](https://github.com/lizmat/Ecosystem-Cache/actions)

# NAME

Ecosystem::Cache - maintain a local cache of an ecosystem

# SYNOPSIS

```
use Ecosystem::Cache;

my $ec = Ecosystem::Cache.new;  # defaults to REA

$ec.update;  # make sure all distributions are up-to-date

```

# DESCRIPTION

The `Ecosystem::Cache` distribution provides the logic to maintain a local cache of the most recent distributions in a Raku ecosystem.

Its use is mainly intended to serve as an area in which searches can be performed, such as with [`App::Rak`](https://raku.land/zef:lizmat/App::Rak).

# SCRIPTS

```
$ update-ecosystem-cache

```

The `update-ecosystem-cache` script will update the `REA` cache and output any statistics when appropriate.

# MAIN METHODS

## new

```
use Ecosystem::Cache;

my $ec = Ecosystem::Cache.new(:update);  # defaults to REA

```

The `new` method instantiates the `Ecosystem::Cache` object, and optionally refreshes the information about the ecosystem (instead of using the information already cached by `zef`). It takes the following named arguments:

### :ecosystem

Optional. The [`Ecosystem`](https://raku.land/zef:lizmat/Ecosystem) object for which to set up / update a cache. Defaults to whatever ecosystem in instantiated with `Ecosystem.new` (which is currently the `"rea"` ecosystem).

After instantion, the `Ecosystem` object used can be obtained by the `ecosystem` method.

### :cache

Optional. An `IO::Path` indicating the directory where distribution files should be stored. From there, a directory will be added with the ecosystem name.

Defaults to what is either specified by:

* the `RAKU_ECOSYSTEM_CACHE` environment variable
* the subdirectory `.ecosystem/cache` in `$*HOME`
* the subdirectory `.ecosystem/cache` in `$*TMPDIR`

In the most common case, this will default to `~/.ecosystem/cache`.

After instantion, the `IO::Path` used can be obtained by the `cache` method.

### :update

Optional. If specified with a true value, will call the `.update` method on the underlying `Ecosystem` object, causing the meta list of the ecosystem to be fetched from the Internet (rather than using the meta list cached by `zef`).

## update

```
$ec.update(my @new, my @gone, my %erred);
say "Added @new.elems(), removed @gone.elems(), failed %erred.elems()";

```

The `update` method updates the cache with the latest distributions of that ecosystem. If this is the first call to this method for a given cache, it may take quite some time before it is done (at the moment of this writing more than 2200 distributions, totalling to 1.1 GB will be downloaded and handled then). Any calls later will only update new distributions and remove any distributions that are no longer the latest.

The `update` method takes 3 optional positional arguments:

* an array for storing the identities that were added
* an array for storing the identities that were removed
* a hash for storing the identities that had a failure message, keyed to the identity

# HELPER METHODS

## name

```
say $ec.name;

```

Returns the name of the ecosystem to which this cache applies.

## archive-URL

```
say $ec.archive-URL($identity);

```

Returns the URL for downloading the distribution of the given identity.

## cache

```
say $ec.cache;             # root dir of cache info

say $ec.cache($identity);  # dir of given identity

```

Returns the `IO::Path` object for the directory of the given identity in the cache, or the `IO::Path` object for the root directory of the cache if no identity was given.

## provides

```
say $ec.provides;             # IO of paths to files that are provided

.say for $ec.provides.lines;  # list all provided files

```

Returns an `IO::Path` object for the file that contains all of the absolute paths of the files that occurred in the `"provides"` section of the META information of all the distributions.

## tests

```
say $ec.tests;             # IO of paths to test-files

.say for $ec.tests.lines;  # list all provided test-files

```

Returns an `IO::Path` object for the file that contains all of the absolute paths of the test-files (as defined by either having the `".t"` or `".rakutest` extension, inside of a `"t"` or `"xt"` directory).

## scripts

```
say $ec.scripts;             # IO of paths to scripts

.say for $ec.scripts.lines;  # list all provided scripts

```

Returns an `IO::Path` object for the file that contains all of the absolute paths of the scripts (files inside a `"bin"` directory).

## code

```
say $ec.code;             # IO of paths to files with Raku code

.say for $ec.code.lines;  # list all provided files with Raku code

```

Returns an `IO::Path` object for the file that contains all of the absolute paths of the files that contain Raku code (the summation of the files in `provides`, `tests` and `scripts`).

## doc

```
say $ec.doc;             # IO of paths to files with documentation

.say for $ec.doc.lines;  # list all provided files with documentation

```

Returns an `IO::Path` object for the file that contains all of the absolute paths of the files that contain documentation.

## update-identity

```
say $ec.update-identity($identity);

```

Updates the given identity in the cache. Returns either:

* `True` if identity was not yet in the cache, and successfully fetched
* `Nil` if identity was already in the cache
* `Str` error message if fetching identity failed

# AUTHOR

Elizabeth Mattijsen [liz@raku.rocks](mailto:liz@raku.rocks)

Source can be located at: <https://github.com/lizmat/Ecosystem-Cache> . Comments and Pull Requests are welcome.

If you like this module, or what I'm doing more generally, committing to a [small sponsorship](https://github.com/sponsors/lizmat/) would mean a great deal to me!

# COPYRIGHT AND LICENSE

Copyright 2025 Elizabeth Mattijsen

This library is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## dist_github-retupmoca-Auth-PAM-Simple.md
## module Auth::PAM::Simple

A simple way to authenticate against your local unix PAM service.

Note that the only service this has been tested against is the 'login' service. Patches and fixes are welcome.

## Example Usage

```
my Bool $login-valid = authenticate('login', 'retupmoca', 'xxxxxx');

```

### sub authenticate

```
sub authenticate(
    $service,
    Str $user,
    Str $pass
) returns Bool

```

Calls the PAM service $service, and attempts to authenticate using the given $user and $pass. Returns True for success and False for failure.

To build this module, you will need both libpam.so, and it's header files.

You can accomplish this on Debian-based systems with the following command:

```
sudo apt install libpam-dev

```


## dist_zef-japhb-MUGS.md
[![Actions Status](https://github.com/Raku-MUGS/MUGS/workflows/test/badge.svg)](https://github.com/Raku-MUGS/MUGS/actions)

# NAME

MUGS (Multi-User Gaming Services) - A Raku-based platform for game service development

# SYNOPSIS

```
### INITIAL SETUP

# Install MUGS (expect precompilation to take a while)
zef install --exclude="pq:ver<5>:from<native>" MUGS

# Create a long-lived (on disk) data set and identity universe
mugs-admin create-universe [<universe-name>]  # Defaults to "default"

### LOCAL CLIENTS

# Play games using a local UI, using an internal stub server and ephemeral data
mugs-cli  # Turn-based CLI

# Play games using an internal stub server accessing the long-lived data set
mugs-cli --universe=<universe-name>

# Log in and play games on a WebSocket server using a local UI
mugs-cli --server=<host>:<port>

### GAME SERVERS

# Start a TLS WebSocket game server on localhost:10000 using fake certs
mugs-ws-server

# Specify a different MUGS identity universe (defaults to "default")
mugs-ws-server --universe=other-universe

# Start a TLS WebSocket game server on different host:port
mugs-ws-server --host=<hostname> --port=<portnumber>

# Start a TLS WebSocket game server using custom certs
mugs-ws-server --private-key-file=<path> --certificate-file=<path>

# Write a Log::Timeline JSON log for the WebSocket server
LOG_TIMELINE_JSON_LINES=log/mugs-ws-server mugs-ws-server

### WEB UI GATEWAYS

# Start a web UI gateway on localhost:20000 to play games in a web browser
mugs-web-simple --server-host=<websocket-host> --server-port=<websocket-port>
mugs-web-simple --server=<websocket-host>:<websocket-port>

# Start a web UI gateway on a different host:port
mugs-web-simple --host=<hostname> --port=<portnumber>

# Use a different CA to authenticate the WebSocket server's certificates
mugs-web-simple --server-ca-file=<path>

# Use custom certs for the web UI gateway itself
mugs-web-simple --private-key-file=<path> --certificate-file=<path>

# Turn off TLS to the web browser (serving only unencrypted HTTP)
mugs-web-simple --/secure

```

# DESCRIPTION

MUGS is a set of basic services written in the Raku language for creating client-server and multi-user games. It abstracts away the boilerplate of managing player identities, tracking active games and sessions, sending and receiving messages and actions, and so forth.

This Proof-of-Concept release includes a simple local CLI UI, a WebSocket-based game server, a Web UI gateway, and simple admin and developer tools. It can store data using either an internal ephemeral/test storage driver, or in SQLite databases on disk using a storage driver based on the Red ORM.

This release also includes a small selection of very simple games to exercise the basic infrastructure and services.

# ROADMAP

MUGS is still in its infancy, at the beginning of a long and hopefully very enjoyable journey. There is a [draft roadmap for the first few major releases](docs/todo/release-roadmap.md) but I don't plan to do it all myself -- I'm looking for contributions of all sorts to help make it a reality.

# CONTRIBUTING

Please do! :-)

In all seriousness, check out the [CONTRIBUTING doc](docs/CONTRIBUTING.md) (identical in each repo) for details on how to contribute, as well as the [Coding Standards doc](docs/design/coding-standards.md) for guidelines/standards/rules that apply to code contributions in particular.

The MUGS project has a matching GitHub org, [Raku-MUGS](https://github.com/Raku-MUGS), where you will find all related repositories and issue trackers, as well as formal meta-discussion.

More informal discussion can be found on IRC in Libera.Chat #mugs.

# AUTHOR

Geoffrey Broadwell [gjb@sonic.net](mailto:gjb@sonic.net) (japhb on GitHub and Libera.Chat)

# COPYRIGHT AND LICENSE

Copyright 2021-2024 Geoffrey Broadwell

MUGS is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## dist_github-Raku-Noise-Gang-Audio-MIDI-Note.md
# NAME

Audio::MIDI::Note - playable MIDI note

# DESCRIPTION

This module lets you play notes on a MIDI hardware or software device using
methods that allow to replicate sheet music.

# TABLE OF CONTENTS

* [NAME](#name)
* [DESCRIPTION](#description)
* [NON Perl 6 REQUIREMENTS](#non-perl-6-requirements)
* [SYNOPSIS](#synopsis)
  * [*Canon in D* by Johann Pachelbel](#canon-in-d-by-johann-pachelbel)
  * [*Gorgoroth - A World to Win* Solo](#gorgoroth---a-world-to-win-solo)
* [PLAYING TIPS](#playing-tips)
* [ATTRIBUTES](#attributes)
  * [`:stream`](#stream)
  * [`:tempo`](#tempo)
  * [`:value`](#value)
  * [`:velocity`](#velocity)
  * [`:instrument`](#instrument)
  * [`:channel`](#channel)
* [METHODS](#methods)
  * [`.new`](#new)
  * [`.aplay`](#aplay)
  * [`.play`](#play)
    * [First positional](#first-positional)
    * [Second positional](#second-positional)
    * [`:velocity`](#velocity-1)
    * [`:instrument`](#instrument-1)
    * [`:on-on`, `:on`, `:off`](#on-on-on-off)
  * [`.rest`](#rest)
  * [`.riff`](#riff)
* [REPOSITORY](#repository)
* [BUGS](#bugs)
* [AUTHOR](#author)
* [LICENSE](#license)

# NON Perl 6 REQUIREMENTS

This module uses [Audio::PortMIDI](http://modules.perl6.org/repo/Audio::PortMIDI)
under the hood, which requires [portmidi C library](http://portmedia.sourceforge.net/portmidi/).
On Debian and derivatives, you can install it with `sudo apt-get install libportmidi0`

# SYNOPSIS

## *Canon* by Johann Pachelbel (in C key)

Replication of [this sheet music](http://www.8notes.com/scores/420.asp).
Note: on my system, the midi player on that page kills timidity and I have
to do `sudo service timidity restart` to get my scripts to work again...

```
    use Audio::PortMIDI;
    use Audio::MIDI::Note;

    my $stream = Audio::PortMIDI.new.open-output: 3, 32;
    END { $stream.close }

    my Audio::MIDI::Note $note .= new: :20tempo :$stream, :value(½), :49velocity;

    # Pachelbel `Canon` (in C key)
    # Comments reference this sheet music: http://www.8notes.com/scores/420.asp
    $note   .play(<C4 E4>).play(<G3 D4>)  # first line of bars, with one repeat
            .play(<A3 C4>).play(<E3 B3>)
            .play(<F3 A3>).play(<C3 G3>)
            .play(<F3 A3>).play(<G3 B3>)
    for ^2;

    $note   .play(<C4 G4 E5>).play(<G3 B4 D5>) # second line of bars
            .play(<A3 C5   >).play(<E3 G4 B4>)
            .play(<F3 C4 A4>).play(<C3 E4 G4>)
            .play(<F3 F4 A4>).play(<G3 D4 B4>)

            # first two notes of the chord are half-notes and third one is a crotchet,
            # so we play the half-notes in async with .aplay, and then do
            # the crotchet series with blocking .play
            .velocity(64).value(¼) # play louder and switch to quarter note default
            .aplay(<C4 E4>, ½).play('C5').play('C5')
            .aplay(<G3 D4>, ½).play('D5').play('B4')

            # 10th bar
            .aplay(<A3 C4>, ½).play('C5').play('E5')
            .aplay('E3',    ½).play('G5').play('G4')

            # 11th and 12th bars
            .aplay(<F3 A3>, ½).play('A4').play('F4')
            .aplay('C3'   , ½).play('E4').play('G4')
            .aplay(<F3 A3>, ½).play('F4').play('C5')
            .aplay(<G3 B3>, ½).play('B5').play('G4')

            # 13th bar; after the first chord, we're asked to play louder (velocity)
            .aplay(<C4 E4>, ½).play('C5')
            .velocity(80)
            .play('E5', ⅛).play('G5', ⅛).play('G5', ⅛)
            .play('A5', ⅛).play('G5', ⅛).play('F5', ⅛)

            .aplay(<A3 C4>, ½).play('E5', ¼+⅛).play('E5', ⅛)
            .aplay(<E3 G3>, ½).play('E5',   ⅛).play('F5', ⅛).play('E5', ⅛).play('D5', ⅛)

            # 15th, 16th bar
            .aplay(<F3 A3>, ½).play('C5', ⅛).play('Bb4', ⅛).play('A4', ⅛).play('Bb4', ⅛)
            .aplay(<C3 E3>, ½).play('G4').play('E4')
            .aplay(<F3 A3>, ½).play('C4').play('F4', ⅛).play('E4', ⅛)
            .aplay(<G3 B3>, ½).play('D4').play('G4', ⅛).play('F4', ⅛)

            # 17th bar: we'll sound half-notes in async, and will use .rest
            # to play the quarter-note rest on the treble clef.
            # .rest can take a rest value as argument, but our current value is
            # already a crotchet, so no argument is needed:
            .aplay(<C4 E3>, ½).rest.velocity(64).play('C5')
            .aplay('G3', ½).play('D5').play('B4')

            # Last row of bars
            .aplay(<A3 C4>, ½).play('C5').play('E4')
            .aplay(<E3 B3>, ½).play('G4', ¼+⅛).play('A4', ⅛)
            .aplay(<F3 A3>, ½).play('F4').play('C4')
            .aplay(<C3 G3>, ½).play('E4').play('G4')
            .aplay(<F3 A3>, ½).play('F4').play('E4')
            .aplay(<G3 B3>, ½).play('D4').play('G4')
            .play(<C3 C4 E3>, 1)
    ;

```

## *Gorgoroth - A World to Win* Solo

Part of the solo from [A World to Win](https://www.youtube.com/watch?v=7EvOTkEMlug),
showing swap of instruments, re-use of repeating pieces of music, calculation
of triplet note values, and use of on- and off-beat velocity shortcuts.

```
    use Audio::MIDI::Note;

    my $stream = Audio::PortMIDI.new.open-output: 3, 32;
    END { $stream.close }

    my Audio::MIDI::Note $note .= new: :31tempo :30instrument :$stream :value(⅔ * ⅛);

    # Looping `Gorgoroth - A World to Win` solo with organ chord in the background.
    # We use triplet notes and save repeating pieces into variables for reuse
    my &rhythm = *.play('D#5').play('D5').play('C5');
    my &riff = {
        .aplay(<C4 E4 G4>, 4, :19instrument, :40velocity)

        .play('C5',  ⅔*(¼+⅛) )
        .riff(&rhythm).play('C5',  ⅔*(¼+⅛) )
        .riff(&rhythm).play('G#4', ⅔*(¼+⅛) )
        .riff(&rhythm).play('A#4', ⅔*(¼+⅛) )
        .riff(&rhythm).play('C5',  ⅔*(¼+⅛) )
        .riff(&rhythm).play('C5',  ⅔*(¼+⅛) )
        .riff(&rhythm);
    };

    $note   .riff(&riff)
                .play('G5',  ¼, :on).play('F5',  ¼, :off)
                .play('D#5', ¼     ).play('D5',  ¼, :off)
            .riff(&riff)
                .play('F5',  ¼,:on ).play('D#5', ¼, :off)
                .play('D5',  ¼     ).play('A#4', ¼, :off)
    for ^10;

```

# PLAYING TIPS

* Save repeating chunks into subs and play them with `.riff` method
* Play the piece using the shortest notes and rests it requires, using
  `.play`/`.rest` methods. Use the asynchronous `.aplay` method to play
  longer notes that overlap these shorter ones.

# ATTRIBUTES

Note: to facilitate chaining, all attributes can be either assigned to directly
or be given the new value as an argument:

```
    $note.value = ½;
    $note.value(½); # same as above; returns invocant

```

#### `:stream`

The `Audio::PortMIDI::Stream` object opened at a MIDI output device. See
[Audio::PortMIDI](http://modules.perl6.org/dist/Audio::PortMIDI) for details.

#### `:tempo`

Positive `Int`.
Specifies the tempo of the piece in beats per minute per **WHOLE** note.
*Defaults to:* `40`

#### `:value`

`Numeric`. Specifies the default value (amount of time it rings) of the played
notes. *Defaults to:* `¼`

#### `:velocity`

`0 <= Int <= 127`. Specifies the default velocity (similar to volume) of the
played notes; `127` indicates as loud as possible.
*Defaults to:* `80` (`mf` loudness in sheet music).

#### `:instrument`

`Int`. [MIDI Patch code](https://www.midi.org/specifications/item/gm-level-1-sound-set)
for the default instrument to use. *Defaults to:* `0` (piano)

#### `:channel`

`Int`. Specifies the MIDI channel to use. *Defaults to:* `0`

# METHODS

## `.new`

```
my Audio::MIDI::Note $note .= new:
    :stream(Audio::PortMIDI.new.open-output: 3, 32)
    :20tempo
    :value(½)
    :49velocity
    :30instrument
    :0channel;

```

Creates and returns a new `Audio::MIDI::Note` object. See [ATTRIBUTES](#ATTRIBUTES)
section for details on the accepted parameters.

## `.aplay`

```
    $note.aplay('C5')
         .aplay(<C4 E4 G4>, ⅛, :on-on, :100velocity, :30instrument);

```

Same as `.play`, but is asynchronous **and returns immediately**.
Useful to play longer notes that overlap shorter ones (that you would play
with `.play`). Takes the same arguments as `.play`

## `.play`

```
    $note.play('C5')
         .play(<C4 E4 G4>, ⅛, :on-on, :100velocity, :30instrument);

```

Plays one or more notes (simultaneously). Takes the following arguments:

#### First positional

An `Str`or a `List` of strings representing the notes to play. Multiple notes
will be played *at the same time*, not consecutively. Valid notes are from
`C0` through `G#10`/`Ab10`. Use hashmark (`#`) to indicate sharps and lower-case B
(`b`) to indicate flats. This argument is case-sensitive.

#### Second positional

Note value for the currently played notes. *Defaults to:* the value of
`:value` attribute.

#### `:velocity`

Note velocity for the currently played notes. *Defaults to:* the value of
`:velocity` attribute.

#### `:instrument`

MIDI patch code for the instrument for the currently played notes.
*Defaults to:* the value of `:instrument` attribute.

#### `:on-on`, `:on`, `:off`

Velocity control shortcuts for on/off beats. `:on-on` is the loudest,
`:on` is less so, but still louder than normal velocity; `:off` is less loud
than normal velocity.

## `.rest`

```
    $note.rest
         .rest(⅛);

```

"Plays" a rest by blocking execution for the specified note value. Takes
`Numeric` note value, which *defaults to:* the value of `:value` attribute.

## `.riff`

```
    my &riff = *.play('C4').play('E4').play('G4');

    $note.&riff;
    $note.riff(&riff);

```

The last two lines in the code above are equivalent. The only issue is you can't
split a method chain that uses `&riff` onto multiple lines. This is where the
`.riff` method comes into play. It takes your `Callable` as an argument and
lets you break up your method chains on multiple lines.

Storing bits of music into variables and then playing them with `.riff` lets
you re-use repeating bars or fragments in a piece of music.

Also worth noting: method chains started on a `WhateverStar` also cannot be
broken up into multiple lines. Just use a set of curlies instead:

```
    my &riff = {
        .play('C4').play('E4')
        .play('G4').play('C5');
    }

```

---

# REPOSITORY

Fork this module on GitHub:
<https://github.com/zoffixznet/perl6-Audio-MIDI-Note>

# BUGS

To report bugs or request features, please use
<https://github.com/zoffixznet/perl6-Audio-MIDI-Note/issues>

# AUTHOR

Zoffix Znet (<http://zoffix.com/>)

# LICENSE

You can use and distribute this module under the terms of the
The Artistic License 2.0. See the `LICENSE` file included in this
distribution for complete details.


## dist_zef-lizmat-REPL.md
[![Actions Status](https://github.com/lizmat/REPL/actions/workflows/linux.yml/badge.svg)](https://github.com/lizmat/REPL/actions) [![Actions Status](https://github.com/lizmat/REPL/actions/workflows/macos.yml/badge.svg)](https://github.com/lizmat/REPL/actions) [![Actions Status](https://github.com/lizmat/REPL/actions/workflows/windows.yml/badge.svg)](https://github.com/lizmat/REPL/actions)

# NAME

REPL - a more easily configurable REPL

# SYNOPSIS

```
use REPL;

# Start a Read, Evaluate, Print Loop
repl;

```

# DESCRIPTION

The REPL module is a re-imagining of the REPL (Read, Evaluate, Print Loop) functionality as offered by Rakudo before the 2024.11 release. It provides both a programmable interface, as well as a ready made `"repl"` CLI.

# COMMAND LINE INTERFACE

```
# Simplest invocation
$ repl

# Invocation with some custom settings
$ repl --the-prompt='[:index:] :HHMM:' --symbols=🦋,🔥

[0] 20:51 🦋 if 42 {
[0] 20:51 🔥 say "foo"
[0] 20:51 🔥 }
foo
[0] 20:52 🦋

```

The REPL command-line interface can be invoked with named arguments that have the same name as the named arguments to the `REPL.new` call. They are:

* --editor - the editor to use (default: Any)
* --header - whether to show the full header (default: yes)
* --multi-line-ok - can expression span more than one line (default: yes)
* --output-method - the output method to be used (default: gist)
* --symbols - symbols for prompt state (default: ">,\*")
* --the-prompt - string for prompt (default: "[:index:] :symbol: ")

Any other command-line arguments will be ignored.

# SUBROUTINES

## repl

```
repl;

```

The `repl` subroutine creates a new `REPL` object for that context and returns that. When called in sink context, it will activate the interactive Read, Evaluate, Print Loop. This is the most common usage when debugging your code.

```
#line 666 foo.raku
if 42 -> $answer {
    repl "Looking for clues", :$answer;
}

```

```
Looking for clues
answer: 42
[0] >

```

Note that when the `repl` subroutine is used in a debugging mode, it will not show any header, other than the one that is specified with the positional argument (in this case "Looking for clues").

If no explicit heafer is specified, it will show the location of the [`callframe`](https://docs.raku.org/routine/callframe) that the code is currently in (in this case that would have been: line 666 in the file "foo.raku").

Finally it will show the value of any named arguments to help you debug your code (in this case "answer: 32").

It is also possible to save the `REPL` object at one place in the code, and actually run the REPL at a later time in another scope.

If you just press ENTER when using the REPL as a debugging aid in this manner, then it will be interpreted the same as "=quit" for convenience (especially if the `repl` sub is called in a loop).

```
my $repl = do {
    my $a = 42;
    repl
}

# ...

# activate REPL later, allowing access to $a even though that
# variable is no longer in scope
$repl.run;

```

## standard-completions

The `standard-completions` subroutine provides the standard completion logic if no `:additional-completions` argument has been specified with either `REPL.new` or the `repl` subroutine.

It is provided to allow it to be added with the <:additional-completions> argument, and to allow testing of the standard completion logic.

## uniname-words

The `uniname-words` subroutine provides the same functionality as the `uniname-words` subroutine provided by the [`uniname-words`](https://raku.land/zef:lizmat/uniname-words) distribution **if** that distribution is installed.

Otherwise it will always return `Nil`.

## RUNNING A REPL

The `REPL` role is what usually gets punned into a class.

```
my $repl = REPL.new;

$repl.run;

```

Same as above, but with all named arguments spelled out:

```
my $repl = REPL.new:
  :editor(Any),    # or "Readline", "LineEditor", "Linenoise"
  :output-method<gist>,  # or "Str", "raku"
  :out = $*OUT,
  :err = $*ERR,
  :val = $*OUT,
  :header,
  :multi-line-ok,
  :the-prompt("[:index:] :symbol: "),
  :symbols(">", "*"),
  :is-win($*DISTRO.is-win),
  :@completions,
  :@additional-completions,
  :compiler<Raku>,
;

```

The `REPL` role embodies the information needed to run a Read, Evaluate, Print Loop. It allows for these named arguments:

### :editor

Optional. String indicating which editor logic to be used.

If the `INSIDE_EMACS` environment variable is set with a true value, then the `Fallback` editor will be used.

If it can be determined from the environment that the process is running inside the "rlwrap" wrapper, then the `Fallback` editor will be used.

If the `RAKUDO_LINE_EDITOR` environment variable is set, then its contents will be assumed as an indication of preference and will first be tried. If that fails, an error message will be shown.

Whatever is then the value, that value will be used to create a [`Prompt`](https://raku.land/zef:lizmat/Prompt) object.

### :output-method

String. The name of the method to be called to display the value of an expression. This defaults to the value of the `RAKU_REPL_OUTPUT_METHOD` environment variable, or to "gist" if that has not been specified.

Used value available with the `.output-method` method.

### :header

Boolean. Indicate whether to show the REPL header upon entry. Defaults to `True`.

Used value available with the `.header` method.

### :out

Optional. The `:out` named argument specifies the value of `$*OUT` whenever a command is executed. If not specified, or specified with an undefined value, will assume the value of `$*OUT` at command execution time.

### :err

Optional. The `:err` named argument specifies the value of `$*ERR` whenever a command is executed. If not specified, or specified with an undefined value, will assume the value of `$*ERR` at command execution time.

### :multi-line-ok

Optional, Boolean. Indicate whether it is ok to interprete multiple lines of input as a single statement to evaluate. Defaults to `True` unless the `RAKUDO_DISABLE_MULTILINE` environment variable has been specified with a true value.

Used value available with the `.multi-line-ok` method.

### :the-prompt

Optional. Specifies what will be shown to the user before the user can enter characters. Defaults to what has been specified with the `RAKUDO_REPL_PROMPT` environment variable, or `"[:index:] :symbol: "`.

Supports all of the expansions offered by the [`Prompt::Expand`](https://raku.land/zef:lizmat/Prompt::Expand) distribution.

Note that if there is a prompt (implicitely) specified, the string ":symbol: " will be added if there is no ":symbol:" specified, to make sure the user actually sees a prompting symbol, and to make specifying a user prompt a bit easier.

The expanded prompt is also available with the `.the-prompt` method.

### :symbols

Optional. Specifies the symbols that should be used for the `":symbol:"` placeholder in the different REPL states. Defaults to what has been specified as a comma-separated list with the `RAKUDO_REPL_SYMBOLS` environment variable. Defaults to `">", "*"` if that is not specified.

Currently the following states are recognized:

* 0 - accepting expression to be evaluated
* 1 - previous expression not complete, accepting continuation

### :is-win

Boolean. Indicate whether certain OS dependent checks should assume Windows semantics. Defaults to `$*DISTRO.is-win`.

Used value available with the `.is-win` method.

### :completions

A `List` of strings to be used tab-completions. If none are specified, then a default Raku set of completions will be used.

Used value available with the `.completions` method.

### :additional-completions

```
# completion that uppercases whole line if ended with a !
sub shout($line, $pos) {
    ($line.chop.uc,) if $pos == $line.chars && $line.ends-with("!")
}

my $repl = REPL.new(:additional-completions(&shout));

```

A `List` of `Callables` to be called to produce tab-completions. If none are specified, the `standard-completions` will be assumed.

Each `Callable` is expected to accept two positional arguments: the line that has been entered so far, and the position of the cursor. It is expected to return a (potentially) empty `List` with the new state of the line (so including everything before and after the completion).

### :prompt

The [`Prompt`](https://raku.land/zef:lizmat/Prompt) object to be used. If specified, overrides anything related to the <C:editor> named argument. If not specified, will use whatever was (implicitely) specified with `:editor`.

### :compiler

String. The HLL compiler to be used. This defaults to "Raku", which is the only compiler supported at this time.

Used value available with the `.compiler` method.

## method run

Actually run the REPL.

# OTHER METHODS

## err

The object to be used for error output. Defaults to `$*ERR`.

## history

Expected to take no arguments, and return an object that represents the (possibly persistent) history of the REPL's interactive sessions.

By default it will first look for a `RAKUDO_HIST` environment variable and return an `IO::Path` object for that. If that environment variable is not specified, will check the `$*HOME` and `$*TMPDIR` dynamic variables for the existence of a `.raku` subdirectory in that. If found, will return an `IO::Path` for the "rakudo-history" file in that subdirectory and try to create that if it didn't exist yet (and produce an error message if that failed).

## out

The object to be used for standard output. Defaults to `$*OUT`.

## prompt

The [`Prompt`](https://raku.land/zef:lizmat/Prompt) object to be used when obtaining input from the user. Also handles the `read`, `readline`, `load-history`, `add-history`, `save-history` and `editor-name` methods.

## supports-completions

Returns a `Bool` indicating whether the selected editor supports completions.

## teardown

Expected to take no arguments. Will be called whenever the user indicates that they want to exit the REPL. Will call the `save-history` method by default.

## val

The object to be used for outputting values that weren't shown already. Defaults to `$*OUT`.

# USER COMMANDS

The following REPL commands are currently supported: if a command is not recognized, then `Raku` code will be assumed and executed if possible. Note that all REPL commands start with "`=`" to prevent confusion with possibly legal Raku code.

## completions

Shows an introduction to completions. Can be shortened to "=com".

## context

Allows creation of and switching between two or more contexts: "new" creates a new context and switches to it, "switch" switches to an already existing context, and "list" shows the available contexts. Can be shortened to "=con".

## edit

Edit the file given, or the last file that was saved with =write. Can be shortened to "=ed".

## exit

Leaves the REPL. Can be shortened all the way to "=ex".

## help

Shows a list of available commands. Can be shortened all the way to "=h".

## info

Shows the name of the editor logic being used. Can be shortened to to "=inf".

## introduction

Shows a general introduction. Can be shortened to "=int".

## output [method]

Shows the current output method. If a second argument is specified, it indicates the name of the output method to be used from now on. Typical values are "raku", "Str", "gist". Can be shortened all the way to "=o".

## quit

Leaves the REPL. Can be shortened all the way to "=q", and is thus the shortest way to leave the REPL with a REPL command.

## read [path]

Read the code from the file with the indicated path and compiles and executes it. Remembers the path name so that subsequent =write commands need not have it specified.

## reset

Reset the status of the REPL as if it was freshly entered.

## stack

Show the caller stack from where the REPL has been called. Only makes sense if the REPL is being called from within a program, rather than from the command line. Can be shortened to "=s".

## write [path]

Write all lines entered that did **not** produce any output to the indicated path. Remembers the path name from =read and =write so that subsequent =write commands need not have it specified.

# TAB COMPLETIONS

If the `supports-completions` method returns `True`, the standard tab-completion logic will provide:

* all relevant items from the CORE:: namespace
* any relevant items from the direct context (such as a REPL command)
* \123 wil change integer value to superscript: ¹²³, subscript: ₁₂₃
* foo! will tab-complete to FOO, foo, Foo

Additionally, if the [`uniname-words`](https://raku.land/zef:lizmat/uniname-words) module is installed:

* any unclosed [\*\*\c[\*\*](https://docs.raku.org/syntax/%5Cc) sequence will tab-complete on the names of Unicode code-points
* any **\word** will tab-complete to the actual codepoints

# ENVIRONMENT VARIABLES

These environment variables will override default settings.

## RAKUDO\_REPL\_PROMPT

The prompt shown to the user. May contain escape sequences as supported by the [`Prompt.expand`](https://raku.land/zef:lizmat/Prompt#method-expand) method.

## RAKUDO\_REPL\_SYMBOLS

A comma separated list of symbols representing the states of the REPL. Defaults to `>,*>`.

## RAKUDO\_HIST

Path where the history file is / should be stored.

## RAKU\_REPL\_OUTPUT\_METHOD

The name of the method with which to show results to the user.

## RAKUDO\_DISABLE\_MULTILINE

Whether multi-line evaluations should be disabled or not.

# AUTHOR

Elizabeth Mattijsen [liz@raku.rocks](mailto:liz@raku.rocks)

Source can be located at: <https://github.com/lizmat/REPL> . Comments and Pull Requests are welcome.

If you like this module, or what I'm doing more generally, committing to a [small sponsorship](https://github.com/sponsors/lizmat/) would mean a great deal to me!

# COPYRIGHT AND LICENSE

Copyright 2024, 2025 Elizabeth Mattijsen

This library is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## dist_cpan-ROBERTLE-Config-Parser-json.md
# Config::Parser::json

A JSON parser for [Config](https://github.com/scriptkitties/p6-Config).

## License

Config::Parser::json is licensed under the [Artistic License 2.0](https://opensource.org/licenses/Artistic-2.0).

## Feedback and Contact

Please let me know what you think: Robert Lemmen [robertle@semistable.com](mailto:robertle@semistable.com)


## dist_zef-titsuki-Algorithm-KdTree.md
[![Actions Status](https://github.com/titsuki/raku-Algorithm-KdTree/actions/workflows/test.yml/badge.svg)](https://github.com/titsuki/raku-Algorithm-KdTree/actions)

# NAME

Algorithm::KdTree - a Raku binding for C implementation of the Kd-Tree Algorithm (<https://github.com/jtsiomb/kdtree>)

# SYNOPSIS

```
use Algorithm::KdTree;

my $kdtree = Algorithm::KdTree.new(3);

$kdtree.insert: [0e0,0e0,0e0];
$kdtree.insert: [10e0,10e0,10e0];

my $nearest-response = $kdtree.nearest: [1e0,1e0,1e0];
unless $nearest-response.is-end {
   $nearest-response.get-position.say; # [0e0, 0e0, 0e0]
}

my $range-response = $kdtree.nearest-range([9e0,9e0,9e0], sqrt(5));
my @array;
until $range-response.is-end {
   @array.push: $range-response.get-position;
   $range-response.next();
}
@array.perl.say; # [[10e0, 10e0, 10e0], ]

```

# DESCRIPTION

Algorithm::KdTree is a Raku binding for C implementation of the Kd-Tree Algorithm (<https://github.com/jtsiomb/kdtree)>. Kd-Tree is the efficient algorithm for searching nearest neighbors in the k-dimensional space.

## CONSTRUCTOR

### new(Int $dimension)

```
my $kdtree = Algorithm::KdTree.new(3);
my $kdtree = Algorithm::KdTree.new(256); # it could handle a huge dimensional space

```

Sets dimension `$dimension` for constructing `$dimension`-dimensional Kd-Tree.

## METHODS

### insert(@array)

```
$kdtree.insert([1e0, 2e0, 3e0]);

```

Inserts a k-dimensional array.

### nearest(@array)

```
my $response = $kdtree.nearest([1e0, 2e0, 3e0]);
if (not $response.is-end()) {
      my $position = $response.get-position();

# YOUR CODE IS HERE
# ...

}

```

Returns a response which includes the nearest neighbor position of the query `@array` in the Kd-Tree. If the Kd-Tree has no elements, it returns a response which does not include any positions.

### nearest-range(@array, Num $radius)

```
my $response = $kdtree.nearest-range([1e0, 2e0, 3e0], 10e0);
while (not $response.is-end()) {
      my $position = $response.get-position();

# YOUR CODE IS HERE
# ...

$response.next();

}

```

Returns a response which includes positions in the hypersphere. The center of this hypersphere is `@array` and the radius of this is `$radius`. If the Kd-Tree has no elements or no elements are found in the hypersphere, it returns a response which does not include any positions.

# AUTHOR

titsuki [titsuki@cpan.org](mailto:titsuki@cpan.org)

# COPYRIGHT AND LICENSE

Copyright 2016 titsuki

Copyright 2007-2011 John Tsiombikas [nuclear@member.fsf.org](mailto:nuclear@member.fsf.org)

This library is free software; you can redistribute it and/or modify it under the terms of the BSD 3-Clause License.

# SEE ALSO

* kdtree <https://github.com/jtsiomb/kdtree>


## dist_github-FCO-SupplyTimeWindow.md
[![Build Status](https://travis-ci.org/FCO/SupplyTimeWindow.svg?branch=master)](https://travis-ci.org/FCO/SupplyTimeWindow)

# SupplyTimeWindow

```
use SupplyTimeWindow;

my $s = Supplier.new;
my $t = $s.Supply.time-window: 1;

start react whenever $t { .say }

for ^10 -> $i { $s.emit: $i; sleep .5.rand }

```

SupplyTimeWindow creates `time-window()` new method on `Supply`ies that receives the size of the time window in seconds.
Every time the original `Supply` emits, it will emit an `Array` with each value emitted less than `time window`'s size seconds.

```
multi method time-window($seconds --> Supply) {...}

```

It also accepts a optional named parameter `transform`, it's a `Callable` that will be used to transform the time window array.

```
multi method time-window($seconds, :&transform! --> Supply) {...}

```


## dist_cpan-HANENKAMP-IO-Glob.md
# NAME

IO::Glob - Glob matching for paths, strings and file listings.

# SYNOPSIS

```
use IO::Glob;

# Need a list of files somewhere?
for glob("src/core/*.pm") -> $file { say ~$file }

# Or apply the glob to a chosen directory
with glob("*.log") {
    for .dir("/var/log/error") -> $err-log { ... }
    for .dir("/var/log/access") -> $acc-log { ... }
}

# Use a glob to match a string or path
if "some-string" ~~ glob("some-*") { say "match string!" }
if "some/path.txt".IO ~~ glob("some/*.txt") { say "match path!" }

# Use a glob as a test in built-in IO::Path.dir()
for "/var/log".IO.dir(test => glob("*.err")) -> $err-log { ... }

# Globs are objects, which you can save, reuse, and pass around
my $file-match = glob("*.txt");
my @files := dir("$*HOME/docs", :test($file-match));

# Want to use SQL globbing with % and _ instead?
for glob("src/core/%.pm", :sql) -> $file { ... }

# Or want globbing without all the fancy bits?
# :simple turns off everything but * and ?
for glob("src/core/*.pm", :simple) -> $file { ... }

```

# DESCRIPTION

Traditionally, globs provide a handy shorthand for describing the files you're interested in based upon their path. This class provides that shorthand using a BSD-style glob grammar that is familiar to Perl devs. However, it is more powerful than its Perl 5 predecessor.

* Globs are built as `IO::Glob` objects which encapsulate the pattern. You may create them and pass them around.
* By using them as an iterator, you can put globs to their traditional use: listing all the files in a directory.
* Globs can also be smart-matched. It will match against strings or anything that stringifies; it will work against IO::Paths too.
* Globbing can be done with different grammars. This class ships with three: simple, BSD, and SQL.
* **Experimental.** You can use custom grammars for your smart match.

# SUBROUTINES

## sub glob

```
sub glob(
    Str:D $pattern,
    Bool :$sql,
    Bool :$bsd,
    Bool :$simple,
    :$grammar,
    :$spec = $*SPEC
) returns IO::Glob:D

sub glob(
    Whatever $,
    Bool :$sql,
    Bool :$bsd,
    Bool :$simple,
    :$grammar,
    :$spec = $*SPEC
) returns IO::Glob:D

```

When given a string, that string will be stored in the [method pattern/pattern](#method pattern/pattern) attribute and will be parsed according to the [method grammar/grammar](#method grammar/grammar).

When given <Whatever> (`*`) as the argument, it's the same as:

```
glob('*');

```

which will match anything. (Note that what whatever matches may be grammar specific, so `glob(*, :sql)` is the same as `glob('%')`.)

If you want to pick from one of the built-in grammars, you may use these options:

* `:bsd` is the default specifying this is explicit, but unnecessary. This grammar supports `*`, `?`, `[abc]`, `[!abc]`, `~`, and `{ab,cd,efg}`.
* `:sql` uses a SQL-ish grammar that provides `%` and `_` matching.
* `:simple` is a simplified version of `:bsd`, but only supports `*` and `?`.

The `:$spec` option allows you to specify the IO::Spec to use when matching paths. It uses `$*SPEC`, by default. The IO::Spec is used to split paths by directory separator when matching paths. (This is ignored when matching against other kinds of objects.)

An alternative to this is to use the optional `:$grammar` setting lets you select a globbing grammar object to use. These are provided:

* IO::Glob::BSD
* IO::Glob::SQL
* IO::Glob::Simple

**Experimental.** If you want a different grammar, you may create your own as well, but no documentation of that process has been written yet as of this writing.

# METHODS

## method pattern

```
method pattern() returns Str:D

```

Returns the pattern set during construction.

## method spec

```
method spec() returns IO::Spec:D

```

Returns the spec set during construction.

## method grammar

```
method grammar() returns Any:D

```

Returns the grammar set during construction.

## method dir

```
method dir(Cool $path = '.') returns Seq:D

```

Returns a list of files matching the glob. This will descend directories if the pattern contains a IO::Spec#dir-sep using a depth-first search. This method is called implicitly when you use the object as an iterator. For example, these two lines are identical:

```
for glob('*.*') -> $every-dos-file { ... }
for glob('*.*').dir -> $every-dos-file { ... }

```

This is the preferred method for listing files as it will be sure to respect ordering of files by alternates. For example,

```
for glob("{bc,ab}*") -> $file { say $file }

```

This will print all files starting with "bc" before any files starting with ab.

## method ACCEPTS

```
method ACCEPTS(Mu:U $) returns Bool:D
method ACCEPTS(Str:D(Any) $candiate) returns Bool:D
method ACCEPTS(IO::Path:D $path) returns Bool:D

```

This implements smart-match. Undefined values never match. Strings are matched using the whole pattern, without reference to any directory separators in the string. Paths, however, are matched and carefully respect directory separators. For most circumstances, this will not make any difference. However, a case like this will be treated very differently in each case:

```
my $glob = glob("hello{x,y/}world");
say "String" if "helloy/world" ~~ $glob;      # outputs> String
say "Path"   if "helloy/world".IO ~~ $glob;   # outputs nothing, no match
say "Path 2" if "helloy{x,y/}world" ~~ $glob; # outputs> Path 2

```

The reason is that the second and third are matched in parts as follows:

```
"helloy" ~~ glob("hello{x,y") && "world" ~~ glob("}world")
"hello{x,y" ~~ glob("hello{x,y") && "}world" ~~ glob("}world")

```


## dist_zef-lizmat-P5getpriority.md
[![Actions Status](https://github.com/lizmat/P5getpriority/workflows/test/badge.svg)](https://github.com/lizmat/P5getpriority/actions)

# NAME

Raku port of Perl's getpriority() and associated built-ins

# SYNOPSIS

```
use P5getpriority; # exports getpriority, setpriority, getppid, getpgrp

say "My parent process priority is &getpriority(0, getppid())";

say "My process priority is &getpriority(0, $*PID)";

say "My process group has priority &getpriority(1, getpgrp())";

say "My user priority is &getpriority(2, $*USER)";

```

# DESCRIPTION

This module tries to mimic the behaviour of Perl's `getpriority` and associated built-ins as closely as possible in the Raku Programming Language.

It exports by default:

```
getpgrp getppid getpriority setpgrp setpriority

```

# ORIGINAL PERL 5 DOCUMENTATION

```
getpriority WHICH,WHO
        Returns the current priority for a process, a process group, or a
        user. (See getpriority(2).) Will raise a fatal exception if used
        on a machine that doesn't implement getpriority(2).

setpriority WHICH,WHO,PRIORITY
        Sets the current priority for a process, a process group, or a
        user. (See setpriority(2).) Raises an exception when used on a
        machine that doesn't implement setpriority(2).

getpgrp PID
        Returns the current process group for the specified PID. Use a PID
        of 0 to get the current process group for the current process.
        Will raise an exception if used on a machine that doesn't
        implement getpgrp(2). If PID is omitted, returns the process group
        of the current process. Note that the POSIX version of "getpgrp"
        does not accept a PID argument, so only "PID==0" is truly
        portable.

setpgrp PID,PGRP
        Sets the current process group for the specified PID, 0 for the
        current process. Raises an exception when used on a machine that
        doesn't implement POSIX setpgid(2) or BSD setpgrp(2). If the
        arguments are omitted, it defaults to "0,0". Note that the BSD 4.2
        version of "setpgrp" does not accept any arguments, so only
        "setpgrp(0,0)" is portable. See also "POSIX::setsid()".

getppid Returns the process id of the parent process.

        Note for Linux users: Between v5.8.1 and v5.16.0 Perl would work
        around non-POSIX thread semantics the minority of Linux systems
        (and Debian GNU/kFreeBSD systems) that used LinuxThreads, this
        emulation has since been removed. See the documentation for $$ for
        details.

```

# PORTING CAVEATS

This module depends on the availability of POSIX semantics. This is generally not available on Windows, so this module will probably not work on Windows.

# AUTHOR

Elizabeth Mattijsen [liz@raku.rocks](mailto:liz@raku.rocks)

Source can be located at: <https://github.com/lizmat/P5getpriority> . Comments and Pull Requests are welcome.

# COPYRIGHT AND LICENSE

Copyright 2018, 2019, 2020, 2021 Elizabeth Mattijsen

Re-imagined from Perl as part of the CPAN Butterfly Plan.

This library is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## dist_github-ALANVF-P6TK.md
# P6TK

A library that lets you use Tk in Perl 6

## using this

At the moment, you need the Tcl app "wish" installed and in your PATH for this to work. I'll fix this at some point


## bind-pos.md
BIND-POS

Combined from primary sources listed below.

# [In IterationBuffer](#___top "go to top of document")[§](#(IterationBuffer)_method_BIND-POS "direct link")

See primary documentation
[in context](/type/IterationBuffer#method_BIND-POS)
for **method BIND-POS**.

```raku
multi method BIND-POS(IterationBuffer:D: int   $pos, Mu \value)
multi method BIND-POS(IterationBuffer:D: Int:D $pos, Mu \value)
```

Binds the given value at the given element position and returns it. The `IterationBuffer` is automatically lengthened if the given element position is beyond the length of the `IterationBuffer`. An error indicating the index is out of bounds will be thrown for negative position values.

# [In Subscripts](#___top "go to top of document")[§](#(Subscripts)_method_BIND-POS "direct link")

See primary documentation
[in context](/language/subscripts#method_BIND-POS)
for **method BIND-POS**.

```raku
multi method BIND-POS (::?CLASS:D: $index, \new)
```

Expected to bind the value or container `new` to the slot at position `$index`, replacing any container that would be naturally found there. This is what is called when you write:

```raku
my $x = 10;
@numbers[5] := $x;

```

The generic [`Array`](/type/Array) class supports this in order to allow building complex linked data structures, but for more domain-specific types it may not make sense, so don't feel compelled to implement it. If you don't, users will get an appropriate error message when they try to bind to a positional slot of an object of this type.


## dist_zef-lizmat-Git-Blame-File.md
[![Actions Status](https://github.com/lizmat/Git-Blame-File/actions/workflows/linux.yml/badge.svg)](https://github.com/lizmat/Git-Blame-File/actions) [![Actions Status](https://github.com/lizmat/Git-Blame-File/actions/workflows/macos.yml/badge.svg)](https://github.com/lizmat/Git-Blame-File/actions) [![Actions Status](https://github.com/lizmat/Git-Blame-File/actions/workflows/windows.yml/badge.svg)](https://github.com/lizmat/Git-Blame-File/actions)

# NAME

Git::Blame::File - Who did what and when on a file in a Git repository

# SYNOPSIS

```
use Git::Blame::File;

my $blamer = Git::Blame::File.new("xt/target");
say $blamer.lines[2];  # show line #3
# c64c97c3 (Elizabeth Mattijsen 2022-07-27 20:40:22 +0200 3) And this the third line

.say for Git::Blame::File.new("xt/target", :line-numbers(2,4)).lines
#c64c97c3 (Elizabeth Mattijsen 2022-07-27 20:40:22 +0200 2) This became the second line.
#77877dbc (Elizabeth Mattijsen 2022-07-27 20:39:29 +0200 4) This is the second line.

```

# DESCRIPTION

Git::Blame::File is a module that uses `git blame` to extract information from a single file in a Git repository. It processes the `git blame` information into `Git::Blame::Line` objects, while also keeping track of commits in `Git::Blame::Commit` objects.

Stringifies to the filename specified.

# METHODS ON Git::Blame::File

## new

```
my $blamer = Git::Blame::File.new: "t/target";

```

The `new` method either takes a single positional argument as the filename or the `IO::Path` object of which to obtain `git blame` information.

It can also be called with a `:file` named argument, and an optional `:commits` argument. The latter is intended for a future `Git::Blame::Repository` module that would potentially contain all `git blame` information of a repository.

Finally, it can also be called with an optional `:line-numbers` named argument, which should contain the line numbers (in ascending order) of which to obtain blame information. The `.lines` method will then iterate over the blame information of these line numbers.

## lines

Returns an `Array` with all the lines (as `Git::Blame::Line` objects) in the file. Note that these are 0-based, whereas line numbers are typically 1-based.

```
say $blamer.lines[2];  # show line #3
# c64c97c3 (Elizabeth Mattijsen 2022-07-27 20:40:22 +0200 3) And this the third line

```

## authors

Returns a list of unique `author`s of this file.

## commits

Returns a `Map` of all the commits that were seen for this file (and potentially other files in the future. Keyed to the `sha1` of the commit, and having a `Git::Blame::Commit` object as a value.

## created

Returns a `DateTime` object when this file was created, according to the oldest `author-time` information. Note that if no lines of the first commit exist in the file, this may actually be later.

## modified

Returns a `DateTime` object when this file was last modified, according to the newest `committer-time` information.

## file

The file from which the `git blame` information was obtained.

# ACCESSORS ON Git::Blame::Line

Note that `Git::Blame::Line` objects are created automatically by `Git::Blame::File.new`.

* author - the name of the author of this line
* author-mail - the email address of the author of this line
* author-time - a DateTime object for the authoring of this line
* commit - the associated Git::Blame::Commit object
* committed - whether this line has actually been committed
* committer - the name of the committer of this line
* committer-mail - the email address of the committer of this line
* committer-time - a DateTime object for the committing of this line
* filename - the current filename
* line - the actual line currently
* line-number - the current line-number
* original-line-number - line number when this line was created
* previous-sha1 - the full SHA1 of the previous commit of this line
* previous-sha - the shortened SHA1 of the previous commit of this line
* previous-filename - the filename in the previous commit of this line
* sha1 - the full SHA1 of the commit to which this line belongs
* sha - the shortened SHA1 of the commit to which this line belongs
* summary - the first line of the commit message of this line

# ACCESSORS ON Git::Blame::Commit

Note that `Git::Blame::Commit` objects are created automatically by `Git::Blame::File.new`.

* author - the name of the author of this commit
* author-mail - the email address of the author of this commit
* author-time - a DateTime object for the authoring of this commit
* blames - a list of Git::Blame::Line objects of this commit
* committed - whether it has actually been committed
* committer - the name of the committer of this commit
* committer-mail - the email address of the committer of this commit
* committer-time - a DateTime object for the committing of this commit
* previous-sha1 - the full SHA1 of the previous commit
* previous-sha - the shortened SHA1 of the previous commit
* previous-filename - the filename in the previous commit
* sha1 - the full SHA1 of the commit
* sha - the shortened SHA1 of the commit
* summary - the first line of the commit message

# AUTHORS

Elizabeth Mattijsen [liz@raku.rocks](mailto:liz@raku.rocks)

Source can be located at: <https://github.com/lizmat/Git-Blame-File> . Comments and Pull Requests are welcome.

If you like this module, or what I’m doing more generally, committing to a [small sponsorship](https://github.com/sponsors/lizmat/) would mean a great deal to me!

# COPYRIGHT AND LICENSE

Copyright 2022, 2024, 2025 Elizabeth Mattijsen

This library is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## dist_zef-FCO-Functional-Queue.md
[![Actions Status](https://github.com/FCO/Functional-Queue/actions/workflows/test.yml/badge.svg)](https://github.com/FCO/Functional-Queue/actions)

# NAME

Functional::Queue - Functional queue

# SYNOPSIS

```
my $q1 = Functional::Queue.new;
my :($q2, $) := $q1.enqueue: 1;

my :($q3, $v3) := $q2.dequeue;
say $v3;

Functional::Queue.mutate: {
   for ^10 -> $v { .enqueue: $v }
   say .dequeue while .elems;
}

```

# DESCRIPTION

Functional::Queue is a implementation of a functional data structure queue. It's immutable and thread-safe.

It has a `mutate` method that topicalise the object and will always topicalise the new generated stack. And that's gives the impression of mutating and makes it easier to interact with those objects.

# AUTHOR

Fernando Corrêa de Oliveira [fernando.correa@humanstate.com](mailto:fernando.correa@humanstate.com)

# COPYRIGHT AND LICENSE

Copyright 2024 Fernando Corrêa de Oliveira

This library is free software; you can redistribute it and/or modify it under the Artistic License 2.0.


## coll.md
coll

Combined from primary sources listed below.

# [In Operators](#___top "go to top of document")[§](#(Operators)_infix_coll "direct link")

See primary documentation
[in context](/language/operators#infix_coll)
for **infix coll**.

```raku
multi infix:<coll>(Str:D \a, Str:D \b --> Order:D)
multi infix:<coll>(Cool:D \a, Cool:D \b --> Order:D)
multi infix:<coll>(Pair:D \a, Pair:D \b --> Order:D)
```

`coll` is a sorting operator that takes pairs of [`Str`](/type/Str)s, [`Cool`](/type/Cool)s or [`Pair`](/type/Pair)s and returns an [`Order`](/type/Order) that uses the `$*COLLATION` order. The default behavior disregards diacritic marks and capitalization, for instance.

```raku
say "b" cmp "à";  # OUTPUT: «Less␤»
say "b" coll "à"; # OUTPUT: «More␤»
```

In the first case, lexicographic or codepoint order is taken into account. In the second, which uses `coll`, the diacritic is not considered and sorting happens according to intuitive order.

**NOTE:** These are not yet implemented in the JVM.


## dist_zef-rawleyfowler-JSON-Simd.md
# JSON::Simd

Parsing JSON as fast as possible in Raku using [simdjson](https://github.com/simdjson/simdjson).
This library is around 3.3x faster than [JSON::Tiny](https://github.com/moritz/json) and
about on par with [JSON::Fast](https://github.com/timo/json_fast), but,
as time goes on I think this dist should perform better (once I get around to using more nqp).

## How to install

#### Latest nightly

```
zef install -v https://github.com/rawleyfowler/JSON-Simd.git

```

#### Latest stable

```
zef install JSON-Simd

```

## How to use

Simply provide any JSON string

```
use JSON::Simd;

my @users = JSON::Simd::parse('[ { "name": "bob" }, { "name": "kenny" } ]');
@users[0].say; # { name => bob }

```

## License

This project is bundled along-side [simdjson](https://github.com/simdjson/simdjson) which
is provided under the Apache-2.0 License. That includes all directories under `cc/lib/simdjson`. The rest of the code is provided under the Artistic-2.0 License, the same license as Raku.


## dist_zef-vrurg-AttrX-Mooish.md
# NAME

`AttrX::Mooish` - extend attributes with ideas from Moo/Moose (laziness!)

# SYNOPSIS

```
use AttrX::Mooish;
class Foo {
    has $.bar1 is mooish(:lazy, :clearer, :predicate) is rw;
    has $!bar2 is mooish(:lazy, :clearer, :predicate, :trigger);
    has Num $.bar3 is rw is mooish(:lazy, :filter);

    method build-bar1 {
        "lazy init value"
    }

    method !build-bar2 {
        "this is private mana!"
    }

    method !trigger-bar2 ( $value ) {
        # do something after attribute changed.
    }

    method build-bar3 {
        rand;
    }

    method filter-bar3 ( $value, *%params ) {
        if %params<old-value>:exists {
            # Only allow the value to grow
            return ( !%params<old-value>.defined || $value > %params<old-value> ) ?? $value !! %params<old-value>;
        }
        # Only allow inital values from 0.5 and higher
        return $value < 0.5 ?? Nil !! $value;
    }

    method baz {
        # Yes, works with private too! Isn't it magical? ;)
        "Take a look at the magic: «{ $!bar2 }»";
    }
}

my $foo = Foo.new;

say $foo.bar1;
say $foo.bar3.defined ?? "DEF" !! "UNDEF";
for 1..10 { $foo.bar3 = rand; say $foo.bar3 }

```

The above would generate a output similar to the following:

```
lazy init value
UNDEF
0.08662089602505263
0.49049512098324255
0.49049512098324255
0.5983833081770437
0.9367804461546302
0.9367804461546302
0.9367804461546302
0.9367804461546302
0.9367804461546302
0.9367804461546302

```

# DESCRIPTION

This module is aiming at providing some functionality we're all missing from Moo/Moose. It implements laziness, accompanying methods and adds attribute value filter on top of what standard Moo/Moose provide.

What makes this module different from previous versions one could find in the Raku modules repository is that it implements true laziness allowing *Nil* to be a first-class value of a lazy attribute. In other words, if you look at the [SYNOPSIS](#SYNOPSIS) section, `$.bar3` value could randomly be either undefined or 3.1415926.

## Laziness for beginners

This section is inteded for beginners and could be skipped by experienced lazybones.

### What is "lazy attribute"

As always, more information could be found by Google. In few simple words: a lazy attribute is the one which gets its first value on demand, i.e. – on first read operation. Consider the following code:

```
class Foo {
    has $.bar is mooish(:lazy, :predicate);

    method build-bar { π }
}

my $foo = Foo.new
say $foo.has-bar; # False
say $foo.bar;     # 3.1415926...
say $foo.has-bar; # True

```

### When is it useful?

Laziness becomes very handy in cases where intializing an attribute is very expensive operation yet it is not certain if attribute is gonna be used later or not. For example, imagine a monitoring code which raises an alert when a failure is detected:

```
class Monitor {
    has $.notifier;
    has $!failed-object;

    submethod BUILD {
        $!notifier = Notifier.new;
    }

    method report-failure {
        $.notifier.alert( :$!failed-object );
    }

    ...
}

```

Now, imagine that notifier is a memory-consuming object, which is capable of sending notification over different kinds of media (SMTP, SMS, messengers, etc...). Besides, preparing handlers for all those media takes time. Yet, failures are rare and we may need the object, say, once in 10000 times. So, here is the solution:

```
class Monitor {
    has $.notifier is mooish(:lazy);
    has $!failed-object;

    method build-notifier { Notifier.new( :$!failed-object ) }

    method report-failure {
        $.notifier.alert;
    }

    ...
}

```

Now, it would only be created when we really need it.

Such approach also works well in interactive code where many wuch objects are created only the moment a user action requires them. This way overall responsiveness of a program could be significally incresed so that instead of waiting long once a user would experience many short delays which sometimes are even hard to impossible to be aware of.

Laziness has another interesting application in the area of taking care of attribute dependency. Say, `$.bar1` value depend on `$.bar2`, which, in turn, depends either on `$.bar3` or `$.bar4`. In this case instead of manually defining the order of initialization in a `BUILD` submethod, we just have the following code in our attribute builders:

```
method build-bar2 {
    if $some-condition {
        return self.prepare( $.bar3 );
    }
    self.prepare( $.bar4 );
}

```

This module would take care of the rest.

# USAGE

The [SYNOPSIS](#SYNOPSIS) is a very good example of how to use the trait `mooish`.

## Trait parameters

* *`lazy`*

  `Bool`, defines wether attribute is lazy. Can have `Bool`, `Str`, or `Callable` value. The later two have the same meaning, as for *`builder`* parameter.
* *`builder`*

  Defines builder method for a lazy attribute. The value returned by the method will be used to initialize the attribute.

  This parameter can have `Str` or `Callable` values or be not defined at all. In the latter case we expect a method with a name composed of "*build-*" prefix followed by attribute name to be defined in our class. For example, for a attribute named `$!bar` the method name is expected to be *build-bar*.

  A string value defines builder's method name.

  A callable value is used as-is and invoked as an object method. For example:

  ```
  class Foo {
      has $.bar is mooish(:lazy, :builder( -> $,*% {"in-place"} );
  }

  $inst = Foo.new;
  say $inst.bar;

  ```

  This would output '*in-place*'.

  *Note* the use of slurpy `*%` in the pointy block. Read about callback parameters below.
* *`predicate`*

  Could be `Bool` or `Str`. When defined trait will add a method to determine if attribute is set or not. Note that it doesn't matter wether it was set with a builder or by an assignment.

  If parameter is `Bool` *True* then method name is made of attribute name prefixed with *has-*. See [What is "lazy attribute"](#What is "lazy attribute") section for example.

  If parameter is `Str` then the string contains predicate method name:

  ```
          has $.bar is mooish(:lazy, :predicate<bar-is-ready>);
          ...
          method baz {
              if self.bar-is-ready {
                  ...
              }
          }

  ```
* *`clearer`*

  Could be `Bool` or `Str`. When defined trait will add a method to reset the attribute to uninitialzed state. This is not equivalent to *undefined* because, as was stated above, *Nil* is a valid value of initialized attribute.

  Similarly to *`predicate`*, when *True* the method name is formed with *clear-* prefix followed by attribute's name. A `Str` value defines method name:

  ```
          has $.bar is mooish(:lazy, :clearer<reset-bar>, :predicate);
          ...
          method baz {
              $.bar = "a value";
              say self.has-bar;  # True
              self.reset-bar;
              say self.has-bar;  # False
          }

  ```
* *`filter`*

  A filter is a method which is executed right before storing a value to an attribute. What is returned by the method will actually be stored into the attribute. This allows us to manipulate with a user-supplied value in any necessary way.

  The parameter can have values of `Bool`, `Str`, `Callable`. All values are treated similarly to the `builder` parameter except that prefix '*filter-*' is used when value is *True*.

  The filter method is passed with user-supplied value and the following named parameters:

  `attribute` - contains full attribute name.

  `builder` - passed if filter is called as a stage of attribute building.

  `old-value` - passed with the previous attribute value if it had one; i.e. if attribute has been initialized.

  **Note** that it is not recommended for a filter method to use the corresponding attribute directly as it may cause unforseen side-effects like deep recursion. The `old-value` parameter is the right way to do it.
* *`trigger`*

  A trigger is a method which is executed right after attribute value has been changed.

  Allowed values for this parameter are `Bool`, `Str`, `Callable`. All values are treated similarly to the `builder` parameter except that prefix '*trigger-*' is used when value is *True*.

  Trigger method gets passed with the stored value as first positional parameter. If there is also a `filter` defined for the attribute then trigger receives the value returned by the filter, not the initial. I.e. it always get what's eventually stored in the attribute. It also receives the same named parameters as `filter` method: `attribute`, `builder`, `old-value`.
* *`alias`, `aliases`, `init-arg`, `init-args`*

  Those are four different names for the same parameter which allows defining attribute aliases. So, whereas Internally you would have single container for an attribute that container would be accessible via different names. And it means not only attribute accessors but also clearer and predicate methods:

  ```
  class Foo {
      has $.bar is rw is mooish(:clearer, :lazy, :aliases<fubar baz>);

      method build-bar { "The Answer" }
  }

  my $inst = Foo.new( fubar => 42 );
  say $inst.bar; # 42
  $inst.clear-baz;
  say $inst.bar; # The Answer
  $inst.fubar = pi;
  say $inst.baz; # 3.1415926

  ```

  Aliases are not applicable to methods called by the module like builders, triggers, etc.
* *`no-init`*

  This parameter will prevent the attribute from being initialized by the constructor:

  ```
  class Foo {
      has $.bar is mooish(:lazy, :no-init);

      method build-bar { 42 }
  }

  my $inst = Foo.new( bar => "wrong answer" );
  note $inst.bar; # 42

  ```
* *`composer`*

  This is a very specific option mostly useful until role `COMPOSE` phaser is implemented. Method of this option is called upon class composition time.

## Public/Private

For all the trait parameters, if it is applied to a private attribute then all auto-generated methods will be private too.

The call-back style options such as `builder`, `trigger`, `filter` are expected to share the privace mode of their respective attribute:

```
    class Foo {
        has $!bar is rw is mooish(:lazy, :clearer<reset-bar>, :predicate, :filter<wrap-filter>);

        method !build-bar { "a private value" }
        method baz {
            if self!has-bar {
                self!reset-bar;
            }
        }
        method !wrap-filter ( $value, :$attribute ) {
            "filtered $attribute: ($value)"
        }
    }

```

Though if a callback option is defined with method name instead of `Bool` *True* then if method wit the same privacy mode is not found then opposite mode would be tried before failing:

```
    class Foo {
        has $.bar is mooish( :trigger<on_change> );
        has $!baz is mooish( :trigger<on_change> );
        has $!fubar is mooish( :lazy<set-fubar> );

        method !on_change ( $val ) { say "changed! ({$val})"; }
        method set-baz { $!baz = "new pvt" }
        method use-fubar { $!fubar }
    }

    $inst = Foo.new;
    $inst.bar = "new";  # changed! (new)
    $inst.set-baz;      # changed! (new pvt)
    $inst.use-fubar;    # Dies with "No such private method '!set-fubar' for invocant of type 'Foo'" message

```

## User method's (callbacks) options

User defined (callback-type) methods receive additional named parameters (options) to help them understand their context. For example, a class might have a couple of attributes for which it's ok to have same trigger method if only it knows what attribute it is applied to:

```
    class Foo {
        has $.foo is rw is mooish(:trigger('on_fubar'));
        has $.bar is rw is mooish(:trigger('on_fubar'));

        method on_fubar ( $value, *%opt ) {
            say "Triggered for {%opt<attribute>} with {$value}";
        }
    }

    my $inst = Foo.new;
    $inst.foo = "ABC";
    $inst.bar = "123";

The expected output would be:

    Triggered for $!foo with with ABC
    Triggered for $!bar with with 123

```

**NOTE:** If a method doesn't care about named parameters it may only have positional arguments in its signature. This doesn't work for pointy blocks where anonymous slurpy hash would be required:

```
    class Foo {
        has $.bar is rw is mooish(:trigger(-> $, $val, *% {...}));
    }

```

### Options

* *`attribute`*

  Full attribute name with twigil. Passed to all callbacks.
* *`builder`*

  Only set to *True* for `filter` and `trigger` methods when attribute value is generated by lazy builder. Otherwise no this parameter is not passed to the method.
* *`old-value`*

  Set for `filter` only. See its description above.

## Definite Types

The module allows for lazy attributes to have a definite type. By default the compiler will throw an error unless such attribute has `is required` trait or a default value. But for lazy attributes the default value must be provided by their builders:

```
class Foo {
    has Int:D $.the-answer is mooish(:lazy);
    method build-the-answer { 42 }
}

```

Apparently, the value returned by a builder must pass the typecheck. Therefore the following code will fail a run time:

```
class Foo {
    has Str:D $.bad is mooish(:lazy);
    method build-bad { Str }
}

```

## Some magic

Note that use of this trait doesn't change attribute accessors. More than that, accessors are not required for private attributes. Consider the `$!bar2` attribute from [SYNOPSIS](#SYNOPSIS).

## Performance

Module versions prior to v0.5.0 were pretty much costly perfomance-wise. This was happening due to use of [`Proxy`](https://docs.raku.org/type/Proxy) to handle all attribute read/writes. Since v0.5.0 only the first read/write operation would be handled by this module unless `filter` or `trigger` parameters are used. When `AttrX::Mooish` is assured that the attribute is properly initialized it steps aside and lets the Raku core to do its job without intervention.

The only exception takes place if `clearer` parameter is used and `clear-<attribute>` method is called. In this case the attribute state is reverted back to uninitialized state and [`Proxy`](https://docs.raku.org/type/Proxy) is getting installed again – until the next read/write operation.

`filter` and `trigger` are special with this respect because they require permanent monitoring of attribute operations making it effectively impossible to strip off `Proxy` from attribute's value. For this reason use of these parameters must be very carefully considered. One is highly discouraged from using them for any code where performance is important.

## Multi-threading

This module provides partial thread-safety and must be used with care with this respect. This means that the following conditions are guaranteed:

* build operations are safe among themselves
* clear operations are safe among themselves
* anything else, including mix of build/clear operations, is unsafe

Consider it the way we normally consider working with an attribute in a concurrent environment, where reads and writes must be mutually protected to ensure data safety.

To sum up the above stated, what would be guaranteed is that a read-only attribute would provide robust results in a multi-threaded environment, as it is expected from a read-only pre-initialized attribute.

Predicates are considered *read* operations and as such are not protected either. Think of testing a non-mooified attribute for definedness, for example.

# CAVEATS

* Due to the "magical" nature of attribute behaviour conflicts with other traits are possible. In particular, mixing up with `is built` trait is not recommended.
* Use of [`Proxy`](https://docs.raku.org/type/Proxy) as the container may have unexpected side effects in some use cases like passing it as a parameter. Multiple calls of `Proxy`'s `FETCH` are possible, for example. While generally harmless this may result in performance issues of affected application. To workaround the problem attribute value can be temporarily assigned into a variable.
* Another surprising side effect happens when a "mooified" array or hash attribute is used with a loop. Since [`Proxy`](https://docs.raku.org/type/Proxy) is a container, loops are considering such attributes as itemized, no matter what their final value is. Consider the following:

  ```
  class Foo {
      has @.a is mooish(:lazy);
      method build-a { 1,2,3 }
      method dump {
          for @!a -> $val { say $val.raku }
      }
  }
  Foo.new.dump; # $[1, 2, 3]

  ```

  Note that this only happens when attribute is accessed privately as `for Foo.new.a {...}` would behave as expected. Also, for non-filtering and non-triggering attributes this only happens when the attribute is not initialized yet.

  The problem could be workarounded either by using `@.a` notation, or with explicit decontainerization `@!a<>`.

## Cloning

Cloning of an object with mooified attributes is a non-trivial case resulting from the use of [`Proxy`](https://docs.raku.org/type/Proxy). Again. The root of the problem lies in the fact that `Proxy` is using closures for its `FETCH`/`STORE`. This is how it knows what object is to be updated when necessary: the object is captured by the closures. But what help us under normal circumstances becomes our problem after cloning because the new object attributes would still be bound to proxies referring the original instance!

`AttrX::Mooish` handles this situation starting with v1.0.0 release by implementing post-clone fix up procedure where all proxies are getting replaced using new closures. This is implemented by installing special `clone` method into each class containing mooified attributes.

So far, so good until it comes down to lazy attributes which were already initialized using other attributes of the class. Simple cloning doesn't affect them, but if their dependency has been changed using twiddles then we're in trouble:

```
class Foo {
    has $.a1 = 1;
    has $.a2 is mooish(:lazy);
    method build-a2 { $!a1 * 2 }
}
my $obj = Foo.new;
say $obj.a2; # 2
my $copy = $obj.clone(:a1(3));
say $copy.a2; # Oops, it's still 2!

```

In such situations `AttrX::Mooish` resets the lazy attributes to unitialized state so they would get re-initialized again using new values.

The only exception is for writable (`is rw`) lazy attributes. When they hold a value there is no way for us to know where the value came from because it could have been assigned by code external to our class in which case resetting it might be not so smart.

**IMPORTTANT!** Also remember that a non-writable attribute can still be assigned via private accessor (`$!attr = $value;`) by class code. These cases cannot be detected either but disreprected by the module. Taking care of them is developer's responsibility!

Generally speaking, there is no good strategy to handle all possible cases what it comes to cloning lazy entities. Sometimes it would be better to resolve edge cases manually. If this is your case then metamodel method `post-clone` can be used to do the standard fixup job:

```
class Foo {
    ...
    method clone(*%twiddles) {
        my \cloned = ::?CLASS.^post-clone: self, callsame(), %twiddles;
        ... # Do specific fixups here
        cloned
    }
}

```

Basically, the first line is what `AttrX::Mooish` installs for you by default. Consider the use of `::?CLASS` instead of `self`. This is mandatory because `self` can be an instance of a child class.

# SEE ALSO

[ChangeLog](ChangeLog.md)

# COPYRIGHT

(c) 2023, Vadim Belman [vrurg@cpan.org](mailto:vrurg@cpan.org)

# LICENSE

Artistic License 2.0

See the [*LICENSE*](LICENSE) file in this distribu


## dist_zef-guifa-User-Timezone.md
# User::Timezone

**Important notice:** This module was previously known as `Intl::UserTimezone`. Its name was changed to align with similar modules. It will still be usable as `Intl::UserTimezone` until the end of 2024 to give ample time for the change to happen.

A simple Raku module for determining the user's timezone as an Olson (IANA or tz) identifier, particularly useful when formatting dates.

To use:

```
use User::Timezone;

say user-timezone;  # 'America/New_York'
                    # 'Africa/Malabo'
                    # 'Asia/Tokyo'
                    # 'Etc/GMT'

```

The returned string does *not* apply a metazone.
If you wish to show a user-facing string like, e.g., "Central European Time", you should use the appropriate functions from `Intl::DateTime` (NYI, might go into `DateTime::*`, haven't decided yet ^\_^).

## Options

The default fallback (in case detection fails) is **Etc/GMT**.
If for some reason you wish to use a different one, pass it as a positional argument in the use statement.
Note that this has *global* effects:

```
use User::Timezone 'Asia/Qyzylorda'

```

Similarly, you can *force* a certain timezone which is useful when testing out aspects of your program that may be sensitive to timezones.
To do that, include the override option.

```
use User::Timezone :override;

```

This will import two additional subroutines into your scope:

```
override-user-timezone(Str $olson-id)
clear-user-timezone-override

```

These do exactly what their names imply.
Again, be aware that their effects are global.

## Compatibility / Implementation Notes

For Mac OS and most \*nix systems, the region is accurately grabbed from `/etc/localtime` if it exists.
Currently timezones indicated by the `$TZ` environmental variable are ignored, but will eventually be supported.

For Windows, the ID should be acceptable and better than a GMT offset, but may occasionally be suboptimal.
This is because Windows uses its own custom timezone identifiers that do not have a one-to-one relationship with Olsen IDs.
The Windows timezone ID is combined with the Windows GeoID to provide a best-guess that should generally be accurate.
For example, if your Windows timezone is "Central Standard Time", and your GeoID is 244 (United States), then it will be reported as **America/Chicago** (others are possible, but there is not enough information to differentiate with **America/Indiana/Knox**, so the broadest is used).
But if your GeoID is 39 (Canada), then it will be reported as **America/Winnipeg**.

## What if it doesn't work

If there is a problem determining the timezone, the default will be `Etc/GMT`, being the most generic, although that's not really an acceptable alternative.
If it's clear that `User::Timezone` cannot determine things for your operating system, or is in some other way not returning the correct results, please file an issue on Github and let's figure out how to make it work on your system.

# Version history

* **v0.3.3**
  * Add native Mac support
* **v0.3.2**
  * Minor adjustment to Windows regions data files
  * Code reorganization for improved future maintenance
* **v0.3.1**
  * Updated Windows zones data files
* **v0.3.0**
  * Changed name to `User::Timezone` and added a fallback message for older uses
  * Adjusted Mac OS detection for improved accuracy
* **v0.2**
  * Added option for a custom fallback (in case detection fails)
  * Added ability for overriding the timezone (mainly for testing purposes)
* **v0.1.1**
  * Removed test code that prevented correct Windows detection.
  * Chomped output to facilitate use in other modules.
* **v0.1**
  * Initial release with support for macOS, most \*nix machines and beta support Windows

# License

Except as indicated, this module and all its files is provided under the Artistic License 2.0.

## Except as indicated

The file `windowsZones.xml` is Copyright 2022 The Unicode Consortium, and distributed without modification in accordance with its [license/terms of use](https://www.unicode.org/copyright.html).