Skip to content

Commit

Permalink
chore: Add support for TLS tests to the contract test service. (#130)
Browse files Browse the repository at this point in the history
  • Loading branch information
kinyoklion authored May 30, 2024
1 parent c7c27b3 commit d746700
Show file tree
Hide file tree
Showing 5 changed files with 83 additions and 12 deletions.
5 changes: 3 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,13 @@ on:
jobs:
build-test:
strategy:
# We want to know the status of all OTP versions, not just if one of them fails.
fail-fast: false
matrix:
versions:
- {os: 'ubuntu-20.04', otp: '21.x', rebar: '3.15.2'}
- {os: 'ubuntu-22.04', otp: '24.x', rebar: '3.18.0'}
- {os: 'ubuntu-22.04', otp: '25.x', rebar: '3.18.0'}
- {os: 'ubuntu-22.04', otp: '26.x', rebar: '3.22.0'}
- {os: 'ubuntu-22.04', otp: '27.x', rebar: '3.23.0'}

runs-on: ${{ matrix.versions.os }}
name: Build and Test - ${{ matrix.versions.otp }}
Expand Down
5 changes: 3 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
REBAR3 = rebar3
ERL_VERSION = `erl -eval 'io:fwrite("~s~n", [erlang:system_info(otp_release)]), halt().' -noshell`

all:
@$(REBAR3) do clean, compile, ct, dialyzer
Expand Down Expand Up @@ -46,8 +47,8 @@ build-contract-tests:
@mkdir -p test-service/_checkouts
@rm -f $(CURDIR)/test-service/_checkouts/ldclient
@ln -sf $(CURDIR)/ $(CURDIR)/test-service/_checkouts/ldclient
@if [ "$(OTP_VER)" = "26.x" ]; then\
echo Dialyze for OTP 26;\
@if [ "$(ERL_VERSION)" -ge "26" ]; then\
echo Dialyze for OTP 26+;\
cd test-service && $(REBAR3) as otp26 dialyzer;\
else\
cd test-service && $(REBAR3) dialyzer;\
Expand Down
8 changes: 4 additions & 4 deletions test-service/rebar.config
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
{erl_opts, [debug_info]}.
{deps, [
{shotgun, "0.5.0"},
{shotgun, "1.0.1"},
{jsx, "3.1.0"},
{verl, "1.0.1"},
{lru, "2.4.0"},
{backoff, "1.1.6"},
{uuid, "2.0.2", {pkg, uuid_erl}},
{eredis, "1.4.0"},
{yamerl, "0.8.1"},
{certifi, "2.8.0"},
{eredis, "1.7.1"},
{yamerl, "0.10.0"},
{certifi, "2.12.0"},
{cowboy, "2.8.0"},
ldclient
]}.
Expand Down
72 changes: 69 additions & 3 deletions test-service/src/ts_sdk_config_params.erl
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,8 @@
streaming => sdk_config_streaming_params(),
polling => sdk_config_polling_params(),
events => sdk_config_event_params(),
tags => sdk_config_tags_params()
tags => sdk_config_tags_params(),
tls => sdk_config_tls_params() | undefined
}.

-type sdk_config_streaming_params() :: #{
Expand All @@ -47,10 +48,16 @@
application_version => binary() | undefined
}.

-type sdk_config_tls_params() :: #{
skip_verify_peer => boolean(),
custom_ca_file => binary() | undefined
}.

-export_type([sdk_config_params/0]).
-export_type([sdk_config_streaming_params/0]).
-export_type([sdk_config_event_params/0]).
-export_type([sdk_config_tags_params/0]).
-export_type([sdk_config_tls_params/0]).

-spec null_to_undefined(Item :: any()) -> any().
null_to_undefined(null) -> undefined;
Expand All @@ -68,14 +75,16 @@ parse_config_params(Params) ->
Polling = parse_config_polling_params(Params),
Events = parse_config_events_params(Params),
Tags = parse_config_tag_params(Params),
Tls = parse_config_tls_params(Params),
#{
credential => Credential,
start_wait_time_ms => StartWaitTimeMS,
init_can_fail => InitCanFail,
streaming => Streaming,
events => Events,
tags => Tags,
polling => Polling
polling => Polling,
tls => Tls
}.

