Merge pull request #11417 from thalesmg/release-v515-patch1-20230809

prepare `v5.1.5-patch.1`
This commit is contained in:
Thales Macedo Garitezi 2023-08-09 15:45:37 -03:00 committed by GitHub
commit fec38c2165
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
17 changed files with 259 additions and 149 deletions

View File

@ -23,7 +23,6 @@ jobs:
container: 'ghcr.io/emqx/emqx-builder/5.1-3:1.14.5-25.3.2-1-ubuntu22.04' container: 'ghcr.io/emqx/emqx-builder/5.1-3:1.14.5-25.3.2-1-ubuntu22.04'
outputs: outputs:
profile: ${{ steps.parse-git-ref.outputs.profile }} profile: ${{ steps.parse-git-ref.outputs.profile }}
edition: ${{ steps.parse-git-ref.outputs.edition }}
release: ${{ steps.parse-git-ref.outputs.release }} release: ${{ steps.parse-git-ref.outputs.release }}
latest: ${{ steps.parse-git-ref.outputs.latest }} latest: ${{ steps.parse-git-ref.outputs.latest }}
version: ${{ steps.parse-git-ref.outputs.version }} version: ${{ steps.parse-git-ref.outputs.version }}
@ -50,12 +49,10 @@ jobs:
run: | run: |
JSON="$(./scripts/parse-git-ref.sh $GITHUB_REF)" JSON="$(./scripts/parse-git-ref.sh $GITHUB_REF)"
PROFILE=$(echo "$JSON" | jq -cr '.profile') PROFILE=$(echo "$JSON" | jq -cr '.profile')
EDITION=$(echo "$JSON" | jq -cr '.edition')
RELEASE=$(echo "$JSON" | jq -cr '.release') RELEASE=$(echo "$JSON" | jq -cr '.release')
LATEST=$(echo "$JSON" | jq -cr '.latest') LATEST=$(echo "$JSON" | jq -cr '.latest')
VERSION="$(./pkg-vsn.sh "$PROFILE")" VERSION="$(./pkg-vsn.sh "$PROFILE")"
echo "profile=$PROFILE" | tee -a $GITHUB_OUTPUT echo "profile=$PROFILE" | tee -a $GITHUB_OUTPUT
echo "edition=$EDITION" | tee -a $GITHUB_OUTPUT
echo "release=$RELEASE" | tee -a $GITHUB_OUTPUT echo "release=$RELEASE" | tee -a $GITHUB_OUTPUT
echo "latest=$LATEST" | tee -a $GITHUB_OUTPUT echo "latest=$LATEST" | tee -a $GITHUB_OUTPUT
echo "version=$VERSION" | tee -a $GITHUB_OUTPUT echo "version=$VERSION" | tee -a $GITHUB_OUTPUT
@ -107,8 +104,9 @@ jobs:
publish: ${{ needs.prepare.outputs.release }} publish: ${{ needs.prepare.outputs.release }}
otp_vsn: ${{ needs.prepare.outputs.otp_vsn }} otp_vsn: ${{ needs.prepare.outputs.otp_vsn }}
elixir_vsn: ${{ needs.prepare.outputs.elixir_vsn }} elixir_vsn: ${{ needs.prepare.outputs.elixir_vsn }}
runner: ${{ needs.prepare.outputs.runner }}
builder_vsn: ${{ needs.prepare.outputs.builder_vsn }} builder_vsn: ${{ needs.prepare.outputs.builder_vsn }}
runner: ${{ needs.prepare.outputs.runner }}
secrets: inherit
build_and_push_docker_images: build_and_push_docker_images:
if: ${{ needs.prepare.outputs.release == 'true' }} if: ${{ needs.prepare.outputs.release == 'true' }}
@ -117,14 +115,14 @@ jobs:
uses: ./.github/workflows/build_and_push_docker_images.yaml uses: ./.github/workflows/build_and_push_docker_images.yaml
with: with:
profile: ${{ needs.prepare.outputs.profile }} profile: ${{ needs.prepare.outputs.profile }}
edition: ${{ needs.prepare.outputs.edition }}
version: ${{ needs.prepare.outputs.version }} version: ${{ needs.prepare.outputs.version }}
latest: ${{ needs.prepare.outputs.latest }}
publish: ${{ needs.prepare.outputs.release }} publish: ${{ needs.prepare.outputs.release }}
latest: ${{ needs.prepare.outputs.latest }}
otp_vsn: ${{ needs.prepare.outputs.otp_vsn }} otp_vsn: ${{ needs.prepare.outputs.otp_vsn }}
elixir_vsn: ${{ needs.prepare.outputs.elixir_vsn }} elixir_vsn: ${{ needs.prepare.outputs.elixir_vsn }}
runner: ${{ needs.prepare.outputs.runner }}
builder_vsn: ${{ needs.prepare.outputs.builder_vsn }} builder_vsn: ${{ needs.prepare.outputs.builder_vsn }}
runner: ${{ needs.prepare.outputs.runner }}
secrets: inherit
compile: compile:
runs-on: ${{ needs.prepare.outputs.runner }} runs-on: ${{ needs.prepare.outputs.runner }}
@ -188,4 +186,3 @@ jobs:
runner: ${{ needs.prepare.outputs.runner }} runner: ${{ needs.prepare.outputs.runner }}
builder: ${{ needs.prepare.outputs.builder }} builder: ${{ needs.prepare.outputs.builder }}
ct-matrix: ${{ needs.prepare.outputs.ct-matrix }} ct-matrix: ${{ needs.prepare.outputs.ct-matrix }}

