trackler 2.1.0.12 → 2.1.0.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (83) hide show
  1. checksums.yaml +4 -4
  2. data/common/exercises/difference-of-squares/canonical-data.json +15 -21
  3. data/lib/trackler/version.rb +1 -1
  4. data/tracks/c/config.json +9 -0
  5. data/tracks/c/exercises/scrabble-score/makefile +16 -0
  6. data/tracks/c/exercises/scrabble-score/src/example.c +43 -0
  7. data/tracks/c/exercises/scrabble-score/src/example.h +6 -0
  8. data/tracks/c/exercises/scrabble-score/test/test_scrabble_score.c +77 -0
  9. data/tracks/c/exercises/scrabble-score/test/vendor/unity.c +1300 -0
  10. data/tracks/c/exercises/scrabble-score/test/vendor/unity.h +274 -0
  11. data/tracks/c/exercises/scrabble-score/test/vendor/unity_internals.h +701 -0
  12. data/tracks/csharp/exercises/grade-school/Example.cs +1 -1
  13. data/tracks/csharp/exercises/grade-school/GradeSchoolTest.cs +8 -8
  14. data/tracks/elixir/README.md +29 -12
  15. data/tracks/elixir/SETUP.md +0 -1
  16. data/tracks/elixir/docs/ABOUT.md +21 -7
  17. data/tracks/elixir/docs/LEARNING.md +4 -2
  18. data/tracks/elixir/docs/RESOURCES.md +2 -2
  19. data/tracks/elixir/docs/TESTS.md +0 -2
  20. data/tracks/go/exercises/atbash-cipher/.meta/gen.go +61 -0
  21. data/tracks/go/exercises/atbash-cipher/atbash_cipher_test.go +1 -16
  22. data/tracks/go/exercises/atbash-cipher/cases_test.go +61 -0
  23. data/tracks/go/exercises/atbash-cipher/example.go +1 -1
  24. data/tracks/java/exercises/hamming/src/main/java/Hamming.java +9 -0
  25. data/tracks/java/exercises/simple-linked-list/src/test/java/SimpleLinkedListTest.java +4 -4
  26. data/tracks/javascript/docs/TESTS.md +1 -1
  27. data/tracks/ocaml/config.json +5 -0
  28. data/tracks/ocaml/exercises/acronym/test.ml +2 -0
  29. data/tracks/ocaml/exercises/all-your-base/test.ml +2 -0
  30. data/tracks/ocaml/exercises/anagram/test.ml +2 -0
  31. data/tracks/ocaml/exercises/atbash-cipher/test.ml +3 -0
  32. data/tracks/ocaml/exercises/beer-song/test.ml +2 -0
  33. data/tracks/ocaml/exercises/binary-search/.merlin +5 -0
  34. data/tracks/ocaml/exercises/binary-search/Makefile +11 -0
  35. data/tracks/ocaml/exercises/binary-search/binary_search.mli +2 -0
  36. data/tracks/ocaml/exercises/binary-search/example.ml +19 -0
  37. data/tracks/ocaml/exercises/binary-search/test.ml +38 -0
  38. data/tracks/ocaml/exercises/bob/test.ml +2 -0
  39. data/tracks/ocaml/exercises/bowling/test.ml +2 -0
  40. data/tracks/ocaml/exercises/bracket-push/test.ml +2 -0
  41. data/tracks/ocaml/exercises/change/test.ml +2 -0
  42. data/tracks/ocaml/exercises/connect/test.ml +2 -0
  43. data/tracks/ocaml/exercises/difference-of-squares/test.ml +10 -8
  44. data/tracks/ocaml/exercises/dominoes/test.ml +2 -0
  45. data/tracks/ocaml/exercises/etl/test.ml +2 -0
  46. data/tracks/ocaml/exercises/hamming/test.ml +2 -0
  47. data/tracks/ocaml/exercises/hello-world/test.ml +2 -0
  48. data/tracks/ocaml/exercises/leap/test.ml +2 -0
  49. data/tracks/ocaml/exercises/luhn/test.ml +2 -0
  50. data/tracks/ocaml/exercises/minesweeper/test.ml +2 -0
  51. data/tracks/ocaml/exercises/pangram/test.ml +2 -0
  52. data/tracks/ocaml/exercises/phone-number/test.ml +2 -0
  53. data/tracks/ocaml/exercises/prime-factors/test.ml +2 -0
  54. data/tracks/ocaml/exercises/raindrops/test.ml +2 -0
  55. data/tracks/ocaml/exercises/roman-numerals/test.ml +2 -0
  56. data/tracks/ocaml/exercises/run-length-encoding/test.ml +2 -0
  57. data/tracks/ocaml/exercises/say/test.ml +2 -0
  58. data/tracks/ocaml/exercises/space-age/test.ml +2 -0
  59. data/tracks/ocaml/exercises/triangle/test.ml +2 -0
  60. data/tracks/ocaml/exercises/word-count/test.ml +2 -0
  61. data/tracks/ocaml/tools/test-generator/src/controller.ml +15 -5
  62. data/tracks/ocaml/tools/test-generator/src/model.ml +5 -0
  63. data/tracks/ocaml/tools/test-generator/src/parser.ml +5 -4
  64. data/tracks/ocaml/tools/test-generator/src/special_cases.ml +12 -0
  65. data/tracks/ocaml/tools/test-generator/templates/binary-search/template.ml +20 -0
  66. data/tracks/ocaml/tools/test-generator/templates/change/template.ml +2 -2
  67. data/tracks/ocaml/tools/test-generator/templates/say/template.ml +1 -1
  68. data/tracks/ocaml/tools/test-generator/test/parser_test.ml +1 -1
  69. data/tracks/r/docs/TESTS.md +24 -4
  70. data/tracks/ruby/exercises/trinary/trinary_test.rb +1 -0
  71. data/tracks/scala/config.json +9 -0
  72. data/tracks/scala/exercises/accumulate/src/main/scala/Accumulate.scala +3 -0
  73. data/tracks/scala/exercises/bob/src/main/scala/Bob.scala +3 -0
  74. data/tracks/scala/exercises/difference-of-squares/src/main/scala/Squares.scala +8 -0
  75. data/tracks/scala/exercises/gigasecond/src/main/scala/Gigasecond.scala +8 -0
  76. data/tracks/scala/exercises/grade-school/src/main/scala/School.scala +11 -0
  77. data/tracks/scala/exercises/pangram/src/main/scala/Pangrams.scala +4 -0
  78. data/tracks/scala/exercises/protein-translation/build.sbt +3 -0
  79. data/tracks/scala/exercises/protein-translation/example.scala +41 -0
  80. data/tracks/scala/exercises/protein-translation/src/main/scala/.keep +0 -0
  81. data/tracks/scala/exercises/protein-translation/src/test/scala/ProteinTranslationTest.scala +59 -0
  82. data/tracks/scala/exercises/space-age/src/main/scala/SpaceAge.scala +10 -0
  83. metadata +28 -2
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open All_your_base
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.1" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Anagram
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Atbash_cipher
@@ -23,6 +25,7 @@ let encode_tests = [
23
25
  ae "gsvjf rxpyi ldmul cqfnk hlevi gsvoz abwlt" (encode "The quick brown fox jumps over the lazy dog.");
24
26
  ]
