Coder Social home page Coder Social logo

SSL support for TDS about tds HOT 45 CLOSED

mjaric avatar mjaric commented on August 16, 2024 5
SSL support for TDS

from tds.

Comments (45)

YocelinGR avatar YocelinGR commented on August 16, 2024 8

Hi, good day. Do you have any update about this issue!?

from tds.

mjaric avatar mjaric commented on August 16, 2024 6

Ha!!! Thanks @georgy !!! this :REDACTED means password obfuscation was done earlier when connection with azure proxy completed. It is probably the reason why redirects within azure fails.

I will fix it and let you know when it is ready for another try.

from tds.

mjaric avatar mjaric commented on August 16, 2024 3

I think I managed to make progress and fool :ssl with a proxy process. Here is commit that works, but I need to add one more thing before it completes :full handshake process (now it only handles hello, message and stuck on KeyExchange)

Tds.TlsWrapper is obsolete, I moved everything yo Tds.Tls. It starts new process, to avoid deadlocks between Tds.Protocol proccess and :tls_connection . Tds.Tls behaves as proxy to :gen_tcp when :ssl module tries to call setopts, controlling_process or recv. Internaly it should track if handsake is completed, after that it stops prepending TDS header on SSL_PAYLOAD.

from tds.

Schultzer avatar Schultzer commented on August 16, 2024 2

Hi @mjaric, I can also verify that TDS is now working for us with one of our clients.

We are now moving forward with replacing our own ODBC solution.

Thanks for all your hard work on this, it's very appreciated!

from tds.

mjaric avatar mjaric commented on August 16, 2024 1

Yes, I found what is the issue, I assumed that tls payload will fit in single TDS package during pre-login TLS hadshake. Let me just try cover all cases since TCP must work in inet ACTIVE mode during handshake. I will update you when to try your example within azure

from tds.

mjaric avatar mjaric commented on August 16, 2024 1

@georgy, I made the change, it should work now at least internet -> azure (proxy). I think Azure -> Azure redirect should work too since it comes later as a eventchage but I don't have VM to check. Can you please run this change in your test env?

from tds.

georgy avatar georgy commented on August 16, 2024 1

@mjaric when running in azure -> azure scenario I see this:

23:42:56.572 [debug] Upgrading connection to SSL/TSL.

23:42:56.591 [debug] Upgrading connection to SSL/TSL.

23:42:56.598 [error] GenServer #PID<0.1227.0> terminating
** (ArgumentError) argument error
    (stdlib 3.14) :unicode.characters_to_binary(:REDACTED, :unicode, {:utf16, :little})
    (tds 2.1.3) lib/tds/latin1.ex:5: Tds.Latin1.encode/2
    (tds 2.1.3) lib/tds/messages.ex:293: Tds.Messages.encode/2
    (tds 2.1.3) lib/tds/protocol.ex:861: Tds.Protocol.login_send/2
    (tds 2.1.3) lib/tds/protocol.ex:576: Tds.Protocol.login/1
    (tds 2.1.3) lib/tds/protocol.ex:409: Tds.Protocol.connect/2
    (tds 2.1.3) lib/tds/protocol.ex:529: Tds.Protocol.decode/2
    (tds 2.1.3) lib/tds/protocol.ex:576: Tds.Protocol.login/1
Last message: nil
State: Tds.Protocol

from tds.

Schultzer avatar Schultzer commented on August 16, 2024 1

@moogle19 I just tested out the new version, and works flawlessly! Thanks for doing this!

from tds.

Schultzer avatar Schultzer commented on August 16, 2024 1

@moogle19 We’re running TDS with SSL in production, so far there has been no issues so I believe we can close this issue.

from tds.

cbourg2 avatar cbourg2 commented on August 16, 2024

Hi are there any new developments on this?

I am attempting to connect to a remote MSSQL DB using this library (standalone and via the ecto_sql adapter) and have been unsuccessful owing, I believe, to the login process implemented here.

I see that there are functions that seem to imply a two step process

https://github.com/livehelpnow/tds/blob/11e2f911a0b3b8452b65505a1e7e2451ec32ab79/lib/tds/protocol.ex#L544-L557