View File

@ -10,9 +10,6 @@ on:
profile: profile:
required: true required: true
type: string type: string
edition:
required: true
type: string
version: version:
required: true required: true
type: string type: string
@ -28,27 +25,31 @@ on:
elixir_vsn: elixir_vsn:
required: true required: true
type: string type: string
runner:
required: true
type: string
builder_vsn: builder_vsn:
required: true required: true
type: string type: string
runner:
required: true
type: string
secrets:
DOCKER_HUB_USER:
required: true
DOCKER_HUB_TOKEN:
required: true
AWS_ACCESS_KEY_ID:
required: true
AWS_SECRET_ACCESS_KEY:
required: true
workflow_dispatch: workflow_dispatch:
inputs: inputs:
ref: ref:
required: false required: false
version:
required: true
type: string
profile: profile:
required: false required: false
type: string type: string
default: 'emqx' default: 'emqx'
edition: version:
required: false required: true
type: string
default: 'Opensource'
latest: latest:
required: false required: false
type: boolean type: boolean
@ -65,14 +66,14 @@ on:
required: false required: false
type: string type: string
default: '1.14.5' default: '1.14.5'
runner:
required: false
type: string
default: 'ubuntu-22.04'
builder_vsn: builder_vsn:
required: false required: false
type: string type: string
default: '5.1-3' default: '5.1-3'
runner:
required: false
type: string
default: 'ubuntu-22.04'
jobs: jobs:
docker: docker:
@ -83,18 +84,10 @@ jobs:
matrix: matrix:
profile: profile:
- ${{ inputs.profile }} - ${{ inputs.profile }}
- ${{ inputs.profile }}-elixir
registry: registry:
- 'docker.io' - 'docker.io'
- 'public.ecr.aws' - 'public.ecr.aws'
os:
- [debian11, "debian:11-slim", "deploy/docker/Dockerfile"]
builder:
- ${{ inputs.builder_vsn }}
otp:
- ${{ inputs.otp_vsn }}
elixir:
- 'no_elixir'
- ${{ inputs.elixir_vsn }}
steps: steps:
- uses: actions/checkout@v3 - uses: actions/checkout@v3
@ -121,53 +114,20 @@ jobs:
password: ${{ secrets.AWS_SECRET_ACCESS_KEY }} password: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
ecr: true ecr: true
- name: prepare for docker/metadata-action - name: Build docker image
id: pre-meta env:
shell: bash PROFILE: ${{ matrix.profile }}
DOCKER_REGISTRY: ${{ matrix.registry }}
DOCKER_ORG: ${{ github.repository_owner }}
DOCKER_LATEST: ${{ inputs.latest }}
DOCKER_PUSH: ${{ inputs.publish == 'true' || inputs.publish || github.repository_owner != 'emqx' }}
DOCKER_BUILD_NOCACHE: true
DOCKER_PLATFORMS: linux/amd64,linux/arm64
EMQX_RUNNER: 'debian:11-slim'
EMQX_DOCKERFILE: 'deploy/docker/Dockerfile'
PKG_VSN: ${{ inputs.version }}
EMQX_BUILDER_VSN: ${{ inputs.builder_vsn }}
EMQX_OTP_VSN: ${{ inputs.otp_vsn }}
EMQX_ELIXIR_VSN: ${{ inputs.elixir_vsn }}
run: | run: |
extra_labels= ./build ${PROFILE} docker
img_suffix=
if [ "${{ matrix.elixir }}" != 'no_elixir' ]; then
img_suffix="-elixir"
extra_labels="org.opencontainers.image.elixir.version=${{ matrix.elixir }}"
fi
extra_deps=
if [[ "${{ matrix.profile }}" = *enterprise* ]]; then
extra_deps='libsasl2-2,libsasl2-modules-gssapi-mit'
fi
echo "img_suffix=$img_suffix" >> $GITHUB_OUTPUT
echo "extra_labels=$extra_labels" >> $GITHUB_OUTPUT
echo "extra_deps=$extra_deps" >> $GITHUB_OUTPUT
- uses: docker/metadata-action@v4
id: meta
with:
images: |
${{ matrix.registry }}/${{ github.repository_owner }}/${{ matrix.profile }}
flavor: |
latest=${{ matrix.elixir == 'no_elixir' }}
suffix=${{ steps.pre-meta.outputs.img_suffix }}
tags: |
type=semver,pattern={{major}}.{{minor}},value=${{ inputs.version }}
type=semver,pattern={{version}},value=${{ inputs.version }}
type=raw,value=${{ inputs.version }}
type=raw,value=latest,enable=${{ inputs.latest }}
labels: |
org.opencontainers.image.otp.version=${{ matrix.otp }}
org.opencontainers.image.edition=${{ inputs.edition }}
${{ steps.pre-meta.outputs.extra_labels }}
- uses: docker/build-push-action@v3
with:
push: ${{ inputs.publish == 'true' || github.repository_owner != 'emqx' }}
pull: true
no-cache: true
platforms: linux/amd64,linux/arm64
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
build-args: |
EMQX_NAME=${{ matrix.profile }}${{ steps.pre-meta.outputs.img_suffix }}
EXTRA_DEPS=${{ steps.pre-meta.outputs.extra_deps }}
file: source/${{ matrix.os[2] }}

