发布一个包

将包发布到 Hex 包含注册 Hex 用户、在项目 的 mix.exs 文件中添加元数据,最后使用 mix 任务提交包。

注册 Hex 用户

注册用户时,系统会提示您输入用户名、电子邮件和密码。电子邮件用于在注册时确认您的身份,以及在您的包出现问题时与您联系。电子邮件永远不会与第三方共享。

$ mix hex.user register
Username: johndoe
Email: [email protected]
Password:
Password (confirm):
Registering...
Generating API key...
You are required to confirm your email to access your account, a confirmation email has been sent to [email protected]

完成此步骤后,请检查您的电子邮件收件箱以获取确认邮件。在您点击邮件中的链接后,您的帐户即可使用。

命名您的包

在发布之前,您需要选择包的名称。请记住,发布到 Hex 的包是公开的,社区中的任何人都可以访问它们。社区也有责任选择和鼓励好的包名称。以下是一些提示

  • 避免使用攻击性或骚扰性的包名称、昵称或其他可能会损害所有用户友好、安全和欢迎环境的标识符。
  • 如果您在现有包的基础上提供功能,请考虑使用该包名称作为前缀。例如,如果您想为 Plug 添加身份验证,请考虑将您的包命名为 plug_auth (或 plug_somename),而不是 auth (或 somename)。
  • 避免与现有包发生命名空间冲突。Plug 拥有 Plug 命名空间,如果您为 Plug 提供一个身份验证包,请使用 PlugAuth 命名空间,而不是 Plug.Auth
    • 此准则适用于您的所有模块,因此,如果您的包是 plug_auth,那么您的所有模块(除了像 mix 任务之类的特殊模块)都应以 PlugAuth. 开头(例如 PlugAuth.UtilsPlugAuth.User)。这一点很重要,因为在 BEAM 系统中只能有一个具有给定名称的模块运行,如果多个包定义了相同的模块,那么您就无法使用这两个包,因为只会使用该模块的一个版本。

有了名称,就可以在 mix.exs 文件中添加相应的元数据了。

mix.exs 中添加元数据

包是在项目 的 mix.exs 文件的 project 函数中配置的。 请参阅下面的示例文件

首先,请确保 :version 属性正确。所有 Hex 包都必须遵循 语义版本控制。当您的包版本处于主版本“0”时,任何重大更改都应通过增加次版本来指示。例如,0.1.0 -> 0.2.0

填写 :description 属性。它应该是描述包的一个句子或几个句子。

:package 属性下,还有一些额外的配置选项

:name
如果您想以与应用程序名称不同的名称发布包,则为包的名称。默认情况下,它设置为与您的 OTP 应用程序名称相同(与 `project.app` 的值相同),并以 snake_case 格式(小写,用下划线作为单词分隔符)编写。
:organization
包所属的组织。该包将发布到组织的存储库,默认情况下为全局 "hexpm" 存储库。
:licenses
项目使用的许可证列表。此属性是必需的。建议使用 SPDX 许可证标识符
:links
一个映射,其中键是链接名称,值是链接 URL。可选,但强烈建议使用。
:files
要包含在包中的文件和目录列表。默认为标准项目目录,因此通常您不需要设置此属性。
:build_tools
可以构建包的构建工具列表。您很少需要设置它,因为 Hex 会尝试根据包中的文件自动检测构建工具。如果存在 rebarrebar.config 文件,Hex 将标记它可以使用 rebar 构建。通过设置此字段可以覆盖此检测。

为了改进 ExDoc 生成的文档,也可以在 project 函数中提供以下字段

:source_url
指向您的源代码公开可用位置的 URL。这将用于从文档中直接链接到不同模块函数的代码。
:homepage_url
指向您的应用程序主页的 URL。这将用于从生成的文档中链接回您的主页。

有关改进生成文档的更多信息,请参阅 ExDoc 文档

依赖项

没有 SCM (:git:path) 的依赖项将自动被视为 Hex 依赖项。有关详细信息,请参阅 用法指南

包只能使用 Hex 包作为依赖项。无法上传具有 Git 依赖项的包。此外,只包含生产依赖项,就像 Mix 在获取依赖项的依赖项时只获取生产依赖项一样。当依赖项在没有 :only 属性或使用 only: :prod 定义时,它将被视为生产依赖项。

文档

当您发布包时,文档会自动发布到 hexdocs.pm。如果您只希望发布包本身,可以运行 mix hex.publish package,类似地,如果您想(重新)发布现有包版本的文档,可以运行 mix hex.publish docs