Though I do not see Tds.Protocol.prelogin/1 called anywhere nor is it a defined callback for the DBConnection behaviour. (it's not called from that library either as far as I can tell.

I'm wondering if maybe there is a configuration option that will invoke prelogin/1? Or maybe it's an unfinished feature?

from tds.

mjaric avatar mjaric commented on August 16, 2024

Hi @cbourg2 , it is not implemented yet. At the moment no one is working on this as I'm aware

from tds.

cbourg2 avatar cbourg2 commented on August 16, 2024

@mjaric Ok. Thank you very much for the quick response.

from tds.

mjaric avatar mjaric commented on August 16, 2024

This is kind of tricky to implement, erlang :ssl module completely hides buffer from user code so it is impossible to extract servers "hello" message from second PreLogin.

So problem is this

  1. client connects with gen_tcp
  2. client sends first Prelogin message saying it is supports encryption
  3. if server responds with its Prelogin saying encryption is ON ot REQUIRED
  4. client sends new Prelogin message (header only) preceding SSL Hnadshake payload (SSL Hello record)
  5. server (if encryption is ON) responds with Prelogin message (header only) preceeding SSL Handshake payload

So above requires that :ssl.connect(socket, sock_options, timeout) call can accept callback that still can inject preceding unencrypted 8 bytes as Prelogin header and on match header with 8 bytes that is returned from server as response before client handshake part is processed by :ssl internal code.

One solution is to build Tds.Tsl module that reuses erlang :tls internal modules just for handshake purpose, and luckily if possible continue with regular :ssl module after successful handshake.

For instance, mssql client written in Rust, has TlsPreloginWrapper it handles tds header before stream is processed by Tls module.

from tds.

josevalim avatar josevalim commented on August 16, 2024

@mjaric do you have a small proof of concept code that you can share with us so we understand this better? :)

from tds.

mjaric avatar mjaric commented on August 16, 2024

Partially, here is a "hack" I did to mimic client sending PreLogin header before ssl hello record that is sent with :ssl.connect/3 few lines below

In this case sever will respond with package that contains first byte 0x12 (18 dec) + 7 bytes as content of servers PreLogin response header, the rest bytes in message are SSL handshake from server. Since erlang expects first byte to correspond to cheaper code e.g. 0x16 it will throw error. And this is only required during handshake, after that :ssl module should do the rest

