Support publish to Hex.pm

To do it, run:
    make hex-publish PROJECT_VERSION=3.6.6

You can also publish documentation to hexdocs.pm. The documentation is
generated first with the `docs` Erlang.mk target and the content of the
`doc` subdirectory is published. To do it, run:
    make hex-publish-docs PROJECT_VERSION=3.6.6

Generated files are published to Hex.pm so that users of this package
don't have to depend on rabbitmq-codegen and Python.

`git-revisions.txt` is generated in the process to carry the version of
the project. Not really standard, but it's the way other RabbitMQ
projects do it for now, so take advantage of the existing
infrastructure. Once a package is published to Hex.pm, it's good to
`make clean` so this file is removed.

Other RabbitMQ components can also be published to Hex.pm with a few
modifications. For them, rabbit_common/mk/rabbitmq-components.hexpm.mk
is sent in place of their copy of rabbitmq-components.mk. This modified
file pulls dependencies from Hex.pm using version $(PROJECT_VERSION),
instead of using Git.

All projects published to Hex.pm can use $(RABBITMQ_HEXPM_DEFAULT_FILES)
as the list of files to put in the `files` key in the .app file.

[#134268483]
This commit is contained in:
Jean-Sébastien Pédron 2016-12-13 17:14:58 +01:00
parent 56e07472f9
commit c83c6a2967
6 changed files with 174 additions and 44 deletions

View File

@ -2,13 +2,18 @@
.sw?
.*.sw?
*.beam
*.coverdata
/.erlang.mk/
/cover/
/deps/
/doc/
/ebin/
/git-revisions.txt
/logs/
/plugins/
/rebar.config
/rebar.lock
/test/ct.cover.spec
/xrefr
/rabbit_common.d

View File

@ -1,18 +1,25 @@
PROJECT = rabbit_common
PROJECT_DESCRIPTION = Modules shared by rabbitmq-server and rabbitmq-erlang-client
define PROJECT_APP_EXTRA_KEYS
%% Hex.pm package informations.
{maintainers, [
"RabbitMQ Team <info@rabbitmq.com>",
"Jean-Sebastien Pedron <jean-sebastien@rabbitmq.com>"
]},
{licenses, ["MPL 1.1"]},
{links, [
{"Website", "http://www.rabbitmq.com/"},
{"GitHub", "https://github.com/rabbitmq/rabbitmq-common"}
]},
{build_tools, ["make", "rebar3"]},
{files, [
$(RABBITMQ_HEXPM_DEFAULT_FILES),
"mk"
]}
endef
LOCAL_DEPS = compiler syntax_tools xmerl
BUILD_DEPS = rabbitmq_codegen
TEST_DEPS = proper
.DEFAULT_GOAL = all
EXTRA_SOURCES += include/rabbit_framing.hrl \
src/rabbit_framing_amqp_0_8.erl \
src/rabbit_framing_amqp_0_9_1.erl
.DEFAULT_GOAL = all
$(PROJECT).d:: $(EXTRA_SOURCES)
# FIXME: Use erlang.mk patched for RabbitMQ, while waiting for PRs to be
# reviewed and merged.
@ -20,6 +27,16 @@ $(PROJECT).d:: $(EXTRA_SOURCES)
ERLANG_MK_REPO = https://github.com/rabbitmq/erlang.mk.git
ERLANG_MK_COMMIT = rabbitmq-tmp
# Variables and recipes in development.*.mk are meant to be used from
# any Git clone. They are excluded from the files published to Hex.pm.
# Generated files are published to Hex.pm however so people using this
# source won't have to depend on Python and rabbitmq-codegen.
#
# That's why those Makefiles are included with `-include`: we ignore any
# inclusion errors.
-include development.pre.mk
include mk/rabbitmq-components.mk
include erlang.mk
include mk/rabbitmq-build.mk
@ -36,36 +53,4 @@ ifeq ($(call compare_version,$(ERTS_VER),$(tls_atom_version_MAX_ERTS_VER),<),tru
RMQ_ERLC_OPTS += -Ddefine_tls_atom_version
endif
# --------------------------------------------------------------------
# Framing sources generation.
# --------------------------------------------------------------------
PYTHON ?= python
CODEGEN = $(CURDIR)/codegen.py
CODEGEN_DIR ?= $(DEPS_DIR)/rabbitmq_codegen
CODEGEN_AMQP = $(CODEGEN_DIR)/amqp_codegen.py
AMQP_SPEC_JSON_FILES_0_8 = $(CODEGEN_DIR)/amqp-rabbitmq-0.8.json
AMQP_SPEC_JSON_FILES_0_9_1 = $(CODEGEN_DIR)/amqp-rabbitmq-0.9.1.json \
$(CODEGEN_DIR)/credit_extension.json
include/rabbit_framing.hrl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_9_1) $(AMQP_SPEC_JSON_FILES_0_8)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) --ignore-conflicts header \
$(AMQP_SPEC_JSON_FILES_0_9_1) $(AMQP_SPEC_JSON_FILES_0_8) $@
src/rabbit_framing_amqp_0_9_1.erl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_9_1)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) body $(AMQP_SPEC_JSON_FILES_0_9_1) $@
src/rabbit_framing_amqp_0_8.erl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_8)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) body $(AMQP_SPEC_JSON_FILES_0_8) $@
clean:: clean-extra-sources
clean-extra-sources:
$(gen_verbose) rm -f $(EXTRA_SOURCES)
-include development.post.mk

