Repository: hedyorg/hedy

Issue:
[BUG] Translation code does not preserve == symbol
PR #1580 has created the exact same issue as we had in #1579 but for `==`.
[BUG] Cannot use boolean operators with number comparisons 
**Describe the bug**
Starting from level 14 number comparison operators are introduced, but they can't be used with boolean operators.

**Paste the Hedy code & level**
Level 14
This gives a parsing error
```
age = ask 'How old are you?'
if age >= 0 and age < 18
    print 'You are a minor!'
else
    print 'You are OLD!'
```

**Expected behavior**
Comparisons operators should work with boolean operators.



Discussion:
Maybe you can pick this up too @racertop? No rush at all of course since we are not even using the translation code in production!
Hi! Yes :) no problem!


Resolving patch:
diff --git a/hedy.py b/hedy.py
--- a/hedy.py
+++ b/hedy.py
@@ -521,6 +521,12 @@ def equality_check(self, tree):
         rules = [int_to_float, int_to_string, float_to_string] if self.level < 12 else [int_to_float]
         self.validate_binary_command_args_type(Command.equality, tree, rules)
         return self.to_typed_tree(tree, HedyType.boolean)
+    
+    def equality_check_is(self, tree):
+        return self.equality_check(tree)
+    
+    def equality_check_equals(self, tree):
+        return self.equality_check(tree)
 
     def repeat_list(self, tree):
         self.save_type_to_lookup(tree.children[0].children[0], HedyType.any)
@@ -1346,8 +1352,11 @@ def equality_check(self, args):
 
         return f"str({arg0}) == str({arg1})"
 
-        #TODO if we start using fstrings here, this str can go
+    def equality_check_is(self, args):
+        return self.equality_check(args)
 
+    def equality_check_equals(self, args):
+        return self.equality_check(args)
 
     def assign(self, args):
         parameter = args[0]
@@ -1611,6 +1620,8 @@ def process_comparison(self, args, operator):
         else:
             return f"{simple_comparison} and {args[2]}"
 
+    def equality_check_dequals(self, args):
+        return super().equality_check(args)
 
     def smaller(self, args):
         return self.process_comparison(args, "<")
diff --git a/hedy_translation.py b/hedy_translation.py
--- a/hedy_translation.py
+++ b/hedy_translation.py
@@ -248,6 +248,12 @@ def list_access_var_is(self, args):
         var = args[0]
         var_list = args[1]
         return var + " " + self.keywords["is"] + " " + var_list + " " + self.keywords["at"]  + " " + args[2]
+    
+    def equality_check_is(self, args):
+        return args[0] + " " + self.keywords["is"] + " " + " ".join([str(c) for c in args[1:]]) + " "
+
+    def equality_check_equals(self, args):
+        return args[0] + " = ".join([str(c) for c in args[1:]]) + " "
 
 @hedy_translator(level=7)
 class ConvertToLang7(ConvertToLang6):
@@ -269,9 +275,12 @@ def ifs(self, args):
     def elses(self, args):
         return self.keywords["else"] + indent(args[0:])
 
-    def equality_check(self, args):
+    def equality_check_is(self, args):
         return args[0] + " " + self.keywords["is"] + " " + " ".join([str(c) for c in args[1:]])
 
+    def equality_check_equals(self, args):
+        return args[0] + " = " + " ".join([str(c) for c in args[1:]])
+
     def end_block(self, args):
         return args
 
@@ -320,6 +329,9 @@ def in_list_check(self, args):
 @hedy_translator(level=14)
 class ConvertToLang14(ConvertToLang13):
 
+    def equality_check_dequals(self, args):
+       return args[0] + " == " + " ".join([str(c) for c in args[1:]])     
+
     def bigger(self, args):
         return args[0] + " > " + args[1]
 


Test patch:
diff --git a/tests/test_level_14.py b/tests/test_level_14.py
--- a/tests/test_level_14.py
+++ b/tests/test_level_14.py
@@ -170,6 +170,36 @@ def test_if_with_double_equals(self):
       expected=expected,
       max_level=16)
 
+
+  @parameterized.expand(HedyTester.comparison_commands)
+  def test_comparisons_with_boolean(self, comparison):
+    code = textwrap.dedent(f"""\
+      leeftijd is ask 'Hoe oud ben jij?'
+      if leeftijd {comparison} 12 or leeftijd {comparison} 15
+          print 'Dan ben je jonger dan ik!'
+      if leeftijd {comparison} 12 and leeftijd {comparison} 15
+          print 'Some other string!'""")
+      
+    expected = textwrap.dedent(f"""\
+      leeftijd = input(f'Hoe oud ben jij?')
+      try:
+        leeftijd = int(leeftijd)
+      except ValueError:
+        try:
+          leeftijd = float(leeftijd)
+        except ValueError:
+          pass
+      if str(leeftijd).zfill(100){comparison}str(12).zfill(100) or str(leeftijd).zfill(100){comparison}str(15).zfill(100):
+        print(f'Dan ben je jonger dan ik!')
+      if str(leeftijd).zfill(100){comparison}str(12).zfill(100) and str(leeftijd).zfill(100){comparison}str(15).zfill(100):
+        print(f'Some other string!')""")
+
+    self.multi_level_tester(
+      code=code,
+      max_level=16,
+      expected=expected,
+    )
+
   @parameterized.expand([
     ("'text'", '1'),      # text and number
     ('1, 2', '1'),        # list and number
diff --git a/tests/test_translation_level_14.py b/tests/test_translation_level_14.py
--- a/tests/test_translation_level_14.py
+++ b/tests/test_translation_level_14.py
@@ -82,4 +82,18 @@ def test_not_equal(self):
         als hedy != 6
             print 'hedy'""")
 
+        self.assertEqual(expected, result)
+    
+    def test_double_equals(self):
+        code = textwrap.dedent("""\
+        hedy = 5
+        if hedy == 6
+            print 'hedy'""")
+
+        result = hedy_translation.translate_keywords(code, from_lang="en", to_lang="nl", level=self.level)
+        expected = textwrap.dedent("""\
+        hedy = 5
+        als hedy == 6
+            print 'hedy'""")
+
         self.assertEqual(expected, result)
\ No newline at end of file