{:tls_alert, {:unexpected_message, 'TLS client: In state hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message\n {unsupported_record_type,18}’}}

from tds.

josevalim avatar josevalim commented on August 16, 2024

Ah, I see, but the receiving part is not done yet, right? Have you tried the handshape option on connect? Maybe it allows you to control the handshape at exactly this point.

from tds.

mjaric avatar mjaric commented on August 16, 2024

I tried handshake, but maybe I set wrong size in Prelogin header, I'll give it a try again... but it looks like only server socket can use hanshake_continue, I'm not sure how to validate and remove first 8 bytes before ssl reads that hello record

from tds.

mjaric avatar mjaric commented on August 16, 2024

Yep, like it says here

Performs the TLS/DTLS server-side handshake.

from tds.

mjaric avatar mjaric commented on August 16, 2024

Here is full debug with :ssl.connect/3

mix test test/login_test.exs
Compiling 1 file (.ex)
Excluding tags: [:manual]

.PRELOGIN RESPONSE: <<0, 0, 26, 0, 6, 1, 0, 32, 0, 1, 3, 0, 33, 0, 0, 4, 0, 33, 0, 1, 6, 0, 34, 0,
  1, 255, 14, 0, 7, 235, 0, 0, 2, 0, 0>>
.PRELOGIN RESPONSE: <<0, 0, 26, 0, 6, 1, 0, 32, 0, 1, 3, 0, 33, 0, 0, 4, 0, 33, 0, 1, 6, 0, 34, 0,
  1, 255, 14, 0, 7, 235, 0, 0, 1, 0, 0>>

18:17:45.042 [debug] Upgrading connection to SSL/TSL.

18:17:45.094 [debug] [direction: :outbound, message: {:client_hello, {3, 3}, <<95, 190, 145, 185, 32, 41, 105, 199, 57, 16, 26, 183, 141, 131, 7, 86, 239, 187, 16, 231, 36, 197, 34, 172, 159, 243, 163, 6, 51, 10, 85, 7>>, "", :undefined, [<<0, 255>>, <<19, 2>>, <<19, 1>>, <<19, 3>>, <<19, 4>>, <<19, 5>>, <<192, 44>>, <<192, 48>>, <<192, 36>>, <<192, 40>>, <<192, 46>>, <<192, 50>>, <<192, 38>>, <<192, 42>>, <<0, 159>>, <<0, 163>>, <<0, 107>>, <<0, 106>>, <<192, 43>>, <<192, 47>>, "̩", "̨", <<192, 35>>, <<192, 39>>, <<192, 45>>, <<192, 49>>, <<192, 37>>, <<192, 41>>, <<0, 158>>, <<0, 162>>, "̪", <<0, 103>>, <<0, 64>>, <<192, 10>>, <<192, 20>>, <<0, 57>>, <<0, 56>>, <<192, 5>>, <<192, 15>>, <<192, 9>>, <<192, ...>>, <<...>>, ...], [0], %{alpn: :undefined, client_hello_versions: {:client_hello_versions, [{3, 4}, {3, 3}]}, ec_point_formats: {:ec_point_formats, [0]}, elliptic_curves: {:supported_groups, [:x25519, :x448, :secp256r1, :secp384r1]}, key_share: {:key_share_client_hello, [{:key_share_entry, :x25519, <<134, 227, 18, 238, 145, 114, 129, 48, 16, 188, 214, 222, 91, 38, 241, 151, 247, 68, 146, 38, 42, 234, 219, 22, 60, 93, 198, 118, 7, ...>>}]}, max_frag_enum: :undefined, next_protocol_negotiation: :undefined, renegotiation_info: {:renegotiation_info, :undefined}, signature_algs: {:signature_algorithms, [:ecdsa_secp521r1_sha512, :ecdsa_secp384r1_sha384, :ecdsa_secp256r1_sha256, :rsa_pss_pss_sha512, :rsa_pss_pss_sha384, :rsa_pss_pss_sha256, :rsa_pss_rsae_sha512, :rsa_pss_rsae_sha384, :rsa_pss_rsae_sha256, :rsa_pkcs1_sha512, :rsa_pkcs1_sha384, :rsa_pkcs1_sha256, :ecdsa_sha1, :rsa_pkcs1_sha1, {:sha512, :ecdsa}, {:sha512, :rsa}, {:sha384, :ecdsa}, {:sha384, :rsa}, {:sha256, :ecdsa}, {:sha256, :rsa}, {:sha224, :ecdsa}, {:sha224, :rsa}, {:sha, :ecdsa}, {:sha, :rsa}, {:sha, :dsa}]}, signature_algs_cert: :undefined, sni: :undefined, srp: :undefined}}, protocol: :handshake]
>>> TLS 1.3 Handshake, ClientHello
[{client_version,{3,3}},
 {random,
     <<95,190,145,185,32,41,105,199,57,16,26,183,141,131,7,86,239,187,16,231,
       36,197,34,172,159,243,163,6,51,10,85,7>>},
 {session_id,<<>>},
 {cookie,undefined},
 {cipher_suites,
     ["TLS_EMPTY_RENEGOTIATION_INFO_SCSV","TLS_AES_256_GCM_SHA384",
      "TLS_AES_128_GCM_SHA256","TLS_CHACHA20_POLY1305_SHA256",
      "TLS_AES_128_CCM_SHA256","TLS_AES_128_CCM_8_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384",
      "TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384",
      "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384",
      "TLS_DHE_RSA_WITH_AES_256_GCM_SHA384",
      "TLS_DHE_DSS_WITH_AES_256_GCM_SHA384",
      "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256",
      "TLS_DHE_DSS_WITH_AES_256_CBC_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256",
      "TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256",
      "TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256",
      "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256",
      "TLS_DHE_RSA_WITH_AES_128_GCM_SHA256",
      "TLS_DHE_DSS_WITH_AES_128_GCM_SHA256",
      "TLS_DHE_RSA_WITH_CHACHA20_POLY1305_SHA256",
      "TLS_DHE_RSA_WITH_AES_128_CBC_SHA256",
      "TLS_DHE_DSS_WITH_AES_128_CBC_SHA256",
      "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA","TLS_DHE_RSA_WITH_AES_256_CBC_SHA",
      "TLS_DHE_DSS_WITH_AES_256_CBC_SHA",
      "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA",
      "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA","TLS_DHE_RSA_WITH_AES_128_CBC_SHA",
      "TLS_DHE_DSS_WITH_AES_128_CBC_SHA",
      "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA",
      "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA"]},
 {compression_methods,[0]},
 {extensions,
     #{alpn => undefined,
       client_hello_versions => {client_hello_versions,[{3,4},{3,3}]},
       ec_point_formats => {ec_point_formats,[0]},
       elliptic_curves => {supported_groups,[x25519,x448,secp256r1,secp384r1]},
       key_share =>
           {key_share_client_hello,
               [{key_share_entry,x25519,
                    <<134,227,18,238,145,114,129,48,16,188,214,222,91,38,
                      241,151,247,68,146,38,42,234,219,22,60,93,198,118,7,
                      208,238,116>>}]},
       max_frag_enum => undefined,next_protocol_negotiation => undefined,
       renegotiation_info => {renegotiation_info,undefined},
       signature_algs =>
           {signature_algorithms,
               [ecdsa_secp521r1_sha512,ecdsa_secp384r1_sha384,
                ecdsa_secp256r1_sha256,rsa_pss_pss_sha512,rsa_pss_pss_sha384,
                rsa_pss_pss_sha256,rsa_pss_rsae_sha512,rsa_pss_rsae_sha384,
                rsa_pss_rsae_sha256,rsa_pkcs1_sha512,rsa_pkcs1_sha384,
                rsa_pkcs1_sha256,ecdsa_sha1,rsa_pkcs1_sha1,
                {sha512,ecdsa},
                {sha512,rsa},
                {sha384,ecdsa},
                {sha384,rsa},
                {sha256,ecdsa},
                {sha256,rsa},
                {sha224,ecdsa},
                {sha224,rsa},
                {sha,ecdsa},
                {sha,rsa},
                {sha,dsa}]},
       signature_algs_cert => undefined,sni => undefined,srp => undefined}}]

18:17:45.097 [debug] [direction: :outbound, message: [<<22, 3, 3, 1, 6>>, [1, <<0, 1, 2>>, <<3, 3, 95, 190, 145, 185, 32, 41, 105, 199, 57, 16, 26, 183, 141, 131, 7, 86, 239, 187, 16, 231, 36, 197, 34, 172, 159, 243, 163, 6, 51, 10, 85, 7, 0, 0, 90, 0, 255, 19, 2, 19, 1, ...>>]], protocol: :record]
writing (267 bytes) TLS 1.2 Record Protocol, handshake
0000 - 16 03 03 01 06 01 00 01  02 03 03 5f be 91 b9 20    ..........._...
0010 - 29 69 c7 39 10 1a b7 8d  83 07 56 ef bb 10 e7 24    )i.9......V....$
0020 - c5 22 ac 9f f3 a3 06 33  0a 55 07 00 00 5a 00 ff    .".....3.U...Z..
0030 - 13 02 13 01 13 03 13 04  13 05 c0 2c c0 30 c0 24    ...........,.0.$
0040 - c0 28 c0 2e c0 32 c0 26  c0 2a 00 9f 00 a3 00 6b    .(...2.&.*.....k
0050 - 00 6a c0 2b c0 2f cc a9  cc a8 c0 23 c0 27 c0 2d    .j.+./.....#.'.-
0060 - c0 31 c0 25 c0 29 00 9e  00 a2 cc aa 00 67 00 40    .1.%.).......g.@
0070 - c0 0a c0 14 00 39 00 38  c0 05 c0 0f c0 09 c0 13    .....9.8........
0080 - 00 33 00 32 c0 04 c0 0e  01 00 00 7f 00 0d 00 34    .3.2...........4
0090 - 00 32 06 03 05 03 04 03  08 0b 08 0a 08 09 08 06    .2..............
00a0 - 08 05 08 04 06 01 05 01  04 01 02 03 02 01 06 03    ................
00b0 - 06 01 05 03 05 01 04 03  04 01 03 03 03 01 02 03    ................
00c0 - 02 01 02 02 00 33 00 26  00 24 00 1d 00 20 86 e3    .....3.&.$... ..
00d0 - 12 ee 91 72 81 30 10 bc  d6 de 5b 26 f1 97 f7 44    ...r.0....[&...D
00e0 - 92 26 2a ea db 16 3c 5d  c6 76 07 d0 ee 74 00 0a    .&*...<].v...t..
00f0 - 00 0a 00 08 00 1d 00 1e  00 17 00 18 00 0b 00 02    ................
0100 - 01 00 00 2b 00 05 04 03  04 03 03                   ...+.......