33
deps/rabbit_common/development.post.mk vendored Normal file
View File

@ -0,0 +1,33 @@
# --------------------------------------------------------------------
# Framing sources generation.
# --------------------------------------------------------------------
PYTHON ?= python
CODEGEN = $(CURDIR)/codegen.py
CODEGEN_DIR ?= $(DEPS_DIR)/rabbitmq_codegen
CODEGEN_AMQP = $(CODEGEN_DIR)/amqp_codegen.py
AMQP_SPEC_JSON_FILES_0_8 = $(CODEGEN_DIR)/amqp-rabbitmq-0.8.json
AMQP_SPEC_JSON_FILES_0_9_1 = $(CODEGEN_DIR)/amqp-rabbitmq-0.9.1.json \
$(CODEGEN_DIR)/credit_extension.json
include/rabbit_framing.hrl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_9_1) $(AMQP_SPEC_JSON_FILES_0_8)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) --ignore-conflicts header \
$(AMQP_SPEC_JSON_FILES_0_9_1) $(AMQP_SPEC_JSON_FILES_0_8) $@
src/rabbit_framing_amqp_0_9_1.erl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_9_1)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) body $(AMQP_SPEC_JSON_FILES_0_9_1) $@
src/rabbit_framing_amqp_0_8.erl:: $(CODEGEN) $(CODEGEN_AMQP) \
$(AMQP_SPEC_JSON_FILES_0_8)
$(gen_verbose) env PYTHONPATH=$(CODEGEN_DIR) \
$(PYTHON) $(CODEGEN) body $(AMQP_SPEC_JSON_FILES_0_8) $@
clean:: clean-extra-sources
clean-extra-sources:
$(gen_verbose) rm -f $(EXTRA_SOURCES)

14
deps/rabbit_common/development.pre.mk vendored Normal file
View File

@ -0,0 +1,14 @@
# Variables and recipes in development.*.mk are meant to be used from
# any Git clone. They are excluded from the files published to Hex.pm.
# Generated files are published to Hex.pm however so people using this
# source won't have to depend on Python and rabbitmq-codegen.
BUILD_DEPS = rabbitmq_codegen
TEST_DEPS = proper
EXTRA_SOURCES += include/rabbit_framing.hrl \
src/rabbit_framing_amqp_0_8.erl \
src/rabbit_framing_amqp_0_9_1.erl
.DEFAULT_GOAL = all
$(PROJECT).d:: $(EXTRA_SOURCES)

