trackler 2.2.1.74 → 2.2.1.75

Sign up to get free protection for your applications and to get access to all the features.
Files changed (227) hide show
  1. checksums.yaml +4 -4
  2. data/fixtures/tracks/fruit/docs/something.md +0 -0
  3. data/lib/trackler/version.rb +1 -1
  4. data/problem-specifications/README.md +8 -4
  5. data/problem-specifications/exercises/acronym/canonical-data.json +19 -7
  6. data/problem-specifications/exercises/all-your-base/canonical-data.json +106 -64
  7. data/problem-specifications/exercises/allergies/canonical-data.json +37 -13
  8. data/tracks/c/config.json +176 -176
  9. data/tracks/clojure/config.json +17 -1
  10. data/tracks/clojure/exercises/isbn-verifier/README.md +43 -0
  11. data/tracks/clojure/exercises/isbn-verifier/project.clj +4 -0
  12. data/tracks/clojure/exercises/isbn-verifier/src/example.clj +17 -0
  13. data/tracks/clojure/exercises/isbn-verifier/src/isbn_verifier.clj +3 -0
  14. data/tracks/clojure/exercises/isbn-verifier/test/isbn_verifier_test.clj +42 -0
  15. data/tracks/clojure/exercises/proverb/README.md +15 -0
  16. data/tracks/clojure/exercises/proverb/project.clj +4 -0
  17. data/tracks/clojure/exercises/proverb/src/example.clj +15 -0
  18. data/tracks/clojure/exercises/proverb/src/proverb.clj +3 -0
  19. data/tracks/clojure/exercises/proverb/test/proverb_test.clj +14 -0
  20. data/tracks/common-lisp/docs/LEARNING.md +4 -3
  21. data/tracks/common-lisp/docs/RESOURCES.md +11 -0
  22. data/tracks/delphi/.gitignore +1 -0
  23. data/tracks/delphi/config.json +24 -0
  24. data/tracks/delphi/docs/INSTALLATION.md +1 -1
  25. data/tracks/delphi/exercises/isbn-verifier/ISBNVerifier.dpr +60 -0
  26. data/tracks/delphi/exercises/isbn-verifier/README.md +68 -0
  27. data/tracks/delphi/exercises/isbn-verifier/uISBNVerifierExample.pas +46 -0
  28. data/tracks/delphi/exercises/isbn-verifier/uTestISBNVerifier.pas +136 -0
  29. data/tracks/delphi/exercises/secret-handshake/README.md +56 -0
  30. data/tracks/delphi/exercises/secret-handshake/SecretHandshake.dpr +60 -0
  31. data/tracks/delphi/exercises/secret-handshake/uSecretHandshakeExample.pas +56 -0
  32. data/tracks/delphi/exercises/secret-handshake/uTestSecretHandshake.pas +215 -0
  33. data/tracks/ecmascript/docs/ABOUT.md +13 -9
  34. data/tracks/factor/exercises/two-fer/README.md +1 -1
  35. data/tracks/fsharp/docs/RESOURCES.md +1 -1
  36. data/tracks/fsharp/generators/{Input.fs → CanonicalData.fs} +5 -10
  37. data/tracks/fsharp/generators/Exercise.fs +11 -10
  38. data/tracks/fsharp/generators/{Output.fs → Formatting.fs} +2 -56
  39. data/tracks/fsharp/generators/Generators.fs +93 -93
  40. data/tracks/fsharp/generators/Generators.fsproj +9 -4
  41. data/tracks/fsharp/generators/Options.fs +1 -1
  42. data/tracks/fsharp/generators/Program.fs +3 -3
  43. data/tracks/fsharp/generators/Rendering.fs +57 -0
  44. data/tracks/go/exercises/all-your-base/.meta/gen.go +80 -0
  45. data/tracks/go/exercises/all-your-base/.meta/hints.md +13 -0
  46. data/tracks/go/exercises/all-your-base/README.md +16 -1
  47. data/tracks/go/exercises/all-your-base/all_your_base_test.go +12 -163
  48. data/tracks/go/exercises/all-your-base/cases_test.go +183 -0
  49. data/tracks/go/exercises/all-your-base/example.go +25 -29
  50. data/tracks/java/CONTRIBUTING.md +1 -1
  51. data/tracks/java/POLICIES.md +15 -1
  52. data/tracks/java/exercises/flatten-array/.meta/hints.md +58 -0
  53. data/tracks/java/exercises/flatten-array/README.md +62 -0
  54. data/tracks/java/exercises/hamming/src/main/java/Hamming.java +1 -1
  55. data/tracks/java/exercises/matrix/.meta/src/reference/java/Matrix.java +6 -6
  56. data/tracks/java/exercises/meetup/.meta/src/reference/java/Meetup.java +2 -2
  57. data/tracks/java/exercises/meetup/.meta/src/reference/java/MeetupSchedule.java +1 -1
  58. data/tracks/java/exercises/meetup/src/main/java/MeetupSchedule.java +1 -1
  59. data/tracks/java/exercises/pig-latin/.meta/hints.md +58 -0
  60. data/tracks/java/exercises/pig-latin/README.md +61 -0
  61. data/tracks/java/exercises/reverse-string/src/main/java/ReverseString.java +2 -2
  62. data/tracks/java/exercises/secret-handshake/README.md +1 -1
  63. data/tracks/javascript/.eslintignore +0 -3
  64. data/tracks/javascript/exercises/food-chain/example.js +50 -37
  65. data/tracks/javascript/exercises/octal/example.js +1 -1
  66. data/tracks/javascript/exercises/robot-name/robot-name.spec.js +7 -7
  67. data/tracks/javascript/package-lock.json +1846 -0
  68. data/tracks/python/docs/EXERCISE_README_INSERT.md +15 -0
  69. data/tracks/python/exercises/accumulate/README.md +15 -0
  70. data/tracks/python/exercises/acronym/README.md +15 -0
  71. data/tracks/python/exercises/all-your-base/README.md +15 -0
  72. data/tracks/python/exercises/all-your-base/all_your_base_test.py +19 -9
  73. data/tracks/python/exercises/allergies/README.md +15 -0
  74. data/tracks/python/exercises/alphametics/README.md +15 -0
  75. data/tracks/python/exercises/anagram/README.md +15 -0
  76. data/tracks/python/exercises/atbash-cipher/README.md +15 -0
  77. data/tracks/python/exercises/beer-song/README.md +16 -1
  78. data/tracks/python/exercises/binary-search-tree/README.md +16 -2
  79. data/tracks/python/exercises/binary-search/README.md +15 -0
  80. data/tracks/python/exercises/binary-search/binary_search_test.py +14 -4
  81. data/tracks/python/exercises/binary/README.md +15 -0
  82. data/tracks/python/exercises/binary/binary_test.py +14 -4
  83. data/tracks/python/exercises/bob/README.md +15 -0
  84. data/tracks/python/exercises/book-store/README.md +15 -0
  85. data/tracks/python/exercises/bracket-push/README.md +15 -0
  86. data/tracks/python/exercises/change/README.md +15 -0
  87. data/tracks/python/exercises/circular-buffer/README.md +15 -0
  88. data/tracks/python/exercises/circular-buffer/circular_buffer_test.py +15 -5
  89. data/tracks/python/exercises/circular-buffer/example.py +2 -2
  90. data/tracks/python/exercises/clock/README.md +15 -0
  91. data/tracks/python/exercises/collatz-conjecture/.meta/hints.md +1 -1
  92. data/tracks/python/exercises/collatz-conjecture/README.md +15 -0
  93. data/tracks/python/exercises/complex-numbers/README.md +15 -0
  94. data/tracks/python/exercises/connect/README.md +18 -3
  95. data/tracks/python/exercises/crypto-square/README.md +15 -0
  96. data/tracks/python/exercises/diamond/README.md +15 -0
  97. data/tracks/python/exercises/difference-of-squares/README.md +15 -0
  98. data/tracks/python/exercises/diffie-hellman/README.md +14 -0
  99. data/tracks/python/exercises/dominoes/README.md +16 -1
  100. data/tracks/python/exercises/error-handling/README.md +17 -0
  101. data/tracks/python/exercises/error-handling/error_handling_test.py +13 -3
  102. data/tracks/python/exercises/error-handling/example.py +1 -1
  103. data/tracks/python/exercises/etl/README.md +16 -1
  104. data/tracks/python/exercises/flatten-array/README.md +15 -0
  105. data/tracks/python/exercises/food-chain/README.md +15 -0
  106. data/tracks/python/exercises/forth/README.md +15 -0
  107. data/tracks/python/exercises/forth/example.py +7 -9
  108. data/tracks/python/exercises/forth/forth_test.py +107 -17
  109. data/tracks/python/exercises/gigasecond/README.md +15 -0
  110. data/tracks/python/exercises/go-counting/README.md +21 -3
  111. data/tracks/python/exercises/grade-school/README.md +15 -0
  112. data/tracks/python/exercises/grains/README.md +15 -0
  113. data/tracks/python/exercises/grains/grains_test.py +16 -6
  114. data/tracks/python/exercises/grep/README.md +15 -0
  115. data/tracks/python/exercises/hamming/README.md +15 -0
  116. data/tracks/python/exercises/hamming/hamming_test.py +12 -2
  117. data/tracks/python/exercises/hello-world/README.md +15 -0
  118. data/tracks/python/exercises/hexadecimal/README.md +15 -0
  119. data/tracks/python/exercises/hexadecimal/hexadecimal_test.py +11 -1
  120. data/tracks/python/exercises/house/README.md +16 -1
  121. data/tracks/python/exercises/isogram/README.md +15 -0
  122. data/tracks/python/exercises/kindergarten-garden/README.md +18 -3
  123. data/tracks/python/exercises/largest-series-product/README.md +15 -0
  124. data/tracks/python/exercises/largest-series-product/largest_series_product_test.py +14 -4
  125. data/tracks/python/exercises/leap/README.md +15 -0
  126. data/tracks/python/exercises/linked-list/README.md +15 -0
  127. data/tracks/python/exercises/list-ops/README.md +15 -0
  128. data/tracks/python/exercises/luhn/README.md +15 -0
  129. data/tracks/python/exercises/markdown/README.md +18 -0
  130. data/tracks/python/exercises/matrix/README.md +15 -0
  131. data/tracks/python/exercises/meetup/README.md +31 -12
  132. data/tracks/python/exercises/meetup/meetup_test.py +11 -1
  133. data/tracks/python/exercises/minesweeper/README.md +15 -0
  134. data/tracks/python/exercises/minesweeper/minesweeper_test.py +12 -2
  135. data/tracks/python/exercises/nth-prime/README.md +15 -0
  136. data/tracks/python/exercises/nth-prime/nth_prime_test.py +11 -1
  137. data/tracks/python/exercises/nucleotide-count/README.md +17 -2
  138. data/tracks/python/exercises/nucleotide-count/nucleotide_count_test.py +11 -1
  139. data/tracks/python/exercises/ocr-numbers/README.md +16 -1
  140. data/tracks/python/exercises/ocr-numbers/ocr_numbers_test.py +12 -2
  141. data/tracks/python/exercises/octal/README.md +15 -0
  142. data/tracks/python/exercises/octal/octal_test.py +16 -3
  143. data/tracks/python/exercises/palindrome-products/README.md +16 -1
  144. data/tracks/python/exercises/pangram/README.md +15 -0
  145. data/tracks/python/exercises/pascals-triangle/README.md +16 -1
  146. data/tracks/python/exercises/perfect-numbers/README.md +15 -0
  147. data/tracks/python/exercises/perfect-numbers/perfect_numbers_test.py +13 -3
  148. data/tracks/python/exercises/phone-number/README.md +16 -2
  149. data/tracks/python/exercises/phone-number/example.py +1 -1
  150. data/tracks/python/exercises/phone-number/phone_number_test.py +17 -7
  151. data/tracks/python/exercises/pig-latin/README.md +15 -0
  152. data/tracks/python/exercises/point-mutations/README.md +15 -0
  153. data/tracks/python/exercises/poker/README.md +15 -0
  154. data/tracks/python/exercises/pov/README.md +20 -2
  155. data/tracks/python/exercises/pov/example.py +2 -2
  156. data/tracks/python/exercises/pov/pov_test.py +15 -5
  157. data/tracks/python/exercises/prime-factors/README.md +15 -0
  158. data/tracks/python/exercises/protein-translation/README.md +15 -0
  159. data/tracks/python/exercises/protein-translation/protein_translation_test.py +10 -0
  160. data/tracks/python/exercises/proverb/README.md +14 -0
  161. data/tracks/python/exercises/pythagorean-triplet/README.md +15 -0
  162. data/tracks/python/exercises/pythagorean-triplet/pythagorean_triplet_test.py +11 -1
  163. data/tracks/python/exercises/queen-attack/README.md +15 -0
  164. data/tracks/python/exercises/queen-attack/queen_attack_test.py +17 -7
  165. data/tracks/python/exercises/rail-fence-cipher/README.md +15 -0
  166. data/tracks/python/exercises/raindrops/README.md +15 -0
  167. data/tracks/python/exercises/react/README.md +15 -1
  168. data/tracks/python/exercises/rectangles/README.md +24 -9
  169. data/tracks/python/exercises/rna-transcription/.meta/hints.md +1 -0
  170. data/tracks/python/exercises/rna-transcription/README.md +18 -5
  171. data/tracks/python/exercises/rna-transcription/rna_transcription_test.py +13 -3
  172. data/tracks/python/exercises/robot-name/README.md +15 -0
  173. data/tracks/python/exercises/robot-simulator/README.md +15 -0
  174. data/tracks/python/exercises/roman-numerals/README.md +15 -0
  175. data/tracks/python/exercises/rotational-cipher/README.md +15 -0
  176. data/tracks/python/exercises/run-length-encoding/README.md +15 -0
  177. data/tracks/python/exercises/saddle-points/README.md +15 -0
  178. data/tracks/python/exercises/saddle-points/saddle_points_test.py +11 -1
  179. data/tracks/python/exercises/say/README.md +15 -0
  180. data/tracks/python/exercises/say/say_test.py +12 -2
  181. data/tracks/python/exercises/scale-generator/README.md +15 -0
  182. data/tracks/python/exercises/scale-generator/example.py +3 -3
  183. data/tracks/python/exercises/scale-generator/scale_generator_test.py +11 -1
  184. data/tracks/python/exercises/scrabble-score/README.md +15 -0
  185. data/tracks/python/exercises/secret-handshake/README.md +16 -1
  186. data/tracks/python/exercises/series/README.md +15 -0
  187. data/tracks/python/exercises/series/series_test.py +12 -2
  188. data/tracks/python/exercises/sieve/README.md +15 -0
  189. data/tracks/python/exercises/simple-cipher/.meta/hints.md +6 -6
  190. data/tracks/python/exercises/simple-cipher/README.md +17 -1
  191. data/tracks/python/exercises/simple-cipher/simple_cipher_test.py +12 -2
  192. data/tracks/python/exercises/simple-linked-list/{hints.md → .meta/hints.md} +10 -10
  193. data/tracks/python/exercises/simple-linked-list/README.md +16 -0
  194. data/tracks/python/exercises/simple-linked-list/example.py +2 -2
  195. data/tracks/python/exercises/simple-linked-list/simple_linked_list_test.py +13 -3
  196. data/tracks/python/exercises/space-age/README.md +15 -0
  197. data/tracks/python/exercises/strain/README.md +16 -3
  198. data/tracks/python/exercises/sublist/README.md +15 -0
  199. data/tracks/python/exercises/sum-of-multiples/README.md +18 -3
  200. data/tracks/python/exercises/tournament/README.md +15 -0
  201. data/tracks/python/exercises/transpose/README.md +15 -0
  202. data/tracks/python/exercises/tree-building/README.md +30 -0
  203. data/tracks/python/exercises/tree-building/example.py +3 -5
  204. data/tracks/python/exercises/tree-building/tree_building_test.py +16 -6
  205. data/tracks/python/exercises/triangle/README.md +15 -0
  206. data/tracks/python/exercises/triangle/example.py +1 -1
  207. data/tracks/python/exercises/triangle/triangle_test.py +15 -5
  208. data/tracks/python/exercises/trinary/README.md +15 -0
  209. data/tracks/python/exercises/twelve-days/README.md +15 -0
  210. data/tracks/python/exercises/two-bucket/README.md +22 -7
  211. data/tracks/python/exercises/two-fer/README.md +16 -0
  212. data/tracks/python/exercises/variable-length-quantity/README.md +15 -0
  213. data/tracks/python/exercises/variable-length-quantity/variable_length_quantity_test.py +12 -2
  214. data/tracks/python/exercises/word-count/README.md +15 -0
  215. data/tracks/python/exercises/word-search/README.md +15 -0
  216. data/tracks/python/exercises/wordy/README.md +15 -0
  217. data/tracks/python/exercises/wordy/wordy_test.py +14 -4
  218. data/tracks/python/exercises/zebra-puzzle/README.md +15 -0
  219. data/tracks/python/exercises/zipper/README.md +16 -3
  220. data/tracks/rust/config.json +11 -0
  221. data/tracks/rust/exercises/saddle-points/.gitignore +8 -0
  222. data/tracks/rust/exercises/saddle-points/Cargo.toml +5 -0
  223. data/tracks/rust/exercises/saddle-points/README.md +66 -0
  224. data/tracks/rust/exercises/saddle-points/example.rs +24 -0
  225. data/tracks/rust/exercises/saddle-points/src/lib.rs +3 -0
  226. data/tracks/rust/exercises/saddle-points/tests/saddle-points.rs +60 -0
  227. metadata +38 -5