18:17:45.097 [debug] [direction: :outbound, message: [<<21, 3, 3, 0, 2>>, <<2, 10>>], protocol: :record]
writing (7 bytes) TLS 1.2 Record Protocol, alert
0000 - 15 03 03 00 02 02 0a                                .......

18:17:45.097 [info]  TLS :client: In state :hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message
 - {:unsupported_record_type, 18}

18:17:45.098 [error] GenServer #PID<0.284.0> terminating
** (Tds.Error) Unable to establish secure connection to server due {:tls_alert, {:unexpected_message, 'TLS client: In state hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message\n {unsupported_record_type,18}'}}
    (db_connection 2.2.0) lib/db_connection/connection.ex:87: DBConnection.Connection.connect/2
    (connection 1.0.4) lib/connection.ex:622: Connection.enter_connect/5
    (stdlib 3.13.2) proc_lib.erl:226: :proc_lib.init_p_do_apply/3
Last message: nil
State: Tds.Protocol


  1) test tsl (LoginTest)
     test/login_test.exs:34
     ** (EXIT from #PID<0.281.0>) killed

from tds.

josevalim avatar josevalim commented on August 16, 2024

They document the handshake under connect though: https://erlang.org/doc/man/ssl.html#connect-3 - and it has a separate return type.

from tds.

mjaric avatar mjaric commented on August 16, 2024

:) let me try