在发布文档之前,Hex 将通过运行 mix docs 任务来构建文档,以确保它是最新的。Elixir 的主要文档工具 ex_doc 提供了此任务,因此,如果您将它添加为依赖项,那么在发布包时就不需要做任何其他事情来获取自动文档构建。查看 ex_doc 文档,了解有关如何配置文档的信息,建议您在发布文档到 Hex 之前使用 mix docs 在本地构建文档。最后,还要查看 Elixir 文档编写指南,了解建议和最佳实践。

如果您想使用其他文档工具,或者对 ex_doc 的构建进行后期处理,可以为 docs 任务创建别名,有关详细信息,请查看 任务别名 docs。构建的文档应该放在 doc/ 目录中,至少包含一个 index.html 文件。

示例 mix.exs 文件

defmodule Postgrex.MixProject do
  use Mix.Project

  def project() do
    [
      app: :postgrex,
      version: "0.1.0",
      elixir: "~> 1.0",
      build_embedded: Mix.env == :prod,
      start_permanent: Mix.env == :prod,
      description: description(),
      package: package(),
      deps: deps(),
      name: "Postgrex",
      source_url: "https://github.com/elixir-ecto/postgrex"
    ]
  end

  def application() do
    []
  end

  defp deps() do
    [
      {:decimal, "~> 1.0"},
      {:ex_doc, "~> 0.14", only: :dev, runtime: false}
    ]
  end

  defp description() do
    "A few sentences (a paragraph) describing the project."
  end

  defp package() do
    [
      # This option is only needed when you don't want to use the OTP application name
      name: "postgrex",
      # These are the default files included in the package
      files: ~w(lib priv .formatter.exs mix.exs README* readme* LICENSE*
                license* CHANGELOG* changelog* src),
      licenses: ["Apache-2.0"],
      links: %{"GitHub" => "https://github.com/elixir-ecto/postgrex"}
    ]
  end
end

提交软件包

在将软件包元数据和依赖项添加到 mix.exs 后,我们就可以使用 mix hex.publish 命令发布软件包了。

$ mix hex.publish
Publishing postgrex v0.4.0
  Dependencies:
    decimal ~> 0.1.0
  Excluded dependencies (not part of the Hex package):
    ex_doc
  Included files:
    lib/postgrex
    lib/postgrex/binary_utils.ex
    lib/postgrex/connection.ex
    lib/postgrex/protocol.ex
    lib/postgrex/records.ex
    lib/postgrex/types.ex
    mix.exs
Proceed? [Yn] Y
Published postgrex v0.4.0

恭喜你,你已经发布了你的软件包!它将出现在 hex.pm 网站上,并且可以在其他 Mix 项目中添加为依赖项。

请在发布后测试你的软件包,方法是将其添加为 Mix 项目的依赖项,并获取并编译它。如果有任何问题,你可以在首次发布后的一个小时内再次发布软件包。也可以使用 mix hex.publish --revert VERSION 撤回发布。

在运行发布软件包的命令时,Hex 将创建一个包含 :files 属性中列出的所有文件和目录的 tar 文件。tar 包上传到 Hex 服务器后,它将被上传到 CDN,以便用户能够快速可靠地访问。Hex 还将重新编译所有客户端将自动更新的注册表文件,以便在获取依赖项时使用。

从 CI 发布

你可以使用 CI 等工具来自动发布软件包。你需要一个具有发布软件包权限的密钥。

$ mix hex.user key generate --key-name publish-ci --permission api:write
Username:
Account password:
Generating key...
f48ac236bca15c3271e077c15c5320c4

如果你正在为你的组织发布一个软件包,建议使用组织的密钥而不是个人密钥。

$ mix hex.organization key acme generate --key-name publish-ci --permission api:write
Local password:
f48ac236bca15c3271e077c15c5320c4

HEX_API_KEY 系统环境变量中设置密钥。要发布软件包而不提示,请传递 --yes 标志。

$ HEX_API_KEY=f48ac236bca15c3271e077c15c5320c4 mix hex.publish --yes

请注意,在自动化发布时应谨慎操作,因为 Hex 会输出重要的警告,甚至会提供有关如何改进软件包的建议,这些建议在自动化过程中很容易被忽略。另外,请注意 Hex 仍然处于 1.0 之前的阶段,因此在任何版本之间都可能出现重大更改,而 CI 通常会安装最新版本。