1package gosnowflake 2 3import ( 4 "fmt" 5 "net/url" 6 "reflect" 7 "testing" 8 "time" 9) 10 11type tcParseDSN struct { 12 dsn string 13 config *Config 14 ocspMode string 15 err error 16} 17 18func TestParseDSN(t *testing.T) { 19 20 privKeyPKCS8 := generatePKCS8StringSupress(testPrivKey) 21 privKeyPKCS1 := generatePKCS1String(testPrivKey) 22 testcases := []tcParseDSN{ 23 { 24 dsn: "user:pass@ac-1-laksdnflaf.global/db/schema", 25 config: &Config{ 26 Account: "ac-1", User: "user", Password: "pass", Region: "global", 27 Protocol: "https", Host: "ac-1-laksdnflaf.global.snowflakecomputing.com", Port: 443, 28 Database: "db", Schema: "schema", 29 OCSPFailOpen: OCSPFailOpenTrue, 30 ValidateDefaultParameters: ConfigBoolTrue, 31 }, 32 ocspMode: ocspModeFailOpen, 33 err: nil, 34 }, 35 { 36 dsn: "user:pass@ac-laksdnflaf.global/db/schema", 37 config: &Config{ 38 Account: "ac", User: "user", Password: "pass", Region: "global", 39 Protocol: "https", Host: "ac-laksdnflaf.global.snowflakecomputing.com", Port: 443, 40 Database: "db", Schema: "schema", 41 OCSPFailOpen: OCSPFailOpenTrue, 42 ValidateDefaultParameters: ConfigBoolTrue, 43 }, 44 ocspMode: ocspModeFailOpen, 45 err: nil, 46 }, 47 { 48 dsn: "u:p@asnowflakecomputing.com/db/pa?account=a&protocol=https&role=r&timezone=UTC&aehouse=w", 49 config: &Config{Account: "a", User: "u", Password: "p", Database: "db", Schema: "pa", 50 Protocol: "https", Role: "r", Host: "asnowflakecomputing.com.snowflakecomputing.com", Port: 443, Region: "com", 51 OCSPFailOpen: OCSPFailOpenTrue, 52 ValidateDefaultParameters: ConfigBoolTrue, 53 }, 54 ocspMode: ocspModeFailOpen, 55 err: nil, 56 }, 57 { 58 dsn: "u:p@/db?account=ac", 59 config: &Config{ 60 Account: "ac", User: "u", Password: "p", Database: "db", 61 Protocol: "https", Host: "ac.snowflakecomputing.com", Port: 443, 62 OCSPFailOpen: OCSPFailOpenTrue, 63 ValidateDefaultParameters: ConfigBoolTrue, 64 }, 65 ocspMode: ocspModeFailOpen, 66 err: nil, 67 }, 68 { 69 dsn: "user:pass@account-hfdw89q748ew9gqf48w9qgf.global/db/s", 70 config: &Config{ 71 Account: "account", User: "user", Password: "pass", Region: "global", 72 Protocol: "https", Host: "account-hfdw89q748ew9gqf48w9qgf.global.snowflakecomputing.com", Port: 443, 73 Database: "db", Schema: "s", 74 ValidateDefaultParameters: ConfigBoolTrue, 75 OCSPFailOpen: OCSPFailOpenTrue, 76 }, 77 ocspMode: ocspModeFailOpen, 78 err: nil, 79 }, 80 { 81 dsn: "user:pass@account-hfdw89q748ew9gqf48w9qgf/db/s", 82 config: &Config{ 83 Account: "account-hfdw89q748ew9gqf48w9qgf", User: "user", Password: "pass", Region: "", 84 Protocol: "https", Host: "account-hfdw89q748ew9gqf48w9qgf.snowflakecomputing.com", Port: 443, 85 Database: "db", Schema: "s", 86 ValidateDefaultParameters: ConfigBoolTrue, 87 OCSPFailOpen: OCSPFailOpenTrue, 88 }, 89 ocspMode: ocspModeFailOpen, 90 err: nil, 91 }, 92 { 93 dsn: "user:pass@account", 94 config: &Config{ 95 Account: "account", User: "user", Password: "pass", Region: "", 96 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 97 OCSPFailOpen: OCSPFailOpenTrue, 98 ValidateDefaultParameters: ConfigBoolTrue, 99 }, 100 ocspMode: ocspModeFailOpen, 101 err: nil, 102 }, 103 { 104 dsn: "user:pass@account.eu-faraway", 105 config: &Config{ 106 Account: "account", User: "user", Password: "pass", Region: "eu-faraway", 107 Protocol: "https", Host: "account.eu-faraway.snowflakecomputing.com", Port: 443, 108 OCSPFailOpen: OCSPFailOpenTrue, 109 ValidateDefaultParameters: ConfigBoolTrue, 110 }, 111 ocspMode: ocspModeFailOpen, 112 err: nil, 113 }, 114 { 115 dsn: "user:pass@account?region=eu-faraway", 116 config: &Config{ 117 Account: "account", User: "user", Password: "pass", Region: "eu-faraway", 118 Protocol: "https", Host: "account.eu-faraway.snowflakecomputing.com", Port: 443, 119 OCSPFailOpen: OCSPFailOpenTrue, 120 ValidateDefaultParameters: ConfigBoolTrue, 121 }, 122 ocspMode: ocspModeFailOpen, 123 err: nil, 124 }, 125 { 126 dsn: "user:pass@account/db", 127 config: &Config{ 128 Account: "account", User: "user", Password: "pass", 129 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 130 Database: "db", 131 OCSPFailOpen: OCSPFailOpenTrue, 132 ValidateDefaultParameters: ConfigBoolTrue, 133 }, 134 ocspMode: ocspModeFailOpen, 135 err: nil, 136 }, 137 { 138 dsn: "user:pass@host:123/db/schema?account=ac&protocol=http", 139 config: &Config{ 140 Account: "ac", User: "user", Password: "pass", 141 Protocol: "http", Host: "host", Port: 123, 142 Database: "db", Schema: "schema", 143 OCSPFailOpen: OCSPFailOpenTrue, 144 ValidateDefaultParameters: ConfigBoolTrue, 145 }, 146 ocspMode: ocspModeFailOpen, 147 err: nil, 148 }, 149 { 150 dsn: "user@host:123/db/schema?account=ac&protocol=http", 151 config: &Config{ 152 Account: "ac", User: "user", Password: "pass", 153 Protocol: "http", Host: "host", Port: 123, 154 Database: "db", Schema: "schema", 155 OCSPFailOpen: OCSPFailOpenTrue, 156 ValidateDefaultParameters: ConfigBoolTrue, 157 }, 158 ocspMode: ocspModeFailOpen, 159 err: ErrEmptyPassword, 160 }, 161 { 162 dsn: "@host:123/db/schema?account=ac&protocol=http", 163 config: &Config{ 164 Account: "ac", User: "user", Password: "pass", 165 Protocol: "http", Host: "host", Port: 123, 166 Database: "db", Schema: "schema", 167 OCSPFailOpen: OCSPFailOpenTrue, 168 ValidateDefaultParameters: ConfigBoolTrue, 169 }, 170 ocspMode: ocspModeFailOpen, 171 err: ErrEmptyUsername, 172 }, 173 { 174 dsn: "user:p@host:123/db/schema?protocol=http", 175 config: &Config{ 176 Account: "ac", User: "user", Password: "pass", 177 Protocol: "http", Host: "host", Port: 123, 178 Database: "db", Schema: "schema", 179 OCSPFailOpen: OCSPFailOpenTrue, 180 ValidateDefaultParameters: ConfigBoolTrue, 181 }, 182 ocspMode: ocspModeFailOpen, 183 err: ErrEmptyAccount, 184 }, 185 { 186 dsn: "u:p@a.snowflakecomputing.com/db/pa?account=a&protocol=https&role=r&timezone=UTC&warehouse=w", 187 config: &Config{ 188 Account: "a", User: "u", Password: "p", 189 Protocol: "https", Host: "a.snowflakecomputing.com", Port: 443, 190 Database: "db", Schema: "pa", Role: "r", Warehouse: "w", 191 OCSPFailOpen: OCSPFailOpenTrue, 192 ValidateDefaultParameters: ConfigBoolTrue, 193 }, 194 ocspMode: ocspModeFailOpen, 195 err: nil, 196 }, 197 { 198 dsn: "u:p@snowflake.local:9876?account=a&protocol=http", 199 config: &Config{ 200 Account: "a", User: "u", Password: "p", 201 Protocol: "http", Host: "snowflake.local", Port: 9876, 202 OCSPFailOpen: OCSPFailOpenTrue, 203 ValidateDefaultParameters: ConfigBoolTrue, 204 }, 205 ocspMode: ocspModeFailOpen, 206 err: nil, 207 }, 208 { 209 dsn: "snowflake.local:9876?account=a&protocol=http&authenticator=OAUTH", 210 config: &Config{ 211 Account: "a", Authenticator: AuthTypeOAuth, 212 Protocol: "http", Host: "snowflake.local", Port: 9876, 213 OCSPFailOpen: OCSPFailOpenTrue, 214 ValidateDefaultParameters: ConfigBoolTrue, 215 }, 216 ocspMode: ocspModeFailOpen, 217 err: nil, 218 }, 219 { 220 dsn: "u:@a.snowflake.local:9876?account=a&protocol=http&authenticator=SNOWFLAKE_JWT", 221 config: &Config{ 222 Account: "a", User: "u", Authenticator: AuthTypeJwt, 223 Protocol: "http", Host: "a.snowflake.local", Port: 9876, 224 OCSPFailOpen: OCSPFailOpenTrue, 225 ValidateDefaultParameters: ConfigBoolTrue, 226 }, 227 ocspMode: ocspModeFailOpen, 228 err: nil, 229 }, 230 231 { 232 dsn: "u:p@a?database=d&jwtTimeout=20", 233 config: &Config{ 234 Account: "a", User: "u", Password: "p", 235 Protocol: "https", Host: "a.snowflakecomputing.com", Port: 443, 236 Database: "d", Schema: "", 237 JWTExpireTimeout: 20 * time.Second, 238 OCSPFailOpen: OCSPFailOpenTrue, 239 ValidateDefaultParameters: ConfigBoolTrue, 240 }, 241 ocspMode: ocspModeFailOpen, 242 }, 243 { 244 dsn: "u:p@a?database=d", 245 config: &Config{ 246 Account: "a", User: "u", Password: "p", 247 Protocol: "https", Host: "a.snowflakecomputing.com", Port: 443, 248 Database: "d", Schema: "", 249 JWTExpireTimeout: defaultJWTTimeout, 250 OCSPFailOpen: OCSPFailOpenTrue, 251 ValidateDefaultParameters: ConfigBoolTrue, 252 }, 253 ocspMode: ocspModeFailOpen, 254 }, 255 { 256 dsn: "u:p@snowflake.local:NNNN?account=a&protocol=http", 257 config: &Config{ 258 Account: "a", User: "u", Password: "p", 259 Protocol: "http", Host: "snowflake.local", Port: 9876, 260 OCSPFailOpen: OCSPFailOpenTrue, 261 ValidateDefaultParameters: ConfigBoolTrue, 262 }, 263 ocspMode: ocspModeFailOpen, 264 err: &SnowflakeError{ 265 Message: errMsgFailedToParsePort, 266 MessageArgs: []interface{}{"NNNN"}, 267 Number: ErrCodeFailedToParsePort, 268 }, 269 }, 270 { 271 dsn: "u:p@a?database=d&schema=s&role=r&application=aa&authenticator=snowflake&insecureMode=true&passcode=pp&passcodeInPassword=true", 272 config: &Config{ 273 Account: "a", User: "u", Password: "p", 274 Protocol: "https", Host: "a.snowflakecomputing.com", Port: 443, 275 Database: "d", Schema: "s", Role: "r", Authenticator: AuthTypeSnowflake, Application: "aa", 276 InsecureMode: true, Passcode: "pp", PasscodeInPassword: true, 277 OCSPFailOpen: OCSPFailOpenTrue, 278 ValidateDefaultParameters: ConfigBoolTrue, 279 }, 280 ocspMode: ocspModeInsecure, 281 err: nil, 282 }, 283 { 284 // schema should be ignored as no value is specified. 285 dsn: "u:p@a?database=d&schema", 286 config: &Config{ 287 Account: "a", User: "u", Password: "p", 288 Protocol: "https", Host: "a.snowflakecomputing.com", Port: 443, 289 Database: "d", Schema: "", 290 OCSPFailOpen: OCSPFailOpenTrue, 291 ValidateDefaultParameters: ConfigBoolTrue, 292 }, 293 ocspMode: ocspModeFailOpen, 294 err: nil, 295 }, 296 { 297 dsn: "u:p@a?database= %Sd", 298 config: &Config{}, 299 err: url.EscapeError(`invalid URL escape`), 300 }, 301 { 302 dsn: "u:p@a?schema= %Sd", 303 config: &Config{}, 304 err: url.EscapeError(`invalid URL escape`), 305 }, 306 { 307 dsn: "u:p@a?warehouse= %Sd", 308 config: &Config{}, 309 err: url.EscapeError(`invalid URL escape`), 310 }, 311 { 312 dsn: "u:p@a?role= %Sd", 313 config: &Config{}, 314 err: url.EscapeError(`invalid URL escape`), 315 }, 316 { 317 dsn: ":/", 318 config: &Config{}, 319 err: &SnowflakeError{ 320 Number: ErrCodeFailedToParsePort, 321 }, 322 }, 323 { 324 dsn: "u:u@/+/+?account=+&=0", 325 config: &Config{}, 326 err: ErrEmptyAccount, 327 }, 328 { 329 dsn: "u:u@/+/+?account=+&=+&=+", 330 config: &Config{}, 331 err: ErrEmptyAccount, 332 }, 333 { 334 dsn: "user%40%2F1:p%3A%40s@/db%2F?account=ac", 335 config: &Config{ 336 Account: "ac", User: "user@/1", Password: "p:@s", Database: "db/", 337 Protocol: "https", Host: "ac.snowflakecomputing.com", Port: 443, 338 OCSPFailOpen: OCSPFailOpenTrue, 339 ValidateDefaultParameters: ConfigBoolTrue, 340 }, 341 ocspMode: ocspModeFailOpen, 342 err: nil, 343 }, 344 { 345 dsn: fmt.Sprintf("u:p@ac.snowflake.local:9876?account=ac&protocol=http&authenticator=SNOWFLAKE_JWT&privateKey=%v", privKeyPKCS8), 346 config: &Config{ 347 Account: "ac", User: "u", Password: "p", 348 Authenticator: AuthTypeJwt, PrivateKey: testPrivKey, 349 Protocol: "http", Host: "ac.snowflake.local", Port: 9876, 350 OCSPFailOpen: OCSPFailOpenTrue, 351 ValidateDefaultParameters: ConfigBoolTrue, 352 }, 353 ocspMode: ocspModeFailOpen, 354 err: nil, 355 }, 356 { 357 dsn: fmt.Sprintf("u:p@ac.snowflake.local:9876?account=ac&protocol=http&authenticator=%v", url.QueryEscape("https://ac.okta.com")), 358 config: &Config{ 359 Account: "ac", User: "u", Password: "p", 360 Authenticator: AuthTypeOkta, 361 OktaURL: &url.URL{ 362 Scheme: "https", 363 Host: "ac.okta.com", 364 }, 365 PrivateKey: testPrivKey, 366 Protocol: "http", Host: "ac.snowflake.local", Port: 9876, 367 OCSPFailOpen: OCSPFailOpenTrue, 368 ValidateDefaultParameters: ConfigBoolTrue, 369 }, 370 ocspMode: ocspModeFailOpen, 371 err: nil, 372 }, 373 { 374 dsn: fmt.Sprintf("u:p@a.snowflake.local:9876?account=a&protocol=http&authenticator=SNOWFLAKE_JWT&privateKey=%v", privKeyPKCS1), 375 config: &Config{ 376 Account: "a", User: "u", Password: "p", 377 Authenticator: AuthTypeJwt, PrivateKey: testPrivKey, 378 Protocol: "http", Host: "a.snowflake.local", Port: 9876, 379 OCSPFailOpen: OCSPFailOpenTrue, 380 ValidateDefaultParameters: ConfigBoolTrue, 381 }, 382 ocspMode: ocspModeFailOpen, 383 err: &SnowflakeError{Number: ErrCodePrivateKeyParseError}, 384 }, 385 { 386 dsn: "user:pass@account/db/s?ocspFailOpen=true", 387 config: &Config{ 388 Account: "account", User: "user", Password: "pass", 389 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 390 Database: "db", Schema: "s", OCSPFailOpen: OCSPFailOpenTrue, 391 ValidateDefaultParameters: ConfigBoolTrue, 392 }, 393 ocspMode: ocspModeFailOpen, 394 err: nil, 395 }, 396 { 397 dsn: "user:pass@account/db/s?ocspFailOpen=false", 398 config: &Config{ 399 Account: "account", User: "user", Password: "pass", 400 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 401 Database: "db", Schema: "s", OCSPFailOpen: OCSPFailOpenFalse, 402 ValidateDefaultParameters: ConfigBoolTrue, 403 }, 404 ocspMode: ocspModeFailClosed, 405 err: nil, 406 }, 407 { 408 dsn: "user:pass@account/db/s?insecureMode=true&ocspFailOpen=false", 409 config: &Config{ 410 Account: "account", User: "user", Password: "pass", 411 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 412 Database: "db", Schema: "s", OCSPFailOpen: OCSPFailOpenFalse, InsecureMode: true, 413 ValidateDefaultParameters: ConfigBoolTrue, 414 }, 415 ocspMode: ocspModeInsecure, 416 err: nil, 417 }, 418 { 419 dsn: "user:pass@account/db/s?validateDefaultParameters=true", 420 config: &Config{ 421 Account: "account", User: "user", Password: "pass", 422 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 423 Database: "db", Schema: "s", ValidateDefaultParameters: ConfigBoolTrue, OCSPFailOpen: OCSPFailOpenTrue, 424 }, 425 ocspMode: ocspModeFailOpen, 426 err: nil, 427 }, 428 { 429 dsn: "user:pass@account/db/s?validateDefaultParameters=false", 430 config: &Config{ 431 Account: "account", User: "user", Password: "pass", 432 Protocol: "https", Host: "account.snowflakecomputing.com", Port: 443, 433 Database: "db", Schema: "s", ValidateDefaultParameters: ConfigBoolFalse, OCSPFailOpen: OCSPFailOpenTrue, 434 }, 435 ocspMode: ocspModeFailOpen, 436 err: nil, 437 }, 438 { 439 dsn: "u:p@a.r.c.snowflakecomputing.com/db/s?account=a.r.c&validateDefaultParameters=false", 440 config: &Config{ 441 Account: "a", User: "u", Password: "p", 442 Protocol: "https", Host: "a.r.c.snowflakecomputing.com", Port: 443, 443 Database: "db", Schema: "s", ValidateDefaultParameters: ConfigBoolFalse, OCSPFailOpen: OCSPFailOpenTrue, 444 }, 445 ocspMode: ocspModeFailOpen, 446 err: nil, 447 }, 448 } 449 450 for i, test := range testcases { 451 // t.Logf("Parsing testcase %d, DSN: %s", i, test.dsn) 452 cfg, err := ParseDSN(test.dsn) 453 switch { 454 case test.err == nil: 455 if err != nil { 456 t.Fatalf("%d: Failed to parse the DSN. dsn: %v, err: %v", i, test.dsn, err) 457 } 458 if test.config.Host != cfg.Host { 459 t.Fatalf("%d: Failed to match host. expected: %v, got: %v", 460 i, test.config.Host, cfg.Host) 461 } 462 if test.config.Account != cfg.Account { 463 t.Fatalf("%d: Failed to match account. expected: %v, got: %v", 464 i, test.config.Account, cfg.Account) 465 } 466 if test.config.User != cfg.User { 467 t.Fatalf("%d: Failed to match user. expected: %v, got: %v", 468 i, test.config.User, cfg.User) 469 } 470 if test.config.Password != cfg.Password { 471 t.Fatalf("%d: Failed to match password. expected: %v, got: %v", 472 i, test.config.Password, cfg.Password) 473 } 474 if test.config.Database != cfg.Database { 475 t.Fatalf("%d: Failed to match database. expected: %v, got: %v", 476 i, test.config.Database, cfg.Database) 477 } 478 if test.config.Schema != cfg.Schema { 479 t.Fatalf("%d: Failed to match schema. expected: %v, got: %v", 480 i, test.config.Schema, cfg.Schema) 481 } 482 if test.config.Warehouse != cfg.Warehouse { 483 t.Fatalf("%d: Failed to match warehouse. expected: %v, got: %v", 484 i, test.config.Warehouse, cfg.Warehouse) 485 } 486 if test.config.Role != cfg.Role { 487 t.Fatalf("%d: Failed to match role. expected: %v, got: %v", 488 i, test.config.Role, cfg.Role) 489 } 490 if test.config.Region != cfg.Region { 491 t.Fatalf("%d: Failed to match region. expected: %v, got: %v", 492 i, test.config.Region, cfg.Region) 493 } 494 if test.config.Protocol != cfg.Protocol { 495 t.Fatalf("%d: Failed to match protocol. expected: %v, got: %v", 496 i, test.config.Protocol, cfg.Protocol) 497 } 498 if test.config.Passcode != cfg.Passcode { 499 t.Fatalf("%d: Failed to match passcode. expected: %v, got: %v", 500 i, test.config.Passcode, cfg.Passcode) 501 } 502 if test.config.PasscodeInPassword != cfg.PasscodeInPassword { 503 t.Fatalf("%d: Failed to match passcodeInPassword. expected: %v, got: %v", 504 i, test.config.PasscodeInPassword, cfg.PasscodeInPassword) 505 } 506 if test.config.Authenticator != cfg.Authenticator { 507 t.Fatalf("%d: Failed to match Authenticator. expected: %v, got: %v", 508 i, test.config.Authenticator.String(), cfg.Authenticator.String()) 509 } 510 if test.config.Authenticator == AuthTypeOkta && *test.config.OktaURL != *cfg.OktaURL { 511 t.Fatalf("%d: Failed to match okta URL. expected: %v, got: %v", 512 i, test.config.OktaURL, cfg.OktaURL) 513 } 514 if test.config.OCSPFailOpen != cfg.OCSPFailOpen { 515 t.Fatalf("%d: Failed to match OCSPFailOpen. expected: %v, got: %v", 516 i, test.config.OCSPFailOpen, cfg.OCSPFailOpen) 517 } 518 if test.ocspMode != cfg.ocspMode() { 519 t.Fatalf("%d: Failed to match OCSPMode. expected: %v, got: %v", 520 i, test.ocspMode, cfg.ocspMode()) 521 } 522 if test.config.ValidateDefaultParameters != cfg.ValidateDefaultParameters { 523 t.Fatalf("%d: Failed to match ValidateDefaultParameters. expected: %v, got: %v", 524 i, test.config.ValidateDefaultParameters, cfg.ValidateDefaultParameters) 525 } 526 case test.err != nil: 527 driverErrE, okE := test.err.(*SnowflakeError) 528 driverErrG, okG := err.(*SnowflakeError) 529 if okE && !okG || !okE && okG { 530 t.Fatalf("%d: Wrong error. expected: %v, got: %v", i, test.err, err) 531 } 532 if okE && okG { 533 if driverErrE.Number != driverErrG.Number { 534 t.Fatalf("%d: Wrong error number. expected: %v, got: %v", i, driverErrE.Number, driverErrG.Number) 535 } 536 } else { 537 t1 := reflect.TypeOf(err) 538 t2 := reflect.TypeOf(test.err) 539 if t1 != t2 { 540 t.Fatalf("%d: Wrong error. expected: %T:%v, got: %T:%v", i, test.err, test.err, err, err) 541 } 542 } 543 } 544 } 545} 546 547type tcDSN struct { 548 cfg *Config 549 dsn string 550 err error 551} 552 553func TestDSN(t *testing.T) { 554 tmfmt := "MM-DD-YYYY" 555 556 testcases := []tcDSN{ 557 { 558 cfg: &Config{ 559 User: "u", 560 Password: "p", 561 Account: "a-aofnadsf.somewhere.azure", 562 }, 563 dsn: "u:p@a-aofnadsf.somewhere.azure.snowflakecomputing.com:443?ocspFailOpen=true®ion=somewhere.azure&validateDefaultParameters=true", 564 }, 565 { 566 cfg: &Config{ 567 User: "u", 568 Password: "p", 569 Account: "a-aofnadsf.global", 570 }, 571 dsn: "u:p@a-aofnadsf.global.snowflakecomputing.com:443?ocspFailOpen=true®ion=global&validateDefaultParameters=true", 572 }, 573 { 574 cfg: &Config{ 575 User: "u", 576 Password: "p", 577 Account: "a-aofnadsf.global", 578 Region: "us-west-2", 579 }, 580 dsn: "u:p@a-aofnadsf.global.snowflakecomputing.com:443?ocspFailOpen=true®ion=global&validateDefaultParameters=true", 581 }, 582 { 583 cfg: &Config{ 584 User: "u", 585 Password: "p", 586 Account: "a-aofnadsf.global", 587 Region: "r", 588 }, 589 err: ErrInvalidRegion, 590 }, 591 { 592 cfg: &Config{ 593 User: "u", 594 Password: "p", 595 Account: "a", 596 }, 597 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=true&validateDefaultParameters=true", 598 }, 599 { 600 cfg: &Config{ 601 User: "u", 602 Password: "p", 603 Account: "a", 604 Region: "us-west-2", 605 }, 606 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=true&validateDefaultParameters=true", 607 }, 608 { 609 cfg: &Config{ 610 User: "u", 611 Password: "p", 612 Account: "a", 613 Region: "r", 614 }, 615 dsn: "u:p@a.r.snowflakecomputing.com:443?ocspFailOpen=true®ion=r&validateDefaultParameters=true", 616 }, 617 { 618 cfg: &Config{ 619 User: "", 620 Password: "p", 621 Account: "a", 622 }, 623 err: ErrEmptyUsername, 624 }, 625 { 626 cfg: &Config{ 627 User: "u", 628 Password: "", 629 Account: "a", 630 }, 631 err: ErrEmptyPassword, 632 }, 633 { 634 cfg: &Config{ 635 User: "u", 636 Password: "p", 637 Account: "", 638 }, 639 err: ErrEmptyAccount, 640 }, 641 { 642 cfg: &Config{ 643 User: "u", 644 Password: "p", 645 Account: "a.e", 646 }, 647 dsn: "u:p@a.e.snowflakecomputing.com:443?ocspFailOpen=true®ion=e&validateDefaultParameters=true", 648 }, 649 { 650 cfg: &Config{ 651 User: "u", 652 Password: "p", 653 Account: "a.e", 654 Region: "us-west-2", 655 }, 656 dsn: "u:p@a.e.snowflakecomputing.com:443?ocspFailOpen=true®ion=e&validateDefaultParameters=true", 657 }, 658 { 659 cfg: &Config{ 660 User: "u", 661 Password: "p", 662 Account: "a.e", 663 Region: "r", 664 }, 665 err: ErrInvalidRegion, 666 }, 667 { 668 cfg: &Config{ 669 User: "u", 670 Password: "p", 671 Account: "a", 672 Database: "db", 673 Schema: "sc", 674 Role: "ro", 675 Region: "b", 676 Authenticator: AuthTypeSnowflake, 677 Passcode: "db", 678 PasscodeInPassword: true, 679 LoginTimeout: 10 * time.Second, 680 RequestTimeout: 300 * time.Second, 681 Application: "special go", 682 }, 683 dsn: "u:p@a.b.snowflakecomputing.com:443?application=special+go&database=db&loginTimeout=10&ocspFailOpen=true&passcode=db&passcodeInPassword=true®ion=b&requestTimeout=300&role=ro&schema=sc&validateDefaultParameters=true", 684 }, 685 { 686 cfg: &Config{ 687 User: "u", 688 Password: "p", 689 Account: "a", 690 Authenticator: AuthTypeExternalBrowser, 691 }, 692 dsn: "u:p@a.snowflakecomputing.com:443?authenticator=externalbrowser&ocspFailOpen=true&validateDefaultParameters=true", 693 }, 694 { 695 cfg: &Config{ 696 User: "u", 697 Password: "p", 698 Account: "a", 699 Authenticator: AuthTypeOkta, 700 OktaURL: &url.URL{ 701 Scheme: "https", 702 Host: "sc.okta.com", 703 }, 704 }, 705 dsn: "u:p@a.snowflakecomputing.com:443?authenticator=https%3A%2F%2Fsc.okta.com&ocspFailOpen=true&validateDefaultParameters=true", 706 }, 707 { 708 cfg: &Config{ 709 User: "u", 710 Password: "p", 711 Account: "a.e", 712 Params: map[string]*string{ 713 "TIMESTAMP_OUTPUT_FORMAT": &tmfmt, 714 }, 715 }, 716 dsn: "u:p@a.e.snowflakecomputing.com:443?TIMESTAMP_OUTPUT_FORMAT=MM-DD-YYYY&ocspFailOpen=true®ion=e&validateDefaultParameters=true", 717 }, 718 { 719 cfg: &Config{ 720 User: "u", 721 Password: ":@abc", 722 Account: "a.e", 723 Params: map[string]*string{ 724 "TIMESTAMP_OUTPUT_FORMAT": &tmfmt, 725 }, 726 }, 727 dsn: "u:%3A%40abc@a.e.snowflakecomputing.com:443?TIMESTAMP_OUTPUT_FORMAT=MM-DD-YYYY&ocspFailOpen=true®ion=e&validateDefaultParameters=true", 728 }, 729 { 730 cfg: &Config{ 731 User: "u", 732 Password: "p", 733 Account: "a", 734 OCSPFailOpen: OCSPFailOpenTrue, 735 }, 736 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=true&validateDefaultParameters=true", 737 }, 738 { 739 cfg: &Config{ 740 User: "u", 741 Password: "p", 742 Account: "a", 743 OCSPFailOpen: OCSPFailOpenFalse, 744 }, 745 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=false&validateDefaultParameters=true", 746 }, 747 { 748 cfg: &Config{ 749 User: "u", 750 Password: "p", 751 Account: "a", 752 ValidateDefaultParameters: ConfigBoolFalse, 753 }, 754 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=true&validateDefaultParameters=false", 755 }, 756 { 757 cfg: &Config{ 758 User: "u", 759 Password: "p", 760 Account: "a", 761 ValidateDefaultParameters: ConfigBoolTrue, 762 }, 763 dsn: "u:p@a.snowflakecomputing.com:443?ocspFailOpen=true&validateDefaultParameters=true", 764 }, 765 { 766 cfg: &Config{ 767 User: "u", 768 Password: "p", 769 Account: "a", 770 InsecureMode: true, 771 }, 772 dsn: "u:p@a.snowflakecomputing.com:443?insecureMode=true&ocspFailOpen=true&validateDefaultParameters=true", 773 }, 774 { 775 cfg: &Config{ 776 User: "u", 777 Password: "p", 778 Account: "a.b.c", 779 }, 780 dsn: "u:p@a.b.c.snowflakecomputing.com:443?ocspFailOpen=true®ion=b.c&validateDefaultParameters=true", 781 }, 782 { 783 cfg: &Config{ 784 User: "u", 785 Password: "p", 786 Account: "a.b.c", 787 Region: "us-west-2", 788 }, 789 dsn: "u:p@a.b.c.snowflakecomputing.com:443?ocspFailOpen=true®ion=b.c&validateDefaultParameters=true", 790 }, 791 { 792 cfg: &Config{ 793 User: "u", 794 Password: "p", 795 Account: "a.b.c", 796 Region: "r", 797 }, 798 err: ErrInvalidRegion, 799 }, 800 } 801 for _, test := range testcases { 802 dsn, err := DSN(test.cfg) 803 if test.err == nil && err == nil { 804 if dsn != test.dsn { 805 t.Errorf("failed to get DSN. expected: %v, got:\n %v", test.dsn, dsn) 806 } 807 _, err := ParseDSN(dsn) 808 if err != nil { 809 t.Errorf("failed to parse DSN. dsn: %v, err: %v", dsn, err) 810 } 811 continue 812 } 813 if test.err != nil && err == nil { 814 t.Errorf("expected error. dsn: %v, err: %v", test.dsn, test.err) 815 continue 816 } 817 if err != nil && test.err == nil { 818 t.Errorf("failed to match. err: %v", err) 819 continue 820 } 821 } 822} 823