from tds.

mjaric avatar mjaric commented on August 16, 2024

If the option {handshake, hello} is used the handshake is paused after receiving the server hello message and the success response

I need to reach buffer before HELLO :)

from tds.

josevalim avatar josevalim commented on August 16, 2024

Oh noes. :(

from tds.

mjaric avatar mjaric commented on August 16, 2024

this is where :ssl should allow custom connection instead of throwing error

from tds.

mjaric avatar mjaric commented on August 16, 2024

Just saw this
what If instead {gen_tcp, tcp, tcp_closed, tcp_error, tcp_passive} I set {MyTcp, tcp, tcp_closed, tcp_error, tcp_passive}? I can create port of MyTcp process, right?

from tds.

josevalim avatar josevalim commented on August 16, 2024

Interesting... does it work? :D

from tds.

mjaric avatar mjaric commented on August 16, 2024

It does when sending message to server. But receiving never goes trough my module, looks like it is {active: true} after first send
here it receives data

from tds.

mjaric avatar mjaric commented on August 16, 2024

... and :ssl takes ownership of port (forgot exact line of code) so that is why it gets data on handle_info

Here and here is my attempt to use CbInfo

from tds.

mjaric avatar mjaric commented on August 16, 2024

Now it works 👀 just need to polish a bit in case of failures

from tds.

mjaric avatar mjaric commented on August 16, 2024

I will left this issue open, since I want to make simple app that connects and disconnects couple of times, if there are no hanging processes I think we can close this issue.

Maybe I should copy binary tail during handshake to avoid leaks.

from tds.

georgy avatar georgy commented on August 16, 2024

Hi @mjaric, what is the current status of this feature? We used Tds for dbs that did not require tls, but now we are blocked since the db we need to connect to enfirces tls. Using this branch as dependency produces following output:

    17:32:34.554 [debug] Upgrading connection to SSL/TSL.
    
    17:32:34.576 [info]  TLS :client: In state :hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message
     - {:unsupported_record_type, 18}
    
    17:32:34.577 [error] Tds.Protocol (#PID<0.408.0>) failed to connect: ** (Tds.Error) Unable to establish secure connection to server due {:tls_alert, {:unexpected_message, 'TLS client: In state hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message\n {unsupported_record_type,18}'}}

I will be happy to provide info/debug on our end to move this issue along, just let me know what to do :)

from tds.

mjaric avatar mjaric commented on August 16, 2024

Hi @georgy, the best would be if you can send me details how you configure encryption in SQL server. So far I tested it with "no configuration", just enabled optional connection encryption. If you have a setup checklist I will gladly configure my environment using it and check why this error occur.

from tds.

georgy avatar georgy commented on August 16, 2024

I am simply adding

      ssl: true,
      ssl_opts: [],

to the options I pass to Tds.start_link. Is that what you are asking?

from tds.

mjaric avatar mjaric commented on August 16, 2024

No, I meant on this configuration

image

That tab, and second one "Certificate" are related to connection encryption. Is anything cahnged there after instalation?

BTW, what version do you use?

  • erlang
  • elixir
  • sql server

from tds.

georgy avatar georgy commented on August 16, 2024

Erlang/OTP 23 [erts-11.1.7] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:1]
Interactive Elixir (1.11.3) - press Ctrl+C to exit (type h() ENTER for help)
SQL server: a PaaS on Azure