@@ -1,5 +1,5 @@
1
1
  def handle_error_by_throwing_exception():
2
- raise Exception()
2
+ raise Exception("Meaningful message describing the source of the error")
3
3
 
4
4
 
5
5
  def handle_error_by_returning_none(input_data):
@@ -1,4 +1,4 @@
1
- # Etl
1
+ # ETL
2
2
 
3
3
  We are going to do the `Transform` step of an Extract-Transform-Load.
4
4
 
@@ -46,6 +46,21 @@ variety of languages, each with its own unique scoring table. For
46
46
  example, an "E" is scored at 2 in the Māori-language version of the
47
47
  game while being scored at 4 in the Hawaiian-language version.
48
48
 
49
+ ## Exception messages
50
+
51
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
52
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
53
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
54
+ a message.
55
+
56
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
57
+ `raise Exception`, you shold write:
58
+
59
+ ```python
60
+ raise Exception("Meaningful message indicating the source of the error")
61
+ ```
62
+
63
+
49
64
  ## Submitting Exercises
50
65
 
51
66
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
@@ -10,6 +10,21 @@ input: [1,[2,3,null,4],[null],5]
10
10
 
11
11
  output: [1,2,3,4,5]
12
12
 
13
+ ## Exception messages
14
+
15
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
16
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
17
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
18
+ a message.
19
+
20
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
21
+ `raise Exception`, you shold write:
22
+
23
+ ```python
24
+ raise Exception("Meaningful message indicating the source of the error")
25
+ ```
26
+
27
+
13
28
  ## Submitting Exercises
