From 52afebed01d274721b822bdca8f8c219d6b4b4a8 Mon Sep 17 00:00:00 2001 From: Ruben Bartelink Date: Thu, 13 Feb 2020 17:59:29 +0000 Subject: [PATCH] Add TCP mode argument processing for ES templates (#46) --- CHANGELOG.md | 3 +++ equinox-testbed/Storage.fs | 6 +++-- propulsion-all-projector/Program.fs | 16 ++++++++++--- propulsion-summary-projector/Program.fs | 16 ++++++++++--- propulsion-sync/Program.fs | 32 ++++++++++++++++++++----- 5 files changed, 59 insertions(+), 14 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5731727bd..8a72b1082 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,6 +9,9 @@ The `Unreleased` section name is replaced by the expected version of next releas ## [Unreleased] ### Added + +- Add handling for `-T` TCP/IP switch on EventStore args [#46](https://github.com/jet/dotnet-templates/pulls/46) + ### Changed ### Removed ### Fixed diff --git a/equinox-testbed/Storage.fs b/equinox-testbed/Storage.fs index 554d61c17..b4ae79b2d 100644 --- a/equinox-testbed/Storage.fs +++ b/equinox-testbed/Storage.fs @@ -104,7 +104,8 @@ module EventStore = | [] VerboseStore | [] Timeout of float | [] Retries of int - | [] Host of string + | [] Tcp + | [] Host of string | [] Username of string | [] Password of string | [] ConcurrentOperationsLimit of int @@ -114,7 +115,8 @@ module EventStore = | VerboseStore -> "include low level Store logging." | Timeout _ -> "specify operation timeout in seconds. Default: 5." | Retries _ -> "specify operation retries. Default: 1." - | Host _ -> "specify a DNS query, using Gossip-driven discovery against all A records returned. Default: localhost." + | Tcp -> "Request connecting direct to a TCP/IP endpoint. Default: Use Clustered mode with Gossip-driven discovery (unless environment variable EQUINOX_ES_TCP specifies 'true')." + | Host _ -> "TCP mode: specify a hostname to connect to directly. Clustered mode: use Gossip protocol against all A records returned from DNS query. (optional if environment variable EQUINOX_ES_HOST specified)" | Username _ -> "specify a username. Default: admin." | Password _ -> "specify a Password. Default: changeit." | ConcurrentOperationsLimit _ -> "max concurrent operations in flight. Default: 5000." diff --git a/propulsion-all-projector/Program.fs b/propulsion-all-projector/Program.fs index 4ba1b948f..ac00863d3 100644 --- a/propulsion-all-projector/Program.fs +++ b/propulsion-all-projector/Program.fs @@ -119,6 +119,7 @@ module CmdParser = | [] Timeout of float | [] Retries of int | [] HeartbeatTimeout of float + | [] Tcp | [] Host of string | [] Port of int | [] Username of string @@ -138,8 +139,9 @@ module CmdParser = | Percent _ -> "EventStore $all Stream Position to commence from (as a percentage of current tail position)" | Verbose -> "Include low level Store logging." - | Host _ -> "specify a DNS query, using Gossip-driven discovery against all A records returned. (optional if environment variable EQUINOX_ES_HOST specified)" - | Port _ -> "specify a custom port. Defaults: envvar:EQUINOX_ES_PORT, 30778." + | Tcp -> "Request connecting direct to a TCP/IP endpoint. Default: Use Clustered mode with Gossip-driven discovery (unless environment variable EQUINOX_ES_TCP specifies 'true')." + | Host _ -> "TCP mode: specify a hostname to connect to directly. Clustered mode: use Gossip protocol against all A records returned from DNS query. (optional if environment variable EQUINOX_ES_HOST specified)" + | Port _ -> "specify a custom port. Uses value of environment variable EQUINOX_ES_PORT if specified. Defaults for Cluster and Direct TCP/IP mode are 30778 and 1113 respectively." | Username _ -> "specify a username. (optional if environment variable EQUINOX_ES_USERNAME specified)" | Password _ -> "specify a Password. (optional if environment variable EQUINOX_ES_PASSWORD specified)" | Timeout _ -> "specify operation timeout in seconds. Default: 20." @@ -161,7 +163,15 @@ module CmdParser = | None, None, None, true -> StartPos.TailOrCheckpoint | None, None, None, _ -> StartPos.StartOrCheckpoint - member __.Discovery = match __.Port with Some p -> Discovery.GossipDnsCustomPort (__.Host, p) | None -> Discovery.GossipDns __.Host + member __.Discovery = + match __.Tcp, __.Port with + | false, None -> Discovery.GossipDns __.Host + | false, Some p -> Discovery.GossipDnsCustomPort (__.Host, p) + | true, None -> Discovery.Uri (UriBuilder("tcp", __.Host).Uri) + | true, Some p -> Discovery.Uri (UriBuilder("tcp", __.Host, p).Uri) + member __.Tcp = + a.Contains EsSourceParameters.Tcp + || EnvVar.tryGet "EQUINOX_ES_TCP" |> Option.exists (fun s -> String.Equals(s, bool.TrueString, StringComparison.OrdinalIgnoreCase)) member __.Port = match a.TryGetResult Port with Some x -> Some x | None -> EnvVar.tryGet "EQUINOX_ES_PORT" |> Option.map int member __.Host = a.TryGetResult Host |> defaultWithEnvVar "EQUINOX_ES_HOST" "Host" member __.User = a.TryGetResult Username |> defaultWithEnvVar "EQUINOX_ES_USERNAME" "Username" diff --git a/propulsion-summary-projector/Program.fs b/propulsion-summary-projector/Program.fs index 8bbe572bb..45f7118f1 100644 --- a/propulsion-summary-projector/Program.fs +++ b/propulsion-summary-projector/Program.fs @@ -103,6 +103,7 @@ module CmdParser = | [] Timeout of float | [] Retries of int | [] HeartbeatTimeout of float + | [] Tcp | [] Host of string | [] Port of int | [] Username of string @@ -122,8 +123,9 @@ module CmdParser = | Percent _ -> "EventStore $all Stream Position to commence from (as a percentage of current tail position)" | Verbose -> "Include low level Store logging." - | Host _ -> "specify a DNS query, using Gossip-driven discovery against all A records returned. (optional if environment variable EQUINOX_ES_HOST specified)" - | Port _ -> "specify a custom port. Defaults: envvar:EQUINOX_ES_PORT, 30778." + | Tcp -> "Request connecting direct to a TCP/IP endpoint. Default: Use Clustered mode with Gossip-driven discovery (unless environment variable EQUINOX_ES_TCP specifies 'true')." + | Host _ -> "TCP mode: specify a hostname to connect to directly. Clustered mode: use Gossip protocol against all A records returned from DNS query. (optional if environment variable EQUINOX_ES_HOST specified)" + | Port _ -> "specify a custom port. Uses value of environment variable EQUINOX_ES_PORT if specified. Defaults for Cluster and Direct TCP/IP mode are 30778 and 1113 respectively." | Username _ -> "specify a username. (optional if environment variable EQUINOX_ES_USERNAME specified)" | Password _ -> "specify a Password. (optional if environment variable EQUINOX_ES_PASSWORD specified)" | Timeout _ -> "specify operation timeout in seconds. Default: 20." @@ -145,7 +147,15 @@ module CmdParser = | None, None, None, true -> StartPos.TailOrCheckpoint | None, None, None, _ -> StartPos.StartOrCheckpoint - member __.Discovery = match __.Port with Some p -> Discovery.GossipDnsCustomPort (__.Host, p) | None -> Discovery.GossipDns __.Host + member __.Discovery = + match __.Tcp, __.Port with + | false, None -> Discovery.GossipDns __.Host + | false, Some p -> Discovery.GossipDnsCustomPort (__.Host, p) + | true, None -> Discovery.Uri (UriBuilder("tcp", __.Host).Uri) + | true, Some p -> Discovery.Uri (UriBuilder("tcp", __.Host, p).Uri) + member __.Tcp = + a.Contains EsSourceParameters.Tcp + || EnvVar.tryGet "EQUINOX_ES_TCP" |> Option.exists (fun s -> String.Equals(s, bool.TrueString, StringComparison.OrdinalIgnoreCase)) member __.Port = match a.TryGetResult Port with Some x -> Some x | None -> EnvVar.tryGet "EQUINOX_ES_PORT" |> Option.map int member __.Host = a.TryGetResult Host |> defaultWithEnvVar "EQUINOX_ES_HOST" "Host" member __.User = a.TryGetResult Username |> defaultWithEnvVar "EQUINOX_ES_USERNAME" "Username" diff --git a/propulsion-sync/Program.fs b/propulsion-sync/Program.fs index eb4a8106f..bc88963a4 100644 --- a/propulsion-sync/Program.fs +++ b/propulsion-sync/Program.fs @@ -228,6 +228,7 @@ module CmdParser = | [] Timeout of float | [] Retries of int | [] HeartbeatTimeout of float + | [] Tcp | [] Host of string | [] Port of int | [] Username of string @@ -249,8 +250,9 @@ module CmdParser = | Percent _ -> "EventStore $all Stream Position to commence from (as a percentage of current tail position)" | Verbose -> "Include low level Store logging." - | Host _ -> "specify a DNS query, using Gossip-driven discovery against all A records returned. (optional if environment variable EQUINOX_ES_HOST specified)" - | Port _ -> "specify a custom port. Defaults: envvar:EQUINOX_ES_PORT, 30778." + | Tcp -> "Request connecting direct to a TCP/IP endpoint. Default: Use Clustered mode with Gossip-driven discovery (unless environment variable EQUINOX_ES_TCP specifies 'true')." + | Host _ -> "TCP mode: specify a hostname to connect to directly. Clustered mode: use Gossip protocol against all A records returned from DNS query. (optional if environment variable EQUINOX_ES_HOST specified)" + | Port _ -> "specify a custom port. Uses value of environment variable EQUINOX_ES_PORT if specified. Defaults for Cluster and Direct TCP/IP mode are 30778 and 1113 respectively." | Username _ -> "specify a username. (optional if environment variable EQUINOX_ES_USERNAME specified)" | Password _ -> "specify a Password. (optional if environment variable EQUINOX_ES_PASSWORD specified)" | Timeout _ -> "specify operation timeout in seconds. Default: 20." @@ -274,7 +276,15 @@ module CmdParser = | None, None, None, true -> StartPos.TailOrCheckpoint | None, None, None, _ -> StartPos.StartOrCheckpoint - member __.Discovery = match __.Port with Some p -> Discovery.GossipDnsCustomPort (__.Host, p) | None -> Discovery.GossipDns __.Host + member __.Discovery = + match __.Tcp, __.Port with + | false, None -> Discovery.GossipDns __.Host + | false, Some p -> Discovery.GossipDnsCustomPort (__.Host, p) + | true, None -> Discovery.Uri (UriBuilder("tcp", __.Host).Uri) + | true, Some p -> Discovery.Uri (UriBuilder("tcp", __.Host, p).Uri) + member __.Tcp = + a.Contains EsSourceParameters.Tcp + || EnvVar.tryGet "EQUINOX_ES_TCP" |> Option.exists (fun s -> String.Equals(s, bool.TrueString, StringComparison.OrdinalIgnoreCase)) member __.Port = match a.TryGetResult EsSourceParameters.Port with Some x -> Some x | None -> EnvVar.tryGet "EQUINOX_ES_PORT" |> Option.map int member __.Host = a.TryGetResult EsSourceParameters.Host |> defaultWithEnvVar "EQUINOX_ES_HOST" "Host" member __.User = a.TryGetResult EsSourceParameters.Username |> defaultWithEnvVar "EQUINOX_ES_USERNAME" "Username" @@ -352,6 +362,7 @@ module CmdParser = #endif and [] EsSinkParameters = | [] Verbose + | [] Tcp | [] Host of string | [] Port of int | [] Username of string @@ -362,15 +373,24 @@ module CmdParser = interface IArgParserTemplate with member a.Usage = a |> function | Verbose -> "Include low level Store logging." - | Host _ -> "specify a DNS query, using Gossip-driven discovery against all A records returned. (optional if environment variable EQUINOX_ES_HOST specified)" - | Port _ -> "specify a custom port. Defaults: envvar:EQUINOX_ES_PORT, 30778." + | Tcp -> "Request connecting direct to a TCP/IP endpoint. Default: Use Clustered mode with Gossip-driven discovery (unless environment variable EQUINOX_ES_TCP specifies 'true')." + | Host _ -> "TCP mode: specify a hostname to connect to directly. Clustered mode: use Gossip protocol against all A records returned from DNS query. (optional if environment variable EQUINOX_ES_HOST specified)" + | Port _ -> "specify a custom port. Uses value of environment variable EQUINOX_ES_PORT if specified. Defaults for Cluster and Direct TCP/IP mode are 30778 and 1113 respectively." | Username _ -> "specify a username. (optional if environment variable EQUINOX_ES_USERNAME specified)" | Password _ -> "specify a password. (optional if environment variable EQUINOX_ES_PASSWORD specified)" | Timeout _ -> "specify operation timeout in seconds. Default: 20." | Retries _ -> "specify operation retries. Default: 3." | HeartbeatTimeout _ -> "specify heartbeat timeout in seconds. Default: 1.5." and EsSinkArguments(a : ParseResults) = - member __.Discovery = match __.Port with Some p -> Discovery.GossipDnsCustomPort (__.Host, p) | None -> Discovery.GossipDns __.Host + member __.Discovery = + match __.Tcp, __.Port with + | false, None -> Discovery.GossipDns __.Host + | false, Some p -> Discovery.GossipDnsCustomPort (__.Host, p) + | true, None -> Discovery.Uri (UriBuilder("tcp", __.Host).Uri) + | true, Some p -> Discovery.Uri (UriBuilder("tcp", __.Host, p).Uri) + member __.Tcp = + a.Contains EsSinkParameters.Tcp + || EnvVar.tryGet "EQUINOX_ES_TCP" |> Option.exists (fun s -> String.Equals(s, bool.TrueString, StringComparison.OrdinalIgnoreCase)) member __.Port = match a.TryGetResult Port with Some x -> Some x | None -> EnvVar.tryGet "EQUINOX_ES_PORT" |> Option.map int member __.Host = a.TryGetResult Host |> defaultWithEnvVar "EQUINOX_ES_HOST" "Host" member __.User = a.TryGetResult Username |> defaultWithEnvVar "EQUINOX_ES_USERNAME" "Username"