Last active
October 21, 2017 23:23
-
-
Save ugexe/10066e2608bdabb1773d69de2d7dfd57 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Namespacing multiple versions/apis with `provides` - theoretical examples. | |
# | |
# The grammar mentioned below for parsing namespaces (depspecs): | |
# https://gist.github.com/ugexe/776d8794518d69749e8b53c36d802ddc#file-zef-utils-distribution-pm6-L11 | |
# | |
# Consider CompUnit::DependencySpecification - it can essentially turn a hash form of depspec into | |
# string form (ignoring the slight naming inconsistencies), ala .new(|%( :short-name<My::API>, :api-matcher<0> )). | |
# What it cannot yet do is turn that same string form back into the hash form it is fed, ala .new("My::API:api<0>"). | |
# With a grammer/parser this round trip is possible for literals. I will now extend this thought to `provides`: | |
{ | |
"name" : "My::API", | |
"version" : "4.2", | |
"api". : "1", | |
"auth" : "foo:bar", | |
"provides" : { | |
"My::API" => "lib/My/API.pm6", | |
# My::API:auth<foo:bar>:api<1>:ver<4.2> | |
# | |
# The common scenario. | |
# CURI/Distribution and zef understand this. | |
"My::API:api<2>" => "lib/My/API.pm6", | |
# My::API:auth<foo:bar>:api<2>:ver<4.2> | |
# | |
# Mapping a specific namespace to a file that differs from parent distribution's value (api). | |
# Zefv2 parses the names with a grammar and can understand them (as a side effect of needing to parse | |
# depends name/adverbs correctly; see url of grammar above). CUR/Distribution does not (it has no need | |
# to parse depends from meta) and considers "My::API:api<2>" to be the short name, so installation and | |
# usage does not currently work. | |
# | |
# Zefv2 could just expand this to a hash for installation (so CUR/Distribution only needs to understand | |
# the new fields zef expands into some hash), but then CUR::FileSystem (-I.) would not work since it | |
# can't parse the namespace. | |
"My::API" => { "file" : "lib/My/API.pm6", "api" : "3" }, | |
# My::API:auth<foo:bar>:api<3>:ver<4.2> | |
# | |
# The expanded form mentioned above. But this is flawed because `provides` is a hash, and | |
# "My::API" might not be unique when providing multiple api versions (precisely the situation | |
# here with api 1 and 3). The prior example avoids this because the unique parts (api version) | |
# is in the namespace string already. | |
# This is similar to CPAN Meta Spec v2. | |
"My::API:ver<6.9>" => { "file" : "lib/My/API.pm6", "api" : "4" }, | |
# My::API:auth<foo:bar>:api<4>:ver<6.9> | |
# | |
# A hybrid approach of examples with api v2 and v3 included for novelty, along with | |
# changing the version from the distribution's 4.2 to 6.9. | |
{ | |
"name" : "My::API", | |
"file" : "lib/My/API.pm6", | |
"api" : "5" | |
}, | |
# My::API:auth<foo:bar>:api<5>:ver<4.2> | |
# | |
# `provides` is not an array so this form would require that to change. | |
# Probably the most generic way, but if you're really providing multiple versions of a namespace it | |
# would be nice if this was differentiated in the structure somehow (which this does not do). | |
"My::API:auth<foo:bar>:api<6>:ver<4.2>:file<lib/My/API.pm6>", | |
# My::API:auth<foo:bar>:api<6>:ver<4.2> | |
# | |
# `provides` is not an array so this form would require that to change. | |
# This is the dependency/use form taken to the near extreme (short of ':name<My::API>:auth<foo:bar>:api<6>:ver<4.2>'') | |
# and is the opposite of the hash form example in api v5. | |
# | |
# Note how api v5 and v6 can easily be round tripped, since its just key/value. | |
# I like the -availability- of this form because its a legit `use` statement, right down to the :file<> | |
# (in the context of the right type of distribution anyway). I also like that it makes this closer | |
# to what a user may put in `depends` (a better example than provides, but a namespace all the same), so | |
# if it can parse one (hash or string form) it can parse both - thus CURI can also be extended to better | |
# understand the total dependency graph of it's distributions (instead of just the individual namespaces). | |
"My::API" => [{ "file" : "lib/My/API.pm6", "api" : "7" }], | |
# My::API:auth<foo:bar>:api<7>:ver<4.2> | |
# | |
# `provides` -value- is not a -string-, so this form would require that to change. | |
# Its like api v3, except namespace adverbs are stored in an Array of Hash so that the namespace can | |
# provide multiple versions while still allowing `provides` to remain a hash. It avoids the problem | |
# mentioned in api v5 because each differentiation on a namespace is grouped under the namespace itself. | |
# | |
# This is arguably the best option along with v5. The advantage to v5 to me is this format is more | |
# human/author friendly as its easier to grok what a namespace encompases vs finding each hash with | |
# the same value in its name field. | |
} | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment