Fork of daniellemaywood.uk/gleam — Wasm codegen work
2

Configure Feed

Select the types of activity you want to include in your feed.

1// SPDX-License-Identifier: Apache-2.0 2// SPDX-FileCopyrightText: 2021 The Gleam contributors 3 4use crate::assert_js; 5 6#[test] 7fn case_on_error() { 8 assert_js!( 9 r#" 10fn a_result() { Error(1) } 11 12pub fn main() { 13 case a_result() { 14 Error(_) -> 1 15 _ -> 2 16 } 17}"# 18 ); 19} 20 21#[test] 22fn tuple_and_guard() { 23 assert_js!( 24 r#" 25pub fn go(x) { 26 case #(1, 2) { 27 #(1, a) if a == 2 -> 1 28 #(_, _) -> 2 29 } 30} 31"#, 32 ) 33} 34 35#[test] 36fn guard_variable_only_brought_into_scope_when_needed() { 37 assert_js!( 38 r#" 39pub fn go(x) { 40 case x { 41 // We want `a` to be defined before the guard check, and 42 // `b` to be defined only if the predicate on a matches! 43 [a, b] if a == 1 -> a + b 44 _ -> 2 45 } 46} 47"# 48 ) 49} 50 51// https://github.com/gleam-lang/gleam/issues/4221 52#[test] 53fn guard_variable_only_brought_into_scope_when_needed_1() { 54 assert_js!( 55 r#" 56pub fn main() { 57 case 1 { 58 i if i == 1 -> True 59 i if i < 2 -> True 60 _ -> False 61 } 62} 63"# 64 ) 65} 66 67// https://github.com/gleam-lang/gleam/issues/1187 68#[test] 69fn pointless() { 70 assert_js!( 71 r#" 72pub fn go(x) { 73 case x { 74 _ -> x 75 } 76} 77"#, 78 ) 79} 80 81// https://github.com/gleam-lang/gleam/issues/1188 82#[test] 83fn following_todo() { 84 assert_js!( 85 r#" 86pub fn go(x) { 87 case x { 88 True -> todo 89 _ -> 1 90 } 91} 92"#, 93 ) 94} 95 96#[test] 97fn multi_subject_catch_all() { 98 assert_js!( 99 r#" 100pub fn go(x, y) { 101 case x, y { 102 True, True -> 1 103 _, _ -> 0 104 } 105} 106"#, 107 ) 108} 109 110#[test] 111fn multi_subject_or() { 112 assert_js!( 113 r#" 114pub fn go(x, y) { 115 case x, y { 116 True, _ | _, True -> 1 117 _, _ -> 0 118 } 119} 120"#, 121 ) 122} 123 124#[test] 125fn multi_subject_no_catch_all() { 126 assert_js!( 127 r#" 128pub fn go(x, y) { 129 case x, y { 130 True, _ -> 1 131 _, True -> 2 132 False, False -> 0 133 } 134} 135"#, 136 ) 137} 138 139#[test] 140fn multi_subject_subject_assignments() { 141 assert_js!( 142 r#" 143pub fn go() { 144 case True, False { 145 True, True -> 1 146 _, _ -> 0 147 } 148} 149"#, 150 ) 151} 152 153#[test] 154fn assignment() { 155 assert_js!( 156 r#" 157pub fn go(x) { 158 let y = case x { 159 True -> 1 160 _ -> 0 161 } 162 y 163} 164"#, 165 ) 166} 167 168#[test] 169fn preassign_assignment() { 170 assert_js!( 171 r#" 172pub fn go(x) { 173 let y = case x() { 174 True -> 1 175 _ -> 0 176 } 177 y 178} 179"#, 180 ) 181} 182 183// https://github.com/gleam-lang/gleam/issues/1237 184#[test] 185fn pipe() { 186 assert_js!( 187 r#" 188pub fn go(x, f) { 189 case x |> f { 190 0 -> 1 191 _ -> 2 192 } 193} 194"#, 195 ) 196} 197 198#[test] 199fn result() { 200 assert_js!( 201 r#" 202pub fn go(x) { 203 case x { 204 Ok(_) -> 1 205 Error(_) -> 0 206 } 207} 208"#, 209 ) 210} 211 212// https://github.com/gleam-lang/gleam/issues/1506 213#[test] 214fn called_case() { 215 assert_js!( 216 r#" 217pub fn go(x, y) { 218 case x { 219 0 -> y 220 _ -> y 221 }() 222} 223"#, 224 ) 225} 226 227// https://github.com/gleam-lang/gleam/issues/1978 228#[test] 229fn case_local_var_in_tuple() { 230 assert_js!( 231 r#" 232pub fn go(x, y) { 233 let z = False 234 case True { 235 x if #(x, z) == #(True, False) -> x 236 _ -> False 237 } 238} 239"#, 240 ) 241} 242 243// https://github.com/gleam-lang/gleam/issues/2665 244#[test] 245fn case_branches_guards_are_wrapped_in_parentheses() { 246 assert_js!( 247 r#" 248pub fn anything() -> a { 249 case [] { 250 [a] if False || True -> a 251 _ -> anything() 252 } 253} 254"#, 255 ) 256} 257 258// https://github.com/gleam-lang/gleam/issues/2759 259#[test] 260fn nested_string_prefix_match() { 261 assert_js!( 262 r#" 263pub fn main() { 264 case Ok(["a", "b c", "d"]) { 265 Ok(["a", "b " <> _, "d"]) -> 1 266 _ -> 1 267 } 268} 269"# 270 ); 271} 272 273// https://github.com/gleam-lang/gleam/issues/2759 274#[test] 275fn nested_string_prefix_match_that_would_crash_on_js() { 276 assert_js!( 277 r#" 278pub fn main() { 279 case Ok(["b c", "d"]) { 280 Ok(["b " <> _, "d"]) -> 1 281 _ -> 1 282 } 283} 284"# 285 ); 286} 287 288#[test] 289fn slicing_is_handled_properly_with_multiple_branches() { 290 assert_js!( 291 r#" 292pub fn main() { 293 case "12345" { 294 "0" <> rest -> rest 295 "123" <> rest -> rest 296 _ -> "" 297 } 298} 299"# 300 ) 301} 302 303// https://github.com/gleam-lang/gleam/issues/3379 304#[test] 305fn single_clause_variables() { 306 assert_js!( 307 r#" 308pub fn main() { 309 let text = "first defined" 310 case "defined again" { 311 text -> Nil 312 } 313 let text = "a third time" 314} 315"# 316 ) 317} 318 319// https://github.com/gleam-lang/gleam/issues/3379 320#[test] 321fn single_clause_variables_assigned() { 322 assert_js!( 323 r#" 324pub fn main() { 325 let text = "first defined" 326 let other = case "defined again" { 327 text -> Nil 328 } 329 let text = "a third time" 330} 331"# 332 ) 333} 334 335// https://github.com/gleam-lang/gleam/issues/3894 336#[test] 337fn nested_string_prefix_assignment() { 338 assert_js!( 339 r#" 340type Wibble { 341 Wibble(wobble: String) 342} 343 344pub fn main() { 345 let tmp = Wibble(wobble: "wibble") 346 case tmp { 347 Wibble(wobble: "w" as wibble <> rest) -> wibble <> rest 348 _ -> panic 349 } 350} 351"# 352 ) 353} 354 355#[test] 356fn deeply_nested_string_prefix_assignment() { 357 assert_js!( 358 r#" 359type Wibble { 360 Wibble(Wobble) 361} 362type Wobble { 363 Wobble(wabble: Wabble) 364} 365type Wabble { 366 Wabble(tuple: #(Int, String)) 367} 368 369pub fn main() { 370 let tmp = Wibble(Wobble(Wabble(#(42, "wibble")))) 371 case tmp { 372 Wibble(Wobble(Wabble(#(_int, "w" as wibble <> rest)))) -> wibble <> rest 373 _ -> panic 374 } 375} 376"# 377 ) 378} 379 380// https://github.com/gleam-lang/gleam/issues/4383 381#[test] 382fn record_update_in_pipeline_in_case_clause() { 383 assert_js!( 384 " 385pub type Wibble { 386 Wibble(wibble: Int, wobble: Int) 387} 388 389fn identity(x) { 390 x 391} 392 393pub fn go(x) { 394 case x { 395 Wibble(1, _) -> Wibble(..x, wibble: 4) |> identity 396 Wibble(_, 3) -> Wibble(..x, wobble: 10) |> identity 397 _ -> panic 398 } 399} 400" 401 ); 402} 403 404#[test] 405fn pattern_matching_on_aliased_result_constructor() { 406 assert_js!( 407 " 408import gleam.{Error as E, Ok as O} 409 410pub fn go(x) { 411 case x { 412 E(_) -> 1 413 O(_) -> 2 414 } 415} 416" 417 ); 418} 419 420#[test] 421fn list_with_guard() { 422 assert_js!( 423 " 424pub fn go(x) { 425 case x { 426 [] -> 0 427 [first, ..] if first < 10 -> first * 2 428 [first, ..] -> first 429 } 430} 431" 432 ); 433} 434 435#[test] 436fn list_with_guard_no_binding() { 437 assert_js!( 438 " 439pub fn go(x) { 440 case x { 441 [] -> 0 442 [first, ..] if 1 < 10 -> first * 2 443 [first, ..] -> first 444 } 445} 446" 447 ); 448} 449 450#[test] 451fn case_building_simple_value_matched_by_pattern() { 452 assert_js!( 453 "pub fn go(x) { 454 case x { 455 1 -> 2 456 n -> n 457 } 458}" 459 ) 460} 461 462#[test] 463fn case_building_list_matched_by_pattern() { 464 assert_js!( 465 "pub fn go(x) { 466 case x { 467 [] -> [] 468 [a, b] -> [a, b] 469 [1, ..rest] -> [1, ..rest] 470 _ -> x 471 } 472}" 473 ) 474} 475 476#[test] 477fn case_building_record_matched_by_pattern() { 478 assert_js!( 479 "pub fn go(x) { 480 case x { 481 Ok(1) -> Ok(1) 482 Ok(n) -> Ok(n) 483 Error(_) -> Error(Nil) 484 } 485}" 486 ) 487} 488 489#[test] 490fn case_building_record_with_select_matched_by_pattern() { 491 assert_js!( 492 " 493import gleam 494 495pub fn go(x) { 496 case x { 497 Ok(1) -> gleam.Ok(1) 498 _ -> Error(Nil) 499 } 500}" 501 ) 502} 503 504#[test] 505fn case_building_record_with_select_matched_by_pattern_2() { 506 assert_js!( 507 " 508import gleam 509 510pub fn go(x) { 511 case x { 512 gleam.Ok(1) -> gleam.Ok(1) 513 _ -> Error(Nil) 514 } 515}" 516 ) 517} 518 519#[test] 520fn case_building_record_with_select_matched_by_pattern_3() { 521 assert_js!( 522 " 523import gleam 524 525pub fn go(x) { 526 case x { 527 gleam.Ok(1) -> Ok(1) 528 _ -> Error(Nil) 529 } 530}" 531 ) 532} 533 534#[test] 535fn case_building_matched_string_1() { 536 assert_js!( 537 r#" 538import gleam 539 540pub fn go(x) { 541 case x { 542 "a" <> rest -> "a" <> rest 543 _ -> "" 544 } 545}"# 546 ) 547} 548 549#[test] 550fn case_building_matched_string_2() { 551 assert_js!( 552 r#" 553import gleam 554 555pub fn go(x) { 556 case x { 557 "a" as a <> rest -> a <> rest 558 _ -> "" 559 } 560}"# 561 ) 562} 563 564#[test] 565fn case_building_matched_value_wrapped_in_block() { 566 assert_js!( 567 r#" 568import gleam 569 570pub fn go(x) { 571 case x { 572 1 -> { 1 } 573 _ -> 2 574 } 575}"# 576 ) 577} 578 579#[test] 580fn case_building_matched_value_alias() { 581 assert_js!( 582 r#" 583import gleam 584 585pub fn go(x) { 586 case x { 587 Ok(_) as a -> a 588 Error(Nil) -> Error(Nil) 589 } 590}"# 591 ) 592} 593 594#[test] 595fn case_building_matched_value_alias_2() { 596 assert_js!( 597 r#" 598import gleam 599 600pub fn go(x) { 601 case x { 602 Ok(1) as a -> Ok(1) 603 Ok(_) -> Ok(2) 604 Error(Nil) -> Error(Nil) 605 } 606}"# 607 ) 608} 609 610#[test] 611fn case_building_matched_value_alias_3() { 612 assert_js!( 613 r#" 614import gleam 615 616pub fn go(x) { 617 case x { 618 Ok(1 as a) -> Ok(a) 619 Ok(_) -> Ok(2) 620 Error(Nil) -> Error(Nil) 621 } 622}"# 623 ) 624} 625 626#[test] 627fn case_building_matched_no_variant_record() { 628 assert_js!( 629 r#" 630pub fn go(x) { 631 case x { 632 Ok(Nil) -> Ok(Nil) 633 _ -> Error(Nil) 634 } 635}"# 636 ) 637} 638 639#[test] 640fn case_building_matched_no_variant_record_2() { 641 assert_js!( 642 r#" 643import gleam 644 645pub fn go(x) { 646 case x { 647 Ok(gleam.Nil) -> Ok(Nil) 648 _ -> Error(Nil) 649 } 650}"# 651 ) 652} 653 654#[test] 655fn case_building_matched_no_variant_record_3() { 656 assert_js!( 657 r#" 658import gleam 659 660pub fn go(x) { 661 case x { 662 Ok(Nil) -> Ok(gleam.Nil) 663 _ -> Error(Nil) 664 } 665}"# 666 ) 667} 668 669#[test] 670fn case_building_matched_no_variant_record_4() { 671 assert_js!( 672 r#" 673import gleam 674 675pub fn go(x) { 676 case x { 677 Ok(gleam.Nil) -> Ok(gleam.Nil) 678 _ -> Error(Nil) 679 } 680}"# 681 ) 682} 683 684#[test] 685fn case_building_record_with_labels_matched_by_pattern_1() { 686 assert_js!( 687 " 688pub type Wibble { 689 Wibble(int: Int, string: String) 690 Wobble(Int) 691} 692 693pub fn go(x) { 694 case x { 695 Wibble(1, s) -> Wibble(1, s) 696 _ -> Wobble(1) 697 } 698}" 699 ) 700} 701 702#[test] 703fn case_building_record_with_labels_matched_by_pattern_2() { 704 assert_js!( 705 " 706pub type Wibble { 707 Wibble(int: Int, string: String) 708 Wobble(Int) 709} 710 711pub fn go(x) { 712 case x { 713 Wibble(string:, int:) -> Wibble(string:, int:) 714 _ -> Wobble(1) 715 } 716}" 717 ) 718} 719 720#[test] 721fn case_building_record_with_labels_matched_by_pattern_3() { 722 assert_js!( 723 " 724pub type Wibble { 725 Wibble(int: Int, string: String) 726 Wobble(Int) 727} 728 729pub fn go(x) { 730 case x { 731 // This should not be optimised away! 732 Wibble(string:, int:) -> Wibble(string:, int: 1) 733 _ -> Wobble(1) 734 } 735}" 736 ) 737} 738 739#[test] 740fn case_building_record_with_labels_matched_by_pattern_4() { 741 assert_js!( 742 " 743pub type Wibble { 744 Wibble(int: Int, string: String) 745 Wobble(Int) 746} 747 748pub fn go(x) { 749 case x { 750 Wibble(string:, int:) -> Wibble(int:, string:) 751 _ -> Wobble(1) 752 } 753}" 754 ) 755} 756 757#[test] 758fn case_building_record_with_labels_matched_by_pattern_5() { 759 assert_js!( 760 " 761pub type Wibble { 762 Wibble(int: Int, string: String) 763 Wobble(Int) 764} 765 766pub fn go(x) { 767 case x { 768 Wibble(string:, int: 1) -> Wibble(1, string:) 769 _ -> Wobble(1) 770 } 771}" 772 ) 773} 774 775#[test] 776fn case_building_record_with_labels_matched_by_pattern_6() { 777 assert_js!( 778 " 779pub type Wibble { 780 Wibble(int: Int, string: String) 781 Wobble(Int) 782} 783 784pub fn go(x) { 785 case x { 786 Wibble(1, string:) -> Wibble(string:, int: 1) 787 _ -> Wobble(1) 788 } 789}" 790 ) 791} 792 793#[test] 794fn case_with_multiple_subjects_building_simple_value_matched_by_pattern() { 795 assert_js!( 796 "pub fn go(x) { 797 case x, x + 1 { 798 1, _ -> 2 799 _, n -> n 800 } 801}" 802 ) 803} 804 805#[test] 806fn case_with_multiple_subjects_building_list_matched_by_pattern() { 807 assert_js!( 808 "pub fn go(n, x) { 809 case n, x { 810 1, [] -> [] 811 _, [a, b] -> [a, b] 812 3, [1, ..rest] -> [1, ..rest] 813 _, _ -> x 814 } 815}" 816 ) 817} 818 819#[test] 820fn case_with_multiple_subjects_building_record_matched_by_pattern() { 821 assert_js!( 822 "pub fn go(x, y) { 823 case x, y { 824 Ok(1), Error(_) -> Ok(1) 825 Error(_), Ok(n) -> Ok(n) 826 _, _ -> Error(Nil) 827 } 828}" 829 ) 830} 831 832#[test] 833fn case_with_multiple_subjects_building_same_value_as_two_subjects_one_is_picked() { 834 assert_js!( 835 " 836import gleam 837 838pub fn go(x, y) { 839 case x, y { 840 gleam.Ok(1), Ok(1) -> Ok(1) 841 _, Error(Nil) -> Error(Nil) 842 _, _ -> Error(Nil) 843 } 844}" 845 ) 846} 847 848#[test] 849fn interfering_string_pattern_succeeds_if_succeeding() { 850 assert_js!( 851 r#" 852pub fn wibble(bits) { 853 case bits { 854 <<"aaa", 0, _:bits>> -> 1 855 // If the first one succeeds, so will the second check, so it won't be 856 // performed twice inside the first if branch! 857 <<"aaa", 1, _:bits>> -> 2 858 _ -> 3 859 } 860}"# 861 ); 862} 863 864#[test] 865fn string_concatenation_in_clause_guards() { 866 assert_js!( 867 r#" 868pub fn main() { 869 let wibble = "wob" 870 case wibble { 871 x if x <> "ble" == "wobble" -> 1 872 _ -> 0 873 } 874}"# 875 ); 876} 877 878#[test] 879fn var_true() { 880 assert_js!( 881 r#" 882fn true() { True } 883pub fn main() { 884 let true_ = true() 885 assert 0 == case Nil { 886 _ if true_ -> 0 887 _ -> 1 888 } 889} 890"# 891 ) 892} 893 894#[test] 895// https://github.com/gleam-lang/gleam/issues/5283 896fn duplicate_name_for_variables_used_in_guards() { 897 assert_js!( 898 r#" 899pub fn wibble() { 900 let a = case 1337 { 901 n if n == 1347 -> Nil 902 _ -> Nil 903 } 904 let b = case 1337 { 905 n -> Nil 906 } 907}"# 908 ) 909} 910 911#[test] 912// https://github.com/gleam-lang/gleam/issues/5283 913fn duplicate_name_for_variables_used_in_guards_shadowing_outer_name() { 914 assert_js!( 915 r#" 916pub fn wibble() { 917 let n = 1 918 let a = case 1337 { 919 n if n == 1347 -> n 920 _ -> n 921 } 922 let b = case 1337 { 923 n -> Nil 924 } 925}"# 926 ) 927} 928 929#[test] 930fn directly_matching_case_subject() { 931 assert_js!( 932 r#" 933pub fn go() { 934 let x = "ABC" 935 case True { 936 True -> { 937 let x = 79 938 0 939 } 940 False -> { 941 let x = True 942 0 943 } 944 } 945 x 946}"# 947 ) 948} 949 950// https://github.com/gleam-lang/gleam/issues/5400 951#[test] 952fn case_matching_single_character_prefixes() { 953 assert_js!( 954 r#" 955pub fn parse_digit(s: String) -> Int { 956 case s { 957 "0" <> s -> 0 958 "1" <> s -> 1 959 "2" <> s -> 2 960 "3" <> s -> 3 961 "4" <> s -> 4 962 "5" <> s -> 5 963 "6" <> s -> 6 964 "7" <> s -> 7 965 "8" <> s -> 8 966 "9" <> s -> 9 967 "" -> todo 968 _ -> panic 969 } 970} 971"# 972 ); 973} 974 975// https://github.com/gleam-lang/gleam/issues/5467 976#[test] 977fn no_duplicate_let_after_directly_matching_case() { 978 assert_js!( 979 r#" 980pub fn go() { 981 let x = 982 case #(1, 2) { 983 #(1, b) -> b 984 #(_, b) -> b 985 } 986 987 let #(a, _b) = #(x, 3) 988 989 a 990}"# 991 ) 992} 993 994// https://github.com/gleam-lang/gleam/issues/5743 995#[test] 996fn no_duplicate_pipe_variable_with_case_in_pipeline() { 997 assert_js!( 998 r#" 999pub fn main() { 1000 0 1001 |> case True { 1002 True -> add_one |> identity 1003 False -> add_one 1004 } 1005 |> add_one 1006} 1007 1008fn identity(x) { 1009 x 1010} 1011 1012fn add_one(x) { 1013 x + 1 1014}"# 1015 ) 1016} 1017 1018#[test] 1019fn list_with_tail_used_in_guard() { 1020 assert_js!( 1021 r#" 1022pub fn go(x: List(Int), y: List(Int)) { 1023 case x { 1024 [1, ..x] if [1, 2, ..x] == y -> True 1025 _ -> False 1026 } 1027}"# 1028 ) 1029} 1030 1031// https://github.com/gleam-lang/gleam/issues/5612 1032#[test] 1033fn no_duplicate_let_after_case_with_same_named_variable_with_declaration_before_and_after() { 1034 assert_js!( 1035 r#" 1036pub fn go() { 1037 let x = 0 1038 let x = x 1039 let x = case #(1, 2) { 1040 #(_, x) -> x 1041 } 1042 1043 let x = x 1044 x 1045}"# 1046 ) 1047} 1048 1049// https://github.com/gleam-lang/gleam/issues/5612 1050#[test] 1051fn no_duplicate_let_after_case_with_same_named_variable() { 1052 assert_js!( 1053 r#" 1054pub fn go() { 1055 let x = case #(1, 2) { 1056 #(_, x) -> x 1057 } 1058 1059 x 1060}"# 1061 ) 1062} 1063 1064// https://github.com/gleam-lang/gleam/issues/5748 1065#[test] 1066fn no_duplicate_let_when_rebinding_variable_after_directly_matching_case() { 1067 assert_js!( 1068 r#" 1069pub fn go() { 1070 let n = 1 1071 case True { 1072 True -> { 1073 let n = 99 1074 n 1075 } 1076 False -> 0 1077 } 1078 let n = n + 5 1079 n 1080}"# 1081 ) 1082} 1083 1084#[test] 1085fn semicolon_exists_with_directly_matching_case() { 1086 assert_js!( 1087 r#" 1088pub fn go() { 1089 case #(1, 2) { 1090 #(a, _) -> a 1091 } 1092 {2 + 4} * 2 1093}"# 1094 ) 1095} 1096 1097#[test] 1098fn semicolon_exists_with_case() { 1099 assert_js!( 1100 r#" 1101pub fn go() { 1102 case #(1, 2) { 1103 #(2, b) -> b 1104 #(1, 3) -> 2 1105 #(a, _) -> a 1106 } 1107 {2 + 4} * 2 1108}"# 1109 ) 1110}