Perl6如何决定加载哪个版本的模块?

时间:2019-04-14 03:19:33

标签: module package versioning perl6 api-versioning

当我执行use Foo:ver<1.0>;时,它将加载模块Foo的1.0版。但是,当我use Foo;时会发生什么?

1 个答案:

答案 0 :(得分:10)

TL; DR:如果未指定特定版本,则默认的Perl6安装将从与该模块的任何版本相匹配的第一个CompUnit::Repository加载最新版本(并且不一定是所有{{ 1}})。


除非另有说明,否则可以创建和加载本身仅加载模块的随机版本的非核心CompUnit::Repository。此答案不适用于这些答案,而是着眼于各个CompUnit::Repository核心的行为和规范。

确定要加载哪个模块的第一件事是哪个CompUnit::Repository首先匹配请求的身份。默认存储库链如下所示:

CompUnit::Repository

# EXAMPLE 1 $ perl6 -e '.say for $*REPO.repo-chain' inst#/home/ugexe/.perl6 inst#/home/ugexe/perl6/install/share/perl6/site inst#/home/ugexe/perl6/install/share/perl6/vendor inst#/home/ugexe/perl6/install/share/perl6 前缀告诉我们这是一个inst#。这是相关的,因为这样的存储库可以包含多个发行版-包括同一发行版的多个版本-对于用于CompUnit::Repository::InstallationCompUnit::Repository::FileSystem的单一发行版-I.而言并非如此(这是真正 -Ilib-Ifile#/home/ugexe/repos/Foo)。

-Ifile#/home/ugexe/repos/Foo/lib

让我们假设以下内容:

  • # EXAMPLE 2 $ perl6 -I. -e '.say for $*REPO.repo-chain' file#/home/ugexe/repos/Foo inst#/home/ugexe/.perl6 inst#/home/ugexe/perl6/install/share/perl6/site inst#/home/ugexe/perl6/install/share/perl6/vendor inst#/home/ugexe/perl6/install/share/perl6 包含file#/home/ugexe/repos/Foo

  • Foo:ver<0.5>包含inst#/home/ugexe/.perl6Foo:ver<0.1>

  • Foo:ver<1.0>包含inst#/home/ugexe/.perl6Foo:ver<2.0>

Foo:ver<0.1>将加载:

  • 示例1 -use Foo;中的Foo:ver<1.0>

  • 示例2 -inst#/home/ugexe/.perl6中的Foo:ver<0.5>

即使所有存储库中最高的版本是file#/home/ugexe/repos/Foo,也是链中第一个与任何版本的Foo相匹配的存储库(即Foo:ver<2.0>)都赢了,所以{从未选择{1}}。您可能会猜到,这使“最高版本”成为确定要加载模块版本的第二件事,但这实际上是第四!但是,我在这里提到了它,因为对于典型用法而言,这已经足够了。


确定要加载模块版本的第二件事是use Foo字段。本质上,这是另一个版本字段,当与版本本身结合使用时,它提供了固定主要版本的基本方法。

让我们假设以下内容:

  • Foo:ver<2.0>包含api

  • file#/home/ugexe/repos/Foo包含Foo:api<0>:ver<0.5>inst#/home/ugexe/.perl6

Foo:api<1>:ver<0.1>将加载:

  • 示例1 -Foo:api<0>:ver<1.0>中的use Foo;

  • 示例2 -Foo:api<1>:ver<0.1>中的inst#/home/ugexe/.perl6

即使在示例1中,最高版本是Foo:api<0>:ver<0.5>,最高api版本是file#/home/ugexe/repos/Foo,因此被选择。


确定加载哪个版本的模块的第三件事是Foo:api<0>:ver<1.0>字段。与Foo:api<1>:ver<0.1>auth不同,它并不意味着任何排序。并且与apiver字段不同,您可能不应该在例如api -它以政策为中心,并且将成为大多数开发人员应该永远不必担心(ab)使用的强大工具/逃生门。

让我们假设以下内容:

  • ver包含use Foo

  • file#/home/ugexe/repos/Foo包含Foo:auth<github:ugexe>:ver<0.5>inst#/home/ugexe/.perl6

Foo:ver<0.1>将加载:

  • 示例1 -Foo:auth<github:ugexe>:ver<1.0>中的use Foo;

  • 示例2 -Foo:auth<github:ugexe>:ver<1.0>中的inst#/home/ugexe/.perl6

在两个示例中,Foo:auth<github:ugexe>:ver<0.5>file#/home/ugexe/repos/Foo相同,因此,即使一个回购假设包含一个不包含use Foo;的模块,这并不意味着它与{ {1}}。相反,use Foo:auth(*):ver(*)包含任何auth值作为匹配项(实际上意味着use Foo;会被完全忽略)。


有关更多示例,spec tests是一个很好的来源