14
29
 
15
30
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
@@ -63,6 +63,21 @@ I know an old lady who swallowed a horse.
63
63
  She's dead, of course!
64
64
  ```
65
65
 
66
+ ## Exception messages
67
+
68
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
69
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
70
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
71
+ a message.
72
+
73
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
74
+ `raise Exception`, you shold write:
75
+
76
+ ```python
77
+ raise Exception("Meaningful message indicating the source of the error")
78
+ ```
79
+
80
+
66
81
  ## Submitting Exercises
67
82
 
68
83
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
@@ -25,6 +25,21 @@ enough.)
25
25
 
26
26
  Words are case-insensitive.
27
27
 
28
+ ## Exception messages
29
+
30
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
31
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
32
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
33
+ a message.
34
+
35
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
36
+ `raise Exception`, you shold write:
37
+
38
+ ```python
39
+ raise Exception("Meaningful message indicating the source of the error")
40
+ ```
41
+
42
+
28
43
  ## Submitting Exercises
29
44
 
30
45
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
@@ -20,7 +20,7 @@ def evaluate(input_data):
20
20
  values.pop(0)
21
21
  key = values.pop(0)
22
22
  if is_integer(key):
23
- raise ValueError()
23
+ raise ValueError("Integers cannot be redefined")
24
24
  defines[key] = values
25
25
  stack = []
26
26
  input_data = input_data[-1].split()
@@ -38,10 +38,10 @@ def evaluate(input_data):
38
38
  elif word == '*':
39
39
  stack.append(stack.pop() * stack.pop())
40
40
  elif word == '/':
41
- divider = stack.pop()
42
- if divider == 0:
43
- raise ZeroDivisionError()
44
- stack.append(int(stack.pop() / divider))
41
+ divisor = stack.pop()
42
+ if divisor == 0:
43
+ raise ZeroDivisionError("Attempted to divide by zero")
44
+ stack.append(int(stack.pop() / divisor))
45
45
  elif word == 'dup':
46
46
  stack.append(stack[-1])
47
47
  elif word == 'drop':
@@ -52,9 +52,7 @@ def evaluate(input_data):
52
52
  elif word == 'over':
53
53
  stack.append(stack[-2])
54
54
  else:
55
- raise ValueError()
56
- except ZeroDivisionError:
57
- raise
55
+ raise ValueError("{} has not been defined".format(word))
58
56
  except IndexError:
59
- raise StackUnderflowError()
57
+ raise StackUnderflowError("Insufficient number of items in stack")
60
58
  return stack
@@ -31,14 +31,24 @@ class ForthAdditionTest(unittest.TestCase):
31
31
 
32
32
  def test_errors_if_there_is_nothing_on_the_stack(self):
33
33
  input_data = ["+"]
34
- with self.assertRaises(StackUnderflowError):
34
+ with self.assertRaisesWithMessage(StackUnderflowError):
35
35
  evaluate(input_data)
36
36
 
37
37
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
38
38
  input_data = ["1 +"]
39
- with self.assertRaises(StackUnderflowError):
39
+ with self.assertRaisesWithMessage(StackUnderflowError):
40
40
  evaluate(input_data)
41
41
 
42
+ # Utility functions
43
+ def setUp(self):
44
+ try:
45
+ self.assertRaisesRegex = self.assertRaisesRegexp
46
+ except AttributeError:
47
+ pass
48
+
49
+ def assertRaisesWithMessage(self, exception):
50
+ return self.assertRaisesRegex(exception, r".+")
51
+
42
52
 
43
53
  class ForthSubtractionTest(unittest.TestCase):
44
54
  def test_can_subtract_two_numbers(self):
@@ -48,14 +58,24 @@ class ForthSubtractionTest(unittest.TestCase):
48
58
 
49
59
  def test_errors_if_there_is_nothing_on_the_stack(self):
50
60
  input_data = ["-"]
51
- with self.assertRaises(StackUnderflowError):
61
+ with self.assertRaisesWithMessage(StackUnderflowError):
52
62
  evaluate(input_data)
53
63
 
54
64
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
55
65
  input_data = ["1 -"]
56
- with self.assertRaises(StackUnderflowError):
66
+ with self.assertRaisesWithMessage(StackUnderflowError):
57
67
  evaluate(input_data)
58
68
 
69
+ # Utility functions
70
+ def setUp(self):
71
+ try:
72
+ self.assertRaisesRegex = self.assertRaisesRegexp
73
+ except AttributeError:
74
+ pass
75
+
76
+ def assertRaisesWithMessage(self, exception):
77
+ return self.assertRaisesRegex(exception, r".+")
78
+
59
79
 
60
80
  class ForthMultiplicationTest(unittest.TestCase):
61
81
  def test_can_multiply_two_numbers(self):
@@ -65,14 +85,24 @@ class ForthMultiplicationTest(unittest.TestCase):
65
85
 
66
86
  def test_errors_if_there_is_nothing_on_the_stack(self):
67
87
  input_data = ["*"]
68
- with self.assertRaises(StackUnderflowError):
88
+ with self.assertRaisesWithMessage(StackUnderflowError):
69
89
  evaluate(input_data)
70
90
 
71
91
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
72
92
  input_data = ["1 *"]
73
- with self.assertRaises(StackUnderflowError):
93
+ with self.assertRaisesWithMessage(StackUnderflowError):
74
94
  evaluate(input_data)
75
95
 
96
+ # Utility functions
97
+ def setUp(self):
98
+ try:
99
+ self.assertRaisesRegex = self.assertRaisesRegexp
100
+ except AttributeError:
101
+ pass
102
+
103
+ def assertRaisesWithMessage(self, exception):
104
+ return self.assertRaisesRegex(exception, r".+")
105
+
76
106
 
77
107
  class ForthDivisionTest(unittest.TestCase):
78
108
  def test_can_divide_two_numbers(self):
@@ -87,19 +117,29 @@ class ForthDivisionTest(unittest.TestCase):
87
117
 
88
118
  def test_errors_if_dividing_by_zero(self):
89
119
  input_data = ["4 0 /"]
90
- with self.assertRaises(ZeroDivisionError):
120
+ with self.assertRaisesWithMessage(ZeroDivisionError):
91
121
  evaluate(input_data)
92
122
 
93
123
  def test_errors_if_there_is_nothing_on_the_stack(self):
94
124
  input_data = ["/"]
95
- with self.assertRaises(StackUnderflowError):
125
+ with self.assertRaisesWithMessage(StackUnderflowError):
96
126
  evaluate(input_data)
97
127
 
98
128
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
99
129
  input_data = ["1 /"]
100
- with self.assertRaises(StackUnderflowError):
130
+ with self.assertRaisesWithMessage(StackUnderflowError):
101
131
  evaluate(input_data)
102
132
 
133
+ # Utility functions
134
+ def setUp(self):
135
+ try:
136
+ self.assertRaisesRegex = self.assertRaisesRegexp
137
+ except AttributeError:
138
+ pass
139
+
140
+ def assertRaisesWithMessage(self, exception):
141
+ return self.assertRaisesRegex(exception, r".+")
142
+
103
143
 
104
144
  class ForthCombinedArithmeticTest(unittest.TestCase):
105
145
  def test_addition_and_subtraction(self):
@@ -126,9 +166,19 @@ class ForthDupTest(unittest.TestCase):
126
166
 
127
167
  def test_errors_if_there_is_nothing_on_the_stack(self):
128
168
  input_data = ["dup"]
129
- with self.assertRaises(StackUnderflowError):
169
+ with self.assertRaisesWithMessage(StackUnderflowError):
130
170
  evaluate(input_data)
131
171
 
172
+ # Utility functions
173
+ def setUp(self):
174
+ try:
175
+ self.assertRaisesRegex = self.assertRaisesRegexp
176
+ except AttributeError:
177
+ pass
178
+
179
+ def assertRaisesWithMessage(self, exception):
180
+ return self.assertRaisesRegex(exception, r".+")
181
+
132
182
 
133
183
  class ForthDropTest(unittest.TestCase):
134
184
  def test_removes_the_top_value_on_the_stack_if_it_is_the_only_one(self):
@@ -148,9 +198,19 @@ class ForthDropTest(unittest.TestCase):
148
198
 
149
199
  def test_errors_if_there_is_nothing_on_the_stack(self):
150
200
  input_data = ["drop"]
151
- with self.assertRaises(StackUnderflowError):
201
+ with self.assertRaisesWithMessage(StackUnderflowError):
152
202
  evaluate(input_data)
153
203
 
204
+ # Utility functions
205
+ def setUp(self):
206
+ try:
207
+ self.assertRaisesRegex = self.assertRaisesRegexp
208
+ except AttributeError:
209
+ pass
210
+
211
+ def assertRaisesWithMessage(self, exception):
212
+ return self.assertRaisesRegex(exception, r".+")
213
+
154
214
 
155
215
  class ForthSwapTest(unittest.TestCase):
156
216
  def test_swaps_only_two_values_on_stack(self):
@@ -170,14 +230,24 @@ class ForthSwapTest(unittest.TestCase):
170
230
 
171
231
  def test_errors_if_there_is_nothing_on_the_stack(self):
172
232
  input_data = ["swap"]
173
- with self.assertRaises(StackUnderflowError):
233
+ with self.assertRaisesWithMessage(StackUnderflowError):
174
234
  evaluate(input_data)
175
235
 
176
236
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
177
237
  input_data = ["1 swap"]
178
- with self.assertRaises(StackUnderflowError):
238
+ with self.assertRaisesWithMessage(StackUnderflowError):
179
239
  evaluate(input_data)
180
240
 
241
+ # Utility functions
242
+ def setUp(self):
243
+ try:
244
+ self.assertRaisesRegex = self.assertRaisesRegexp
245
+ except AttributeError:
246
+ pass
247
+
248
+ def assertRaisesWithMessage(self, exception):
249
+ return self.assertRaisesRegex(exception, r".+")
250
+
181
251
 
182
252
  class ForthOverTest(unittest.TestCase):
183
253
  def test_copies_the_second_element_if_there_are_only_two(self):
@@ -197,14 +267,24 @@ class ForthOverTest(unittest.TestCase):
197
267
 
198
268
  def test_errors_if_there_is_nothing_on_the_stack(self):
199
269
  input_data = ["over"]
200
- with self.assertRaises(StackUnderflowError):
270
+ with self.assertRaisesWithMessage(StackUnderflowError):
201
271
  evaluate(input_data)
202
272
 
203
273
  def test_errors_if_there_is_only_one_value_on_the_stack(self):
204
274
  input_data = ["1 over"]
205
- with self.assertRaises(StackUnderflowError):
275
+ with self.assertRaisesWithMessage(StackUnderflowError):
206
276
  evaluate(input_data)
207
277
 
278
+ # Utility functions
279
+ def setUp(self):
280
+ try:
281
+ self.assertRaisesRegex = self.assertRaisesRegexp
282
+ except AttributeError:
283
+ pass
284
+
285
+ def assertRaisesWithMessage(self, exception):
286
+ return self.assertRaisesRegex(exception, r".+")
287
+
208
288
 
209
289
  class ForthUserDefinedWordsTest(unittest.TestCase):
210
290
  def test_can_consist_of_built_in_words(self):
@@ -258,14 +338,24 @@ class ForthUserDefinedWordsTest(unittest.TestCase):
258
338
 
259
339
  def test_cannot_redefine_numbers(self):
260
340
  input_data = [": 1 2 ;"]
261
- with self.assertRaises(ValueError):
341
+ with self.assertRaisesWithMessage(ValueError):
262
342
  evaluate(input_data)
263
343
 
264
344
  def test_errors_if_executing_a_non_existent_word(self):
265
345
  input_data = ["foo"]
266
- with self.assertRaises(ValueError):
346
+ with self.assertRaisesWithMessage(ValueError):
267
347
  evaluate(input_data)
268
348
 
349
+ # Utility functions
350
+ def setUp(self):
351
+ try:
352
+ self.assertRaisesRegex = self.assertRaisesRegexp
353
+ except AttributeError:
354
+ pass
355
+
356
+ def assertRaisesWithMessage(self, exception):
357
+ return self.assertRaisesRegex(exception, r".+")
358
+
269
359
 
270
360
  if __name__ == '__main__':
271
361
  unittest.main()
@@ -4,6 +4,21 @@ Calculate the moment when someone has lived for 10^9 seconds.
4
4
 
5
5
  A gigasecond is 10^9 (1,000,000,000) seconds.
6
6
 
7
+ ## Exception messages
8
+
9
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
10
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
11
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
12
+ a message.
13
+
14
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
15
+ `raise Exception`, you shold write:
16
+
17
+ ```python
18
+ raise Exception("Meaningful message indicating the source of the error")
19
+ ```
20
+
21
+
7
22
  ## Submitting Exercises
8
23
 
9
24
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
@@ -16,7 +16,7 @@ only horizontal and vertical neighbours count. In the following diagram
16
16
  the stones which matter are marked "O" and the stones that don't are
17
17
  marked "I" (ignored). Empty spaces represent empty intersections.
18
18
 
19
- ```
19
+ ```text
20
20
  +----+
21
21
  |IOOI|
22
22
  |O O|
@@ -33,12 +33,30 @@ For more information see
33
33
  [wikipedia](https://en.wikipedia.org/wiki/Go_%28game%29) or [Sensei's
34
34
  Library](http://senseis.xmp.net/).
35
35
 
36
+ ## Exception messages
37
+
38
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
39
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
40
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
41
+ a message.
42
+
43
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
44
+ `raise Exception`, you shold write:
45
+
46
+ ```python
47
+ raise Exception("Meaningful message indicating the source of the error")
48
+ ```
49
+
50
+
36
51
  ## Submitting Exercises
37
52
 
38
53
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.
39
54
 
40
55
  For example, if you're submitting `bob.py` for the Bob exercise, the submit command would be something like `exercism submit <path_to_exercism_dir>/python/bob/bob.py`.
41
56
 
57
+ For more detailed information about running tests, code style and linting,
58
+ please see the [help page](http://exercism.io/languages/python).
59
+
60
+
42
61
  ## Submitting Incomplete Solutions
43
- It's possible to submit an incomplete solution so you can see how others have completed the
44
- exercise.
62
+ It's possible to submit an incomplete solution so you can see how others have completed the exercise.
@@ -34,6 +34,21 @@ are some additional things you could try:
34
34
  Then please share your thoughts in a comment on the submission. Did this
35
35
  experiment make the code better? Worse? Did you learn anything from it?
36
36
 
37
+ ## Exception messages
38
+
39
+ Sometimes it is necessary to raise an exception. When you do this, you should include a meaningful error message to
40
+ indicate what the source of the error is. This makes your code more readable and helps significantly with debugging. Not
41
+ every exercise will require you to raise an exception, but for those that do, the tests will only pass if you include
42
+ a message.
43
+
44
+ To raise a message with an exception, just write it as an argument to the exception type. For example, instead of
45
+ `raise Exception`, you shold write:
46
+
47
+ ```python
48
+ raise Exception("Meaningful message indicating the source of the error")
49
+ ```
50
+
51
+
37
52
  ## Submitting Exercises
38
53
 
39
54
  Note that, when trying to submit an exercise, make sure the solution is in the `exercism/python/<exerciseName>` directory.