I have two PaaS DBs: one does not enforce TLS at all (a legacy db, not sure how it came about), the other one requires TLS > 2.0 (but can be setup to accept 1.0 or 1.1).

I have an app that uses tds 2.1.3 that is able to connect to legacy db without any issues. I do not have direct prove that TLS is not used in this scenario, but I assume that is the case.

If I point the same app at second DB I get error message saying:

00:20:57.633 [error] Tds.Protocol (#PID<0.598.0>) failed to connect: ** (Tds.Error) Line 0 (Error 47072): Reason: Login failed due to client TLS version being less than minimal TLS version allowed by the server.

If I try to use tds dependency this way:

{:tds, git: "https://github.com/livehelpnow/tds.git", ref: "ntlm_auth"},

and configure tds as:

[
    hostname: "somedb.database.windows.net",
    username: "...",
    password: "...",
    database: "...",
    port: 1433,
    queue_target: 10000,
    queue_interval: 60000,
    show_sensitive_data_on_connection_error: true,
    ssl: "true",
    ssl_opts: []
]

Then I see this message:

00:25:50.604 [debug] Upgrading connection to SSL/TSL.

00:25:50.636 [info] TLS :client: In state :hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message - {:unsupported_record_type, 18}

00:25:50.637 [error] Tds.Protocol (#PID<0.615.0>) failed to connect: ** (Tds.Error) Unable to establish secure connection to server due {:tls_alert, {:unexpected_message, 'TLS client: In state hello at tls_record.erl:539 generated CLIENT ALERT: Fatal - Unexpected Message\n {unsupported_record_type,18}'}}

from tds.

mjaric avatar mjaric commented on August 16, 2024

I've setup azure database and was able to reproduce issue. I will see what is the problem since seems this is issue with azure db connection encryption only

from tds.

georgy avatar georgy commented on August 16, 2024

Great, let me know if you need any additional info. The problematic part is that even if I use ntlm_auth version without adding any ssl settings, then I am not able to connect to the legacy DB (the one that does not enforce TLS at all).

from tds.

mjaric avatar mjaric commented on August 16, 2024

Hmm, that smells like EventChange message, could be that sql server is asking client to redirect. Are your Azure sql server behind proxy?

from tds.

georgy avatar georgy commented on August 16, 2024

Well, all DBs I am working with have Connection policy set to Default. The issue occurs when I try to connect from Azure to Azure (which should use Redirect).

from tds.

georgy avatar georgy commented on August 16, 2024

@mjaric any update on this issue you can share?

from tds.

georgy avatar georgy commented on August 16, 2024

Wow, cool. I will test the change today and get back to you asap

from tds.

mjaric avatar mjaric commented on August 16, 2024

@georgy, any feedback so far?

from tds.

georgy avatar georgy commented on August 16, 2024

The scenario with proxy (internet -> azure) works fine! The azure -> azure scenario does not, I am trying to get additional info and confirm that it is not due to our firewall setup. Will let you know the moment I am sure I am not wasting your time :)

from tds.

moogle19 avatar moogle19 commented on August 16, 2024

@georgy @Schultzer @YocelinGR
I merged the SSL part of @mjaric PR and made some other changes.
It would be nice if you could test the RC and give me some feedback if it doesn't work as expected!
Just replace the current dep with:

{:tds, "~> 2.3.0-rc.1", override: true}

from tds.

moogle19 avatar moogle19 commented on August 16, 2024

@Schultzer
Sound good. Thanks for the feedback!
If there are any bugs or issues in the future, feel free to open a new issue!

from tds.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.