25
27
 
28
+
26
29
  let decode_tests = [
27
30
  "decode exercism" >::
28
31
  ae "exercism" (decode "vcvix rhn");
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Beer_song
@@ -0,0 +1,5 @@
1
+ PKG findlib
2
+ PKG core
3
+ PKG ounit
4
+ S *
5
+ B *
@@ -0,0 +1,11 @@
1
+ test: test.native
2
+ @./test.native
3
+
4
+ test.native: *.ml *.ml
5
+ @corebuild -r -quiet -pkg oUnit test.native
6
+
7
+ clean:
8
+ rm -rf _build
9
+ rm -f test.native
10
+
11
+ .PHONY: clean
@@ -0,0 +1,2 @@
1
+ (* Finds an int in an array of ints via binary search *)
2
+ val find : int array -> int -> int option
@@ -0,0 +1,19 @@
1
+ open Core.Std
2
+
3
+ let find array value =
4
+ let rec go lo hi =
5
+ if lo > hi then None
6
+ else begin
7
+ let mid = lo + (hi - lo) / 2 in
8
+ let mid_val = array.(mid) in
9
+ if mid_val < value
10
+ then go (mid + 1) hi
11
+ else if mid_val > value
12
+ then go lo (mid - 1)
13
+ else Some mid
14
+ end
15
+ in
16
+ if Array.is_empty array
17
+ then None
18
+ else go 0 (Array.length array - 1)
19
+
@@ -0,0 +1,38 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
3
+ open Core.Std
4
+ open OUnit2
5
+ open Binary_search
6
+
7
+ let option_to_string f = function
8
+ | None -> "None"
9
+ | Some x -> "Some " ^ f x
10
+
11
+ let ae exp got _test_ctxt =
12
+ assert_equal ~printer:(option_to_string Int.to_string) exp got
13
+
14
+ let tests = [
15
+ "finds a value in an array with one element" >::
16
+ ae (Some 0) (find [|6|] 6);
17
+ "finds a value in the middle of an array" >::
18
+ ae (Some 3) (find [|1; 3; 4; 6; 8; 9; 11|] 6);
19
+ "finds a value at the beginning of an array" >::
20
+ ae (Some 0) (find [|1; 3; 4; 6; 8; 9; 11|] 1);
21
+ "finds a value at the end of an array" >::
22
+ ae (Some 6) (find [|1; 3; 4; 6; 8; 9; 11|] 11);
23
+ "finds a value in an array of odd length" >::
24
+ ae (Some 9) (find [|1; 3; 5; 8; 13; 21; 34; 55; 89; 144; 233; 377; 634|] 144);
25
+ "finds a value in an array of even length" >::
26
+ ae (Some 5) (find [|1; 3; 5; 8; 13; 21; 34; 55; 89; 144; 233; 377|] 21);
27
+ "identifies that a value is not included in the array" >::
28
+ ae None (find [|1; 3; 4; 6; 8; 9; 11|] 7);
29
+ "a value smaller than the array's smallest value is not included" >::
30
+ ae None (find [|1; 3; 4; 6; 8; 9; 11|] 0);
31
+ "a value larger than the array's largest value is not included" >::
32
+ ae None (find [|1; 3; 4; 6; 8; 9; 11|] 13);
33
+ "nothing is included in an empty array" >::
34
+ ae None (find [||] 1);
35
+ ]
36
+
37
+ let () =
38
+ run_test_tt_main ("binary-search tests" >::: tests)
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Bob
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open! Core.Std
2
4
  open OUnit2
3
5
  open Bowling
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.1.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Bracket_push
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Change
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Connect
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.1.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Difference_of_squares
@@ -5,30 +7,30 @@ open Difference_of_squares
5
7
  let ae exp got _test_ctxt = assert_equal exp got
6
8
 
7
9
  let square_of_sum_tests = [
10
+ "square of sum 1" >::
11
+ ae 1 (square_of_sum 1);
8
12
  "square of sum 5" >::
9
13
  ae 225 (square_of_sum 5);
10
- "square of sum 10" >::
11
- ae 3025 (square_of_sum 10);
12
14
  "square of sum 100" >::
13
15
  ae 25502500 (square_of_sum 100);
14
16
  ]
15
17
 
18
+
16
19
  let sum_of_squares_tests = [
20
+ "sum of squares 1" >::
21
+ ae 1 (sum_of_squares 1);
17
22
  "sum of squares 5" >::
18
23
  ae 55 (sum_of_squares 5);
19
- "sum of squares 10" >::
20
- ae 385 (sum_of_squares 10);
21
24
  "sum of squares 100" >::
22
25
  ae 338350 (sum_of_squares 100);
23
26
  ]
24
27
 
28
+
25
29
  let difference_of_squares_tests = [
26
- "difference of squares 0" >::
27
- ae 0 (difference_of_squares 0);
30
+ "difference of squares 1" >::
31
+ ae 0 (difference_of_squares 1);
28
32
  "difference of squares 5" >::
29
33
  ae 170 (difference_of_squares 5);
30
- "difference of squares 10" >::
31
- ae 2640 (difference_of_squares 10);
32
34
  "difference of squares 100" >::
33
35
  ae 25164150 (difference_of_squares 100);
34
36
  ]
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.1" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Dominoes
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Etl
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
 
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Hello_world
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Leap
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Luhn
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Minesweeper
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Pangram
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.2.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Phone_number
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Prime_factors
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Raindrops
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Roman_numerals
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Run_length_encoding
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Say
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Space_age
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Triangle
@@ -1,3 +1,5 @@
1
+ (* Test/exercise version: "1.0.0" *)
2
+
1
3
  open Core.Std
2
4
  open OUnit2
3
5
  open Word_count
@@ -27,11 +27,16 @@ let combine_files (template_files: (string * content) list) (canonical_data_file
27
27
 
28
28
  (* pangram in the canonical data is a suite but it does not really need to be as there's only one group. Convert a Suite to
29
29
  a Single test in this case, to simplify the template. *)
30
- let simplify_single_test_suite (tests: tests): tests = match tests with
31
- | Suite [{name = name; cases = cases}] -> Single cases
32
- | x -> x
30
+ let simplify_single_test_suite (canonical_data: canonical_data): canonical_data = match canonical_data.tests with
31
+ | Suite [{name = name; cases = cases}] -> {version=canonical_data.version; tests=Single cases}
32
+ | _ -> canonical_data
33
33
 
34
- let generate_code ~(slug: string) ~(template_file: content) ~(canonical_data_file: content): (content, content) Result.t =
34
+
35
+ let prepend_version (v: string option) (str: string): string = match v with
36
+ | None -> str
37
+ | Some v -> "(* Test/exercise version: \"" ^ v ^ "\" *)\n\n" ^ str
38
+
39
+ let generate_code ~(slug: string) ~(template_file: content) ~(canonical_data_file: content): (content, string) Result.t =
35
40
  let open Result.Monad_infix in
36
41
  Result.of_option ~error:("cannot recognize file for " ^ slug ^ " as a template") @@ find_template template_file >>= fun template ->
37
42
  let edit_expected = edit_expected ~stringify:json_to_string ~slug in
@@ -40,11 +45,12 @@ let generate_code ~(slug: string) ~(template_file: content) ~(canonical_data_fil
40
45
  let file_text = template.file_text in
41
46
  let file_lines = String.split_lines file_text |> List.to_array in
42
47
  parse_json_text canonical_data_file (expected_key_name slug) (cases_name slug)
43
- |> Result.map_error ~f:show_error >>| simplify_single_test_suite >>= (function
48
+ |> Result.map_error ~f:show_error >>| simplify_single_test_suite >>= fun cd -> (match cd.tests with
44
49
  | Single cases ->
45
50
  let template = to_single template.template in
46
51
  fill_in_template template.template slug cases
47
52
  |> fill_tests file_text template
53
+ |> prepend_version cd.version
48
54
  |> Result.return
49
55
  | Suite tests ->
50
56
  let suites = to_multi template.template in
@@ -56,6 +62,7 @@ let generate_code ~(slug: string) ~(template_file: content) ~(canonical_data_fil
56
62
  in
57
63
  List.map tests ~f:fill_suite_tests |> sequence >>=
58
64
  fill_suite template
65
+ |> Result.map ~f:(prepend_version cd.version)
59
66
  )
60
67
 
61
68
  let output_tests (files: (string * content * content) list) (output_folder: string) ~(generated_folder: string): unit =
@@ -69,6 +76,9 @@ let output_tests (files: (string * content * content) list) (output_folder: stri
69
76
  | Error e -> print_endline ("Failed when generating " ^ slug ^ ", error: " ^ e) in
70
77
  List.iter files ~f:output1
71
78
 
79
+ (*let add_header (canonical_data_folder: string) (generated: string): string =*)
80
+
81
+
72
82
  let run ~(templates_folder: string) ~(canonical_data_folder: string) ~(output_folder: string) ~(generated_folder: string) (filter: string option) =
73
83
  let template_files = find_template_files templates_folder filter in
74
84
  let canonical_data_files = find_canonical_data_files canonical_data_folder in
@@ -15,6 +15,11 @@ type tests =
15
15
  | Single of case list
16
16
  | Suite of test list
17
17
 
18
+ type canonical_data = {
19
+ version: string option;
20
+ tests: tests
21
+ }
22
+
18
23
  let rec json_to_string (j: json): string = match j with
19
24
  | `Null -> "null"
20
25
  | `String s -> "\"" ^ (String.escaped s) ^ "\""
@@ -69,13 +69,14 @@ let parse_cases_from_suite name suite expected_key cases_key =
69
69
  to_list_note ExpectingListOfCases >>= fun tests ->
70
70
  List.map tests ~f:(parse_case expected_key) |> sequence
71
71
 
72
- let parse_json_text (text: string) (expected_key: string) (cases_key: string): (tests, error) Result.t =
72
+ let parse_json_text (text: string) (expected_key: string) (cases_key: string): (canonical_data, error) Result.t =
73
73
  let open Result.Monad_infix in
74
74
  let json = from_string text in
75
+ let version = member "version" json |> to_string_option in
75
76
  match suite_cases json cases_key with
76
- | Ok suite_cases -> Ok (Suite suite_cases)
77
- | Error _ -> parse_single text expected_key cases_key
78
-
77
+ | Ok suite_cases -> Ok {version; tests=(Suite suite_cases)}
78
+ | Error _ -> parse_single text expected_key cases_key >>= fun tests -> Ok {version; tests}
79
+
79
80
  let show_error = function
80
81
  | TestMustHaveKeyCalledCases name -> "Test named '" ^ name ^ "' is expected to have an object with a key: 'cases'"
81
82
  | ExpectingMapForCase -> "Expected a json map for a test case"
@@ -67,6 +67,7 @@ let edit_expected ~(stringify: json -> string) ~(slug: string) ~(value: json) =
67
67
  | "connect" -> edit_connect_expected value
68
68
  | "change" -> edit_change_expected value
69
69
  | "bowling" -> edit_bowling_expected value
70
+ | "binary-search" -> optional_int ~none:(-1) value
70
71
  | _ -> stringify value
71
72
 
72
73
  let edit_say (ps: (string * json) list) =
@@ -106,6 +107,16 @@ let edit_bowling (ps: (string * json) list): (string * string) list =
106
107
  | (k, v) -> (k, json_to_string v) in
107
108
  List.map ps ~f:edit
108
109
 
110
+ let edit_binary_search (ps: (string * json) list): (string * string) list =
111
+ let open Yojson.Basic.Util in
112
+ let as_array_string xs =
113
+ let xs = to_list xs |> List.map ~f:to_int |> List.map ~f:Int.to_string in
114
+ "[|" ^ String.concat ~sep:"; " xs ^ "|]" in
115
+ let edit = function
116
+ | ("array", v) -> ("array", as_array_string v)
117
+ | (k, v) -> (k, json_to_string v) in
118
+ List.map ps ~f:edit
119
+
109
120
  let edit_parameters ~(slug: string) (parameters: (string * json) list) = match (slug, parameters) with
110
121
  | ("hello-world", ps) -> default_value ~key:"name" ~value:"None" (optional_strings ~f:(fun _x -> true) parameters)
111
122
  | ("say", ps) -> edit_say ps
@@ -113,6 +124,7 @@ let edit_parameters ~(slug: string) (parameters: (string * json) list) = match (
113
124
  | ("dominoes", ps) -> edit_dominoes ps
114
125
  | ("space-age", ps) -> edit_space_age ps
115
126
  | ("bowling", ps) -> edit_bowling ps
127
+ | ("binary-search", ps) -> edit_binary_search ps
116
128
  | (_, ps) -> map_elements json_to_string ps
117
129
 
118
130
  let expected_key_name slug = match slug with