-spec parse_config_tag_params(Params :: map()) -> sdk_config_tags_params().
Expand Down Expand Up @@ -135,6 +144,16 @@ parse_config_events_params(_Params) ->
flush_interval_ms => undefined
}.

parse_config_tls_params(#{<<"tls">> := TlsParams} = _Params) when is_map(TlsParams) ->
SkipVerifyPeer = map_get_null_default(<<"skipVerifyPeer">>, TlsParams, false),
CustomCAFile = map_get_null_default(<<"customCAFile">>, TlsParams, undefined),
#{
skip_verify_peer => SkipVerifyPeer,
custom_ca_file => CustomCAFile
};
parse_config_tls_params(_Params) ->
undefined.

-spec to_ldclient_options(Configuration :: sdk_config_params()) -> map().
to_ldclient_options(Configuration) ->
WithEventsUri = add_events_uri(Configuration, #{}),
Expand All @@ -146,7 +165,8 @@ to_ldclient_options(Configuration) ->
WithTags = add_tags_config(Configuration, WithStreamRetryDelay),
WithPollingUri = add_polling_uri(Configuration, WithTags),
WithPollingInterval = add_poll_interval(Configuration, WithPollingUri),
WithPollingInterval.
WithTlsConfig = add_tls_config(Configuration, WithPollingInterval),
WithTlsConfig.

-spec add_stream_retry_delay(Configuration :: sdk_config_params(), Options:: map()) -> map().
add_stream_retry_delay(#{streaming := #{
Expand Down Expand Up @@ -234,3 +254,49 @@ add_tag_application_version(_, Options) -> Options.

application_or_empty(#{application := Application} = _Options) -> Application;
application_or_empty(_Options) -> #{}.

basic_tls_options(Options) ->
Options#{
http_options => #{
tls_options => ldclient_config:tls_basic_options()
}
}.

%% When using OTP >= 26 the TLS configuration defaults to using verify_peer.
%% Before OTP 26 we must define our own options to pass the secure defaults.
-if(?OTP_RELEASE >= 26).
-define(BASIC_OPTIONS(X), X).
-else.
-define(BASIC_OPTIONS(X), basic_tls_options(X)).
-endif.

add_tls_config(#{tls := undefined} = _Configuration, Options) ->
?BASIC_OPTIONS(Options);
add_tls_config(#{tls := TlsOptions} = _Configuration, Options) ->
WithBasicTls = basic_tls_options(Options),
WithSkipVerifyPeer = add_skip_verify_peer(TlsOptions, WithBasicTls),
add_custom_ca(TlsOptions, WithSkipVerifyPeer).

skip_verify_peer_to_option(true) -> verify_none;
skip_verify_peer_to_option(false) -> verify_peer.

add_skip_verify_peer(#{
skip_verify_peer := SkipVerifyPeer
} = _TlsConfiguration, #{http_options := HttpOptions} = Options) ->
TlsOptions = maps:get(tls_options, HttpOptions, []),
Options#{
http_options => HttpOptions#{
tls_options => [{verify, skip_verify_peer_to_option(SkipVerifyPeer)} | proplists:delete(verify, TlsOptions)]
}
}.

add_custom_ca(#{custom_ca_file := undefined} = _TlsConfiguration, Options) ->
Options;
add_custom_ca(#{custom_ca_file := CaCertFile} = _TlsConfiguration, #{http_options := HttpOptions} = Options) ->
TlsOptions = maps:get(tls_options, HttpOptions, []),
Options#{
http_options => HttpOptions#{
%% Remove cacerts and/or cacertfile from the options and then specify the cert file.
tls_options => [{cacertfile, CaCertFile} | proplists:delete(cacerts, proplists:delete(cacertfile, TlsOptions))]
}
}.
5 changes: 4 additions & 1 deletion test-service/src/ts_service_request_handler.erl
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,10 @@ get_service_detail(Req, State) ->
<<"server-side-polling">>,
<<"user-type">>,
<<"inline-context">>,
<<"anonymous-redaction">>
<<"anonymous-redaction">>,
<<"tls:custom-ca">>,
<<"tls:skip-verify-peer">>,
<<"tls:verify-peer">>
],
<<"clientVersion">> => ldclient_config:get_version()
}),
Expand Down

0 comments on commit d746700

Please sign in to comment.