View File

@ -25,6 +25,25 @@ on:
builder_vsn: builder_vsn:
required: true required: true
type: string type: string
secrets:
AWS_ACCESS_KEY_ID:
required: true
AWS_SECRET_ACCESS_KEY:
required: true
AWS_DEFAULT_REGION:
required: true
AWS_S3_BUCKET:
required: true
AWS_CLOUDFRONT_ID:
required: true
APPLE_ID_PASSWORD:
required: true
APPLE_DEVELOPER_IDENTITY:
required: true
APPLE_DEVELOPER_ID_BUNDLE:
required: true
APPLE_DEVELOPER_ID_BUNDLE_PASSWORD:
required: true
workflow_dispatch: workflow_dispatch:
inputs: inputs:
ref: ref:
@ -249,7 +268,7 @@ jobs:
needs: needs:
- mac - mac
- linux - linux
if: ${{ inputs.publish == 'true' }} if: inputs.publish == 'true' || inputs.publish
strategy: strategy:
fail-fast: false fail-fast: false
matrix: matrix:
@ -261,7 +280,7 @@ jobs:
name: ${{ matrix.profile }} name: ${{ matrix.profile }}
path: packages/${{ matrix.profile }} path: packages/${{ matrix.profile }}
- name: install dos2unix - name: install dos2unix
run: sudo apt-get update && sudo apt install -y dos2unix run: apt-get update && apt install -y dos2unix
- name: get packages - name: get packages
run: | run: |
set -eu set -eu

View File

@ -32,7 +32,7 @@
%% `apps/emqx/src/bpapi/README.md' %% `apps/emqx/src/bpapi/README.md'
%% Opensource edition %% Opensource edition
-define(EMQX_RELEASE_CE, "5.1.5"). -define(EMQX_RELEASE_CE, "5.1.5-patch.1").
%% Enterprise edition %% Enterprise edition
-define(EMQX_RELEASE_EE, "5.1.1"). -define(EMQX_RELEASE_EE, "5.1.1").

View File

@ -158,9 +158,9 @@ offset_second_(Offset) when is_list(Offset) ->
_ -> _ ->
error({bad_time_offset, Offset}) error({bad_time_offset, Offset})
end, end,
Hour = list_to_int_or_error(HourStr, {bad_time_offset_hour, HourStr}), Hour = str_to_int_or_error(HourStr, {bad_time_offset_hour, HourStr}),
Minute = list_to_int_or_error(MinuteStr, {bad_time_offset_minute, MinuteStr}), Minute = str_to_int_or_error(MinuteStr, {bad_time_offset_minute, MinuteStr}),
Second = list_to_int_or_error(SecondStr, {bad_time_offset_second, SecondStr}), Second = str_to_int_or_error(SecondStr, {bad_time_offset_second, SecondStr}),
(Hour =< 23) orelse error({bad_time_offset_hour, Hour}), (Hour =< 23) orelse error({bad_time_offset_hour, Hour}),
(Minute =< 59) orelse error({bad_time_offset_minute, Minute}), (Minute =< 59) orelse error({bad_time_offset_minute, Minute}),
(Second =< 59) orelse error({bad_time_offset_second, Second}), (Second =< 59) orelse error({bad_time_offset_second, Second}),
@ -417,7 +417,11 @@ do_parse_date_str(Date, [Key | Formatter], Result) ->
<<DatePart:Size/binary-unit:8, Tail/binary>> = Date, <<DatePart:Size/binary-unit:8, Tail/binary>> = Date,
case lists:member(Key, ?DATE_PART) of case lists:member(Key, ?DATE_PART) of
true -> true ->
do_parse_date_str(Tail, Formatter, Result#{Key => erlang:binary_to_integer(DatePart)}); %% Note: Here is a fix to make the error reason more sense
%% when the format or date can't be matched,
%% but the root reason comment underneath at <ROOT>
PartValue = str_to_int_or_error(DatePart, bad_formatter_or_date),
do_parse_date_str(Tail, Formatter, Result#{Key => PartValue});
false -> false ->
case lists:member(Key, ?DATE_ZONE_NAME) of case lists:member(Key, ?DATE_ZONE_NAME) of
true -> true ->
@ -425,6 +429,13 @@ do_parse_date_str(Date, [Key | Formatter], Result) ->
parsed_offset => offset_second(DatePart) parsed_offset => offset_second(DatePart)
}); });
false -> false ->
%% <ROOT>
%% Here should have compared the date part with the key,
%% but for compatibility, we can't fix it here
%% e.g.
%% date_to_unix_ts('second','%Y-%m-%d %H-%M-%S', '2022-05-26 10:40:12')
%% this is valid in 4.x, but actually '%H-%M-%S' can't match with '10:40:12'
%% We cannot ensure whether there are more exceptions in the user's rule
do_parse_date_str(Tail, Formatter, Result) do_parse_date_str(Tail, Formatter, Result)
end end
end. end.
@ -456,10 +467,12 @@ dm(10) -> 273;
dm(11) -> 304; dm(11) -> 304;
dm(12) -> 334. dm(12) -> 334.
list_to_int_or_error(Str, Error) -> str_to_int_or_error(Str, Error) ->
case string:to_integer(Str) of case string:to_integer(Str) of
{Int, []} -> {Int, []} ->
Int; Int;
{Int, <<>>} ->
Int;
_ -> _ ->
error(Error) error(Error)
end. end.