View File

@ -72,3 +72,53 @@ ifdef JENKINS_HOME
CT_OPTS += -ct_hooks cth_surefire
export RABBITMQ_CT_SKIP_AS_ERROR = true
endif
# --------------------------------------------------------------------
# Hex.pm.
# --------------------------------------------------------------------
.PHONY: hex-publish hex-publish-docs
HEXPM_URL = file:///home/dumbbell/Projects/pivotal/other-repos/hexpm-cli/hexpm
HEXPM_CLI = $(ERLANG_MK_TMP)/hexpm
$(HEXPM_CLI):
$(gen_verbose) $(call core_http_get,$@,$(HEXPM_URL))
$(verbose) chmod +x $@
rebar.config: dep_rabbit_common = hex $(PROJECT_VERSION)
rebar.config: dep_amqp_client = hex $(PROJECT_VERSION)
define RABBITMQ_HEXPM_DEFAULT_FILES
"erlang.mk",
"git-revisions.txt",
"include",
"LICENSE*",
"Makefile",
"rabbitmq-components.mk",
"README",
"README.md",
"src"
endef
hex-publish: $(HEXPM_CLI) app rebar.config
$(gen_verbose) echo "$(PROJECT_DESCRIPTION) $(PROJECT_VERSION)" \
> git-revisions.txt
ifneq ($(PROJECT),rabbit_common)
$(verbose) mv rabbitmq-components.mk rabbitmq-components.mk.not-hexpm
$(verbose) cp \
$(DEPS_DIR)/rabbit_common/mk/rabbitmq-components.hexpm.mk \
rabbitmq-components.mk
$(verbose) touch -r rabbitmq-components.mk.not-hexpm \
rabbitmq-components.mk
endif
$(verbose) trap '\
rm -f git-revisions.txt rebar.lock; \
if test -f rabbitmq-components.mk.not-hexpm; then \
mv rabbitmq-components.mk.not-hexpm rabbitmq-components.mk; \
fi' EXIT INT; \
$(HEXPM_CLI) publish
hex-publish-docs: $(HEXPM_CLI) app docs
$(gen_verbose) trap 'rm -f rebar.lock' EXIT INT; \
$(HEXPM_CLI) docs

View File

@ -0,0 +1,43 @@
ifeq ($(.DEFAULT_GOAL),)
# Define default goal to `all` because this file defines some targets
# before the inclusion of erlang.mk leading to the wrong target becoming
# the default.
.DEFAULT_GOAL = all
endif
# PROJECT_VERSION defaults to:
# 1. the version exported by rabbitmq-server-release;
# 2. the version stored in `git-revisions.txt`, if it exists;
# 3. a version based on git-describe(1), if it is a Git clone;
# 4. 0.0.0
PROJECT_VERSION := $(RABBITMQ_VERSION)
ifeq ($(PROJECT_VERSION),)
PROJECT_VERSION := $(shell \
if test -f git-revisions.txt; then \
head -n1 git-revisions.txt | \
awk '{print $$$(words $(PROJECT_DESCRIPTION) version);}'; \
else \
(git describe --dirty --abbrev=7 --tags --always --first-parent \
2>/dev/null || echo rabbitmq_v0_0_0) | \
sed -e 's/^rabbitmq_v//' -e 's/^v//' -e 's/_/./g' -e 's/-/+/' \
-e 's/-/./g'; \
fi)
endif
# --------------------------------------------------------------------
# RabbitMQ components.
# --------------------------------------------------------------------
dep_amqp_client = hex $(PROJECT_VERSION)
dep_rabbit_common = hex $(PROJECT_VERSION)
# Third-party dependencies version pinning.
#
# We do that in this file, which is copied in all projects, to ensure
# all projects use the same versions. It avoids conflicts and makes it
# possible to work with rabbitmq-public-umbrella.
dep_cowboy = hex 1.0.4
dep_ranch = hex 1.3.0