View File

@ -54,10 +54,11 @@ fields(config) ->
{pool_size, fun ?ECS:pool_size/1}, {pool_size, fun ?ECS:pool_size/1},
{username, fun ensure_username/1}, {username, fun ensure_username/1},
{password, fun ?ECS:password/1}, {password, fun ?ECS:password/1},
{base_object, {base_dn,
?HOCON(binary(), #{ ?HOCON(binary(), #{
desc => ?DESC(base_object), desc => ?DESC(base_dn),
required => true, required => true,
example => <<"uid=${username},ou=testdevice,dc=emqx,dc=io">>,
validator => fun emqx_schema:non_empty_string/1 validator => fun emqx_schema:non_empty_string/1
})}, })},
{filter, {filter,
@ -66,6 +67,7 @@ fields(config) ->
#{ #{
desc => ?DESC(filter), desc => ?DESC(filter),
default => <<"(objectClass=mqttUser)">>, default => <<"(objectClass=mqttUser)">>,
example => <<"(& (objectClass=mqttUser) (uid=${username}))">>,
validator => fun emqx_schema:non_empty_string/1 validator => fun emqx_schema:non_empty_string/1
} }
)} )}
@ -229,9 +231,9 @@ log(Level, Format, Args) ->
). ).
prepare_template(Config, State) -> prepare_template(Config, State) ->
do_prepare_template(maps:to_list(maps:with([base_object, filter], Config)), State). do_prepare_template(maps:to_list(maps:with([base_dn, filter], Config)), State).
do_prepare_template([{base_object, V} | T], State) -> do_prepare_template([{base_dn, V} | T], State) ->
do_prepare_template(T, State#{base_tokens => emqx_placeholder:preproc_tmpl(V)}); do_prepare_template(T, State#{base_tokens => emqx_placeholder:preproc_tmpl(V)});
do_prepare_template([{filter, V} | T], State) -> do_prepare_template([{filter, V} | T], State) ->
do_prepare_template(T, State#{filter_tokens => emqx_placeholder:preproc_tmpl(V)}); do_prepare_template(T, State#{filter_tokens => emqx_placeholder:preproc_tmpl(V)});

View File

@ -154,7 +154,7 @@ ldap_config(Config) ->
" password = public\n" " password = public\n"
" pool_size = 8\n" " pool_size = 8\n"
" server = \"~s:~b\"\n" " server = \"~s:~b\"\n"
" base_object=\"uid=${username},ou=testdevice,dc=emqx,dc=io\"\n" " base_dn=\"uid=${username},ou=testdevice,dc=emqx,dc=io\"\n"
" filter =\"(objectClass=mqttUser)\"\n" " filter =\"(objectClass=mqttUser)\"\n"
" ~ts\n" " ~ts\n"
"", "",

View File

@ -167,7 +167,7 @@ t_update(_Config) ->
CorrectConfig = raw_ldap_auth_config(), CorrectConfig = raw_ldap_auth_config(),
IncorrectConfig = IncorrectConfig =
CorrectConfig#{ CorrectConfig#{
<<"base_object">> => <<"ou=testdevice,dc=emqx,dc=io">> <<"base_dn">> => <<"ou=testdevice,dc=emqx,dc=io">>
}, },
{ok, _} = emqx:update_config( {ok, _} = emqx:update_config(
@ -208,7 +208,7 @@ raw_ldap_auth_config() ->
<<"mechanism">> => <<"password_based">>, <<"mechanism">> => <<"password_based">>,
<<"backend">> => <<"ldap">>, <<"backend">> => <<"ldap">>,
<<"server">> => ldap_server(), <<"server">> => ldap_server(),
<<"base_object">> => <<"uid=${username},ou=testdevice,dc=emqx,dc=io">>, <<"base_dn">> => <<"uid=${username},ou=testdevice,dc=emqx,dc=io">>,
<<"username">> => <<"cn=root,dc=emqx,dc=io">>, <<"username">> => <<"cn=root,dc=emqx,dc=io">>,
<<"password">> => <<"public">>, <<"password">> => <<"public">>,
<<"pool_size">> => 8 <<"pool_size">> => 8

View File

@ -138,7 +138,7 @@ raw_ldap_authz_config() ->
<<"enable">> => <<"true">>, <<"enable">> => <<"true">>,
<<"type">> => <<"ldap">>, <<"type">> => <<"ldap">>,
<<"server">> => ldap_server(), <<"server">> => ldap_server(),
<<"base_object">> => <<"uid=${username},ou=testdevice,dc=emqx,dc=io">>, <<"base_dn">> => <<"uid=${username},ou=testdevice,dc=emqx,dc=io">>,
<<"username">> => <<"cn=root,dc=emqx,dc=io">>, <<"username">> => <<"cn=root,dc=emqx,dc=io">>,
<<"password">> => <<"public">>, <<"password">> => <<"public">>,
<<"pool_size">> => 8 <<"pool_size">> => 8

View File

@ -1031,6 +1031,35 @@ timezone_to_offset_seconds_helper(FunctionName) ->
apply_func(FunctionName, [local]), apply_func(FunctionName, [local]),
ok. ok.
t_parse_date_errors(_) ->
?assertError(
bad_formatter_or_date,
emqx_rule_funcs:date_to_unix_ts(
second, <<"%Y-%m-%d %H:%M:%S">>, <<"2022-059999-26 10:40:12">>
)
),
?assertError(
bad_formatter_or_date,
emqx_rule_funcs:date_to_unix_ts(second, <<"%y-%m-%d %H:%M:%S">>, <<"2022-05-26 10:40:12">>)
),
%% Compatibility test
UnixTs = 1653561612,
?assertEqual(
UnixTs,
emqx_rule_funcs:date_to_unix_ts(second, <<"%Y-%m-%d %H:%M:%S">>, <<"2022-05-26 10:40:12">>)
),
?assertEqual(
UnixTs,
emqx_rule_funcs:date_to_unix_ts(second, <<"%Y-%m-%d %H-%M-%S">>, <<"2022-05-26 10:40:12">>)
),
?assertEqual(
UnixTs,
emqx_rule_funcs:date_to_unix_ts(second, <<"%Y-%m-%d %H:%M:%S">>, <<"2022-05-26 10-40-12">>)
).
%%------------------------------------------------------------------------------ %%------------------------------------------------------------------------------
%% Utility functions %% Utility functions
%%------------------------------------------------------------------------------ %%------------------------------------------------------------------------------

94
build
View File

@ -368,21 +368,87 @@ docker_cleanup() {
} }
## Build the default docker image based on debian 11. ## Build the default docker image based on debian 11.
## NOTE: docker image build in github action does not call this
## function, see build_and_push_docker_images.yaml
make_docker() { make_docker() {
EMQX_BUILDER="${EMQX_BUILDER:-${EMQX_DEFAULT_BUILDER}}" local EMQX_BUILDER_VERSION="${EMQX_BUILDER_VERSION:-5.1-3}"
EMQX_RUNNER="${EMQX_RUNNER:-${EMQX_DEFAULT_RUNNER}}" local EMQX_BUILDER_PLATFORM="${EMQX_BUILDER_PLATFORM:-debian11}"
EMQX_DOCKERFILE="${EMQX_DOCKERFILE:-deploy/docker/Dockerfile}" local EMQX_BUILDER_OTP="${EMQX_BUILDER_OTP:-25.3.2-1}"
local EMQX_BUILDER_ELIXIR="${EMQX_BUILDER_ELIXIR:-1.14.5}"
local EMQX_BUILDER=${EMQX_BUILDER:-ghcr.io/emqx/emqx-builder/${EMQX_BUILDER_VERSION}:${EMQX_BUILDER_ELIXIR}-${EMQX_BUILDER_OTP}-${EMQX_BUILDER_PLATFORM}}
local EMQX_RUNNER="${EMQX_RUNNER:-${EMQX_DEFAULT_RUNNER}}"
local EMQX_DOCKERFILE="${EMQX_DOCKERFILE:-deploy/docker/Dockerfile}"
local PKG_VSN="${PKG_VSN:-$(./pkg-vsn.sh)}"
# shellcheck disable=SC2155
local VSN_MAJOR="$(echo "$PKG_VSN" | cut -d . -f 1)"
# shellcheck disable=SC2155
local VSN_MINOR="$(echo "$PKG_VSN" | cut -d . -f 2)"
# shellcheck disable=SC2155
local VSN_PATCH="$(echo "$PKG_VSN" | cut -d . -f 3)"
local SUFFIX=''
if [[ "$PROFILE" = *-elixir ]]; then if [[ "$PROFILE" = *-elixir ]]; then
PKG_VSN="$PKG_VSN-elixir" SUFFIX="-elixir"
fi fi
local default_tag="emqx/${PROFILE%%-elixir}:${PKG_VSN}" local DOCKER_REGISTRY="${REGISTRY:-docker.io}"
EMQX_IMAGE_TAG="${EMQX_IMAGE_TAG:-$default_tag}" local DOCKER_ORG="${DOCKER_ORG:-emqx}"
local EMQX_BASE_DOCKER_TAG="${DOCKER_REGISTRY}/${DOCKER_ORG}/${PROFILE%%-elixir}"
local default_tag="${EMQX_BASE_DOCKER_TAG}:${PKG_VSN}${SUFFIX}"
local EMQX_IMAGE_TAG="${EMQX_IMAGE_TAG:-$default_tag}"
local EDITION=Opensource
local LICENSE='Apache-2.0'
local PRODUCT_URL='https://www.emqx.io'
local PRODUCT_DESCRIPTION='Official docker image for EMQX, the most scalable open-source MQTT broker for IoT, IIoT, and connected vehicles.'
local DOCUMENTATION_URL='https://www.emqx.io/docs/en/latest/'
## extra_deps is a comma separated list of debian 11 package names ## extra_deps is a comma separated list of debian 11 package names
local extra_deps='' local EXTRA_DEPS=''
if [[ "$PROFILE" = *enterprise* ]]; then if [[ "$PROFILE" = *enterprise* ]]; then
extra_deps='libsasl2-2,libsasl2-modules-gssapi-mit' EXTRA_DEPS='libsasl2-2,libsasl2-modules-gssapi-mit'
EDITION=Enterprise
LICENSE='(Apache-2.0 AND BSL-1.1)'
PRODUCT_URL='https://www.emqx.com/en/products/emqx'
PRODUCT_DESCRIPTION='Official docker image for EMQX Enterprise, an enterprise MQTT platform at scale. '
DOCUMENTATION_URL='https://docs.emqx.com/en/enterprise/latest/'
fi
# shellcheck disable=SC2155
local ISO_8601_DATE="$(date -u +"%Y-%m-%dT%H:%M:%SZ")"
# shellcheck disable=SC2155
local GIT_REVISION="$(git rev-parse HEAD)"
local DOCKER_BUILDX_ARGS=(
--build-arg BUILD_FROM="${EMQX_BUILDER}" \
--build-arg RUN_FROM="${EMQX_RUNNER}" \
--build-arg EMQX_NAME="${PROFILE}" \
--build-arg EXTRA_DEPS="${EXTRA_DEPS}" \
--build-arg PKG_VSN="${PKG_VSN}" \
--file "${EMQX_DOCKERFILE}" \
--label org.opencontainers.image.title="${PROFILE}" \
--label org.opencontainers.image.edition="${EDITION}" \
--label org.opencontainers.image.version="${PKG_VSN}" \
--label org.opencontainers.image.revision="${GIT_REVISION}" \
--label org.opencontainers.image.created="${ISO_8601_DATE}" \
--label org.opencontainers.image.source='https://github.com/emqx/emqx' \
--label org.opencontainers.image.url="${PRODUCT_URL}" \
--label org.opencontainers.image.description="${PRODUCT_DESCRIPTION}" \
--label org.opencontainers.image.documentation="${DOCUMENTATION_URL}" \
--label org.opencontainers.image.licenses="${LICENSE}" \
--label org.opencontainers.image.otp.version="${EMQX_BUILDER_OTP}" \
--tag "${EMQX_IMAGE_TAG}" \
--tag "${EMQX_BASE_DOCKER_TAG}:${VSN_MAJOR}.${VSN_MINOR}${SUFFIX}" \
--tag "${EMQX_BASE_DOCKER_TAG}:${VSN_MAJOR}.${VSN_MINOR}.${VSN_PATCH}${SUFFIX}" \
--provenance false \
--pull
)
if [ "${DOCKER_BUILD_NOCACHE:-false}" = true ]; then
DOCKER_BUILDX_ARGS+=(--no-cache)
fi
if [ "${SUFFIX}" = '-elixir' ]; then
DOCKER_BUILDX_ARGS+=(--label org.opencontainers.image.elixir.version="${EMQX_BUILDER_ELIXIR}")
fi
if [ "${DOCKER_LATEST:-false}" = true ]; then
DOCKER_BUILDX_ARGS+=(--tag "${DOCKER_REGISTRY}/${DOCKER_ORG}/${PROFILE}:latest${SUFFIX}")
fi
if [ "${DOCKER_PLATFORMS:-default}" != 'default' ]; then
DOCKER_BUILDX_ARGS+=(--platform "${DOCKER_PLATFORMS}")
fi
if [ "${DOCKER_PUSH:-false}" = true ]; then
DOCKER_BUILDX_ARGS+=(--push)
fi fi
# shellcheck disable=SC2015 # shellcheck disable=SC2015
[ -f ./.dockerignore ] && mv ./.dockerignore ./.dockerignore.bak || true [ -f ./.dockerignore ] && mv ./.dockerignore ./.dockerignore.bak || true
@ -393,13 +459,7 @@ make_docker() {
echo '/*.lock' echo '/*.lock'
} >> ./.dockerignore } >> ./.dockerignore
set -x set -x
docker build --no-cache --pull \ docker buildx build "${DOCKER_BUILDX_ARGS[@]}" .
--build-arg BUILD_FROM="${EMQX_BUILDER}" \
--build-arg RUN_FROM="${EMQX_RUNNER}" \
--build-arg EMQX_NAME="${PROFILE}" \
--build-arg EXTRA_DEPS="${extra_deps}" \
--tag "${EMQX_IMAGE_TAG}" \
-f "${EMQX_DOCKERFILE}" .
[[ "${DEBUG:-}" -eq 1 ]] || set +x [[ "${DEBUG:-}" -eq 1 ]] || set +x
echo "${EMQX_IMAGE_TAG}" > ./.docker_image_tag echo "${EMQX_IMAGE_TAG}" > ./.docker_image_tag
} }

View File

@ -0,0 +1 @@
Improve the error reason of the `date_to_unix_ts` to make more sense.

View File

@ -0,0 +1,26 @@
# v5.1.5-patch.1
## Enhancements
- [#10697](https://github.com/emqx/emqx/pull/10697) This change allows to set the minReadySeconds for the StatefulSet. This allows to add a gap between the restarts of each pod by upgrade or restart command.
- [#11390](https://github.com/emqx/emqx/pull/11390) Add `node.broker_pool_size`, `node.generic_pool_size`, `node.channel_cleanup_batch_size` options to EMQX configuration.
Tuning these options can significantly improve performance if cluster interconnect network latency is high.
- [#11389](https://github.com/emqx/emqx/pull/11389) Improved retained message publishing latency by consolidating multiple index update operations into a single mnesia activity, leveraging the new APIs introduced in mria 0.6.0.
- [#11405](https://github.com/emqx/emqx/pull/11405) Improve the error reason of the `date_to_unix_ts` to make more sense.
## Bug Fixes
- [#11388](https://github.com/emqx/emqx/pull/11388) Increase `emqx_router_sup` restart intensity.
The goal is to tolerate occasional crashes that can happen under relatively normal conditions
and don't seem critical to shutdown the whole app (emqx).
For example, mria write/delete call delegated from a replicant to a core node by `emqx_router_helper` may fail,
if the core node is being stopped / restarted / not ready.
- [#11410](https://github.com/emqx/emqx/pull/11410) Reintroduce `cacerts` TLS client option as a deprecated option.
This fixes issues found when trying to upgrade from 5.1.3 where that option is set in the configuration files or persisted in EMQX Operator settings.

View File

@ -5,6 +5,7 @@ FROM ${BUILD_FROM} AS builder
COPY . /emqx COPY . /emqx
ARG EMQX_NAME=emqx ARG EMQX_NAME=emqx
ARG PKG_VSN
ENV EMQX_RELUP=false ENV EMQX_RELUP=false
RUN export PROFILE=${EMQX_NAME%%-elixir} \ RUN export PROFILE=${EMQX_NAME%%-elixir} \

View File

@ -8,16 +8,17 @@ The LDAP default port 389 is used if `[:Port]` is not specified."""
server.label: server.label:
"""Server Host""" """Server Host"""
base_object.desc: base_dn.desc:
"""The name of the base object entry (or possibly the root) relative to """The name of the base object entry (or possibly the root) relative to
which the Search is to be performed.""" which the Search is to be performed."""
base_object.label: base_dn.label:
"""Base Object""" """Base DN"""
filter.desc: filter.desc:
"""The filter that defines the conditions that must be fulfilled in order """The filter that defines the conditions that must be fulfilled in order
for the Search to match a given entry.""" for the Search to match a given entry.<br>
The syntax of the filter follows RFC 4515 and also supports placeholders."""
filter.label: filter.label:
"""Filter""" """Filter"""

View File

@ -18,32 +18,26 @@ is_latest() {
if [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+$ ]]; then if [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+$ ]]; then
PROFILE=emqx PROFILE=emqx
EDITION=Opensource
RELEASE=true RELEASE=true
LATEST=$(is_latest "$1") LATEST=$(is_latest "$1")
elif [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then elif [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+-patch\.[0-9]+$ ]]; then
PROFILE=emqx PROFILE=emqx
EDITION=Opensource
RELEASE=true RELEASE=true
LATEST=$(is_latest "$1") LATEST=$(is_latest "$1")
elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+$ ]]; then elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+$ ]]; then
PROFILE=emqx-enterprise PROFILE=emqx-enterprise
EDITION=Enterprise
RELEASE=true RELEASE=true
LATEST=$(is_latest "$1") LATEST=$(is_latest "$1")
elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+-patch\.[0-9]+$ ]]; then
PROFILE=emqx-enterprise PROFILE=emqx-enterprise
EDITION=Enterprise
RELEASE=true RELEASE=true
LATEST=$(is_latest "$1") LATEST=$(is_latest "$1")
elif [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+-(alpha|beta|rc)\.[0-9]+$ ]]; then elif [[ $1 =~ ^refs/tags/v[5-9]+\.[0-9]+\.[0-9]+-(alpha|beta|rc)\.[0-9]+$ ]]; then
PROFILE=emqx PROFILE=emqx
EDITION=Opensource
RELEASE=true RELEASE=true
LATEST=false LATEST=false
elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+-(alpha|beta|rc)\.[0-9]+$ ]]; then elif [[ $1 =~ ^refs/tags/e[5-9]+\.[0-9]+\.[0-9]+-(alpha|beta|rc)\.[0-9]+$ ]]; then
PROFILE=emqx-enterprise PROFILE=emqx-enterprise
EDITION=Enterprise
RELEASE=true RELEASE=true
LATEST=false LATEST=false
elif [[ $1 =~ ^refs/tags/.+ ]]; then elif [[ $1 =~ ^refs/tags/.+ ]]; then
@ -51,17 +45,14 @@ elif [[ $1 =~ ^refs/tags/.+ ]]; then
exit 1 exit 1
elif [[ $1 =~ ^refs/heads/master$ ]]; then elif [[ $1 =~ ^refs/heads/master$ ]]; then
PROFILE=emqx PROFILE=emqx
EDITION=Opensource
RELEASE=false RELEASE=false
LATEST=false LATEST=false
elif [[ $1 =~ ^refs/heads/release-[5-9][0-9]+$ ]]; then elif [[ $1 =~ ^refs/heads/release-[5-9][0-9]+$ ]]; then
PROFILE=emqx-enterprise PROFILE=emqx-enterprise
EDITION=Enterprise
RELEASE=false RELEASE=false
LATEST=false LATEST=false
elif [[ $1 =~ ^refs/heads/ci/.* ]]; then elif [[ $1 =~ ^refs/heads/ci/.* ]]; then
PROFILE=emqx PROFILE=emqx
EDITION=Opensource
RELEASE=false RELEASE=false
LATEST=false LATEST=false
else else
@ -70,5 +61,5 @@ else
fi fi
cat <<EOF cat <<EOF
{"profile": "$PROFILE", "edition": "$EDITION", "release": $RELEASE, "latest": $LATEST} {"profile": "$PROFILE", "release": $RELEASE, "latest": $LATEST}
EOF EOF

View File

@ -8,19 +8,29 @@ Unrecognized tag: refs/tags/v5.2.0-foobar.1
Unrecognized git ref: v5.2.0 Unrecognized git ref: v5.2.0
>>>= 1 >>>= 1
./parse-git-ref.sh v5.2.0-1
>>>2
Unrecognized git ref: v5.2.0-1
>>>= 1
./parse-git-ref.sh e5.2.0-1
>>>2
Unrecognized git ref: e5.2.0-1
>>>= 1
./parse-git-ref.sh refs/tags/v5.1.0 ./parse-git-ref.sh refs/tags/v5.1.0
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": false} {"profile": "emqx", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/v5.1.5.1 ./parse-git-ref.sh refs/tags/v5.1.5-patch.1
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": false} {"profile": "emqx", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/v5.2.0-alpha.1 ./parse-git-ref.sh refs/tags/v5.2.0-alpha.1
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": false} {"profile": "emqx", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/v5.2.0-alpha-1 ./parse-git-ref.sh refs/tags/v5.2.0-alpha-1
@ -30,62 +40,62 @@ Unrecognized tag: refs/tags/v5.2.0-alpha-1
./parse-git-ref.sh refs/tags/v5.2.0-beta.1 ./parse-git-ref.sh refs/tags/v5.2.0-beta.1
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": false} {"profile": "emqx", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/v5.2.0-rc.1 ./parse-git-ref.sh refs/tags/v5.2.0-rc.1
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": false} {"profile": "emqx", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.1.0 ./parse-git-ref.sh refs/tags/e5.1.0
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": false} {"profile": "emqx-enterprise", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.1.5.1 ./parse-git-ref.sh refs/tags/e5.1.5-patch.1
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": false} {"profile": "emqx-enterprise", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.2.0-alpha.1 ./parse-git-ref.sh refs/tags/e5.2.0-alpha.1
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": false} {"profile": "emqx-enterprise", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.2.0-beta.1 ./parse-git-ref.sh refs/tags/e5.2.0-beta.1
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": false} {"profile": "emqx-enterprise", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.2.0-rc.1 ./parse-git-ref.sh refs/tags/e5.2.0-rc.1
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": false} {"profile": "emqx-enterprise", "release": true, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/e5.1.99 ./parse-git-ref.sh refs/tags/e5.1.99
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": true, "latest": true} {"profile": "emqx-enterprise", "release": true, "latest": true}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/tags/v5.1.99 ./parse-git-ref.sh refs/tags/v5.1.99
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": true, "latest": true} {"profile": "emqx", "release": true, "latest": true}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/heads/master ./parse-git-ref.sh refs/heads/master
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": false, "latest": false} {"profile": "emqx", "release": false, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/heads/release-51 ./parse-git-ref.sh refs/heads/release-51
>>> >>>
{"profile": "emqx-enterprise", "edition": "Enterprise", "release": false, "latest": false} {"profile": "emqx-enterprise", "release": false, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/heads/ci/foobar ./parse-git-ref.sh refs/heads/ci/foobar
>>> >>>
{"profile": "emqx", "edition": "Opensource", "release": false, "latest": false} {"profile": "emqx", "release": false, "latest": false}
>>>= 0 >>>= 0
./parse-git-ref.sh refs/heads/release-44 ./parse-git-ref.sh refs/heads/release-44