]> hydra-www.ietfng.org Git - dyna2/commitdiff
Address Issue #51 - showing errors in "Changes"
authorTim Vieira <tim.f.vieira@gmail.com>
Sun, 21 Jul 2013 12:30:15 +0000 (08:30 -0400)
committerTim Vieira <tim.f.vieira@gmail.com>
Sun, 21 Jul 2013 12:30:15 +0000 (08:30 -0400)
updated doctests, caught some cases of missing clear error.

run-doctests.py
src/Dyna/Backend/Python/interpreter.py
src/Dyna/Backend/Python/repl.py
test/error-handling/basics.dynadoc
test/error-handling/clearing.dynadoc
test/error-handling/clearing2.dynadoc
test/repl/boolean-aggregators.dynadoc
test/repl/colon-equals.dynadoc
test/repl/equals-errors.dynadoc
test/repl/list.dynadoc
test/repl/recursion-limit.dynadoc

index 18b5a853eacb4967ea1ee5d72683d6bdbfdfc810..ee8d18d11f354b7aa8719002e44d1c68f4bbcabe 100755 (executable)
@@ -48,6 +48,13 @@ print 'Doctests'
 print '========'
 
 for x in sorted(path('test').glob("*/*.dynadoc")):
+
+    if '/ptb.dynadoc' in x:
+        continue
+
+    if '/known-failures/' in x:
+        continue
+
     print x,
     sys.stdout.flush()
     with file(x) as f:
index 33a9e41aa3e4ac96279967ef53803287d626014a..83e27076fd10b49a857e43923ac2589b9cc5e8cb 100644 (file)
@@ -123,6 +123,7 @@ class Interpreter(object):
         return self.chart[fn].insert(args)
 
     def delete(self, item, val, ruleix, variables):
+        self.clear_error(item)
         self.emit(item, val, ruleix, variables, delete=True)
 
     def emit(self, item, val, ruleix, variables, delete):
@@ -438,6 +439,8 @@ class Interpreter(object):
             print 'Rule %s not found.' % idx
             return
 
+        self.clear_error(rule)
+
         # remove $rule
         if hasattr(rule, 'item'):
             self.delete(rule.item, true, ruleix=None, variables=None)
@@ -565,12 +568,6 @@ class Interpreter(object):
     def dump_errors(self, out=None):
         if out is None:
             out = sys.stdout
-        # We only dump the error chart if it's non empty.
-        if not self.error and not self.uninitialized_rules:
-            return
-        print >> out
-        print >> out, red % 'Errors'
-        print >> out, red % '======'
 
         # separate errors into aggregation errors and update handler errors
         I = defaultdict(lambda: defaultdict(list))
@@ -583,8 +580,21 @@ class Interpreter(object):
                 if h is None:
                     I[item.fn][type(e)].append((item, val, e))
                 else:
+                    if h.rule.index not in self.rules:
+                        # TODO: clear all errors pertaining to a rule at
+                        # push-time. This is a temporary filter, which is fine
+                        # for now.
+                        continue
                     E[h.rule][type(e)].append((item, val, e))
 
+        # We only dump the error chart if it's non empty.
+        if not I and not E and not self.uninitialized_rules:
+            return
+
+        print >> out
+        print >> out, red % 'Errors'
+        print >> out, red % '======'
+
         # aggregation errors
         for r in sorted(I, key=lambda r: r.index):
             print >> out, 'Error(s) aggregating %s:' % r
@@ -599,7 +609,7 @@ class Interpreter(object):
 
         # errors pertaining to rules
         for r in sorted(E, key=lambda r: r.index):
-            print >> out, 'Error(s) in rule:', r.span
+            print >> out, 'Error(s) in rule %s:' % r.index, r.span
             print >> out
             for line in r.src.split('\n'):
                 print >> out, '   ', line
index b7d427aac052cc74c7a44fae18327abca891135a..217fe1f085d4c85d1932c494f4fe487c91f706c3 100644 (file)
@@ -8,7 +8,7 @@ to help.
 """
 
 import re, os, cmd, readline
-from utils import ip, lexer, subst, drepr, _repr, get_module
+from utils import ip, lexer, subst, drepr, _repr, get_module, yellow
 from stdlib import topython, todyna
 from errors import DynaCompilerError
 from config import dotdynadir
@@ -16,6 +16,10 @@ from errors import show_traceback
 import load, post
 
 
+from interpreter import Rule
+from contextlib import contextmanager
+
+
 class REPL(cmd.Cmd, object):
 
     def __init__(self, interp, hist=dotdynadir / 'dyna.hist'):
@@ -86,12 +90,13 @@ class REPL(cmd.Cmd, object):
         except ValueError:
             print 'Please specify an integer. Type `help retract_rule` to read more.'
         else:
-            changes = self.interp.retract_rule(idx)
-            if changes is None:
-                print 'List available by typing `rules`'
-                print
-            else:
-                self._changed(changes)
+            with self.error_tracker():
+                changes = self.interp.retract_rule(idx)
+                if changes is None:
+                    print 'List available by typing `rules`'
+                    print
+                else:
+                    self._changed(changes)
 
     def do_exit(self, _):
         """
@@ -259,12 +264,42 @@ class REPL(cmd.Cmd, object):
             print 'new rule(s) were not added to program.'
             print
         else:
-            new_rules = self.interp.load_plan(src)
-            changed = self.interp.run_agenda()
-            if show_changed:
-                self._changed(changed)
+            with self.error_tracker():
+                new_rules = self.interp.load_plan(src)
+                changed = self.interp.run_agenda()
+                if show_changed:
+                    self._changed(changed)
             return (new_rules, changed)
 
+    @contextmanager
+    def error_tracker(self):
+        errors_before = self.interp.error.copy()
+        yield
+        if errors_before.items() != self.interp.error.items():
+            e = set(errors_before) | set(self.interp.error)
+            new_errors = 0
+            cleared_errors = 0
+            for k in e:
+                was = k in errors_before
+                now = k in self.interp.error
+                if isinstance(k, Rule):
+                    k = 'rule index %s' % k.index
+                if was and not now:
+                    #print 'cleared error at `%s`.' % k
+                    cleared_errors += 1
+                elif not was and now:
+                    #print 'new error at `%s`.' % k
+                    new_errors += 1
+            if new_errors and cleared_errors:
+                print yellow % '>>>', '%s new errors, %s errors cleared. Type `sol` for details.\n' \
+                    % (new_errors, cleared_errors)
+            elif new_errors:
+                print yellow % '>>>', '%s new errors. Type `sol` for details.\n' \
+                    % (new_errors,)
+            elif cleared_errors:
+                print yellow % '>>>', '%s errors cleared.\n' \
+                    % (cleared_errors,)
+
     def _changed(self, changed):
         if not changed:
             return
index 202701a3f2325fd3082844a36435f8709297b7e1..d553c753ba774b326b6c8cf40e4bf1a38ab1ad32 100644 (file)
@@ -32,6 +32,8 @@ f(1,2) = 2.
 f(2,1) = 1.
 f(2,2) = 2.
 
+>>> 5 new errors. Type `sol` for details.
+
 > sol
 
 Solution
@@ -61,25 +63,25 @@ Error(s) aggregating a/1:
 Error(s) aggregating d/0:
   TypeError:
     `d`: unsupported operand type(s) for *: 'NoneType' and 'int'
-Error(s) in rule: <repl>
+Error(s) in rule 1: <repl>
     a += 1/b.
   ZeroDivisionError:
     when `b` = 0
       division by zero
       a += (1 / b=0)=?.
-Error(s) in rule: <repl>
+Error(s) in rule 2: <repl>
     c += "" + b.
   TypeError:
     when `b` = 0
       cannot concatenate 'str' and 'int' objects
       c += ("" + b=0)=?.
-Error(s) in rule: <repl>
+Error(s) in rule 4: <repl>
     b := e/0.
   ZeroDivisionError:
     when `e` = 0
       division by zero
       b := (e=0 / 0)=?.
-Error(s) in rule: <repl>
+Error(s) in rule 5: <repl>
     a += e/0.
   ZeroDivisionError:
     when `e` = 0
index 1d7e82d58b33c9f3d93e6e8e79b7f872729a2203..6f41162cc9a1cf1a91c54d97a7d1bcd3d7efc902 100644 (file)
@@ -20,6 +20,8 @@ b = 1.
 
 > a += 1/d.
 
+>>> 1 new errors. Type `sol` for details.
+
 > sol
 
 Solution
@@ -48,6 +50,8 @@ a = 2.
 b = 2.
 d = 1.
 
+>>> 1 errors cleared.
+
 % Looks good.
 
 > sol
index aeee31dfc7dc87767d98067cb3482ec074f40eef..44481f3aac29341e83a0946ccca936906cda360b 100644 (file)
@@ -6,6 +6,8 @@ d = 0.
 
 > a += 1 / d.
 
+>>> 1 new errors. Type `sol` for details.
+
 > rules
 
 Rules
@@ -35,3 +37,5 @@ Changes
 =======
 a = 1.0.
 d = 1.
+
+>>> 1 errors cleared.
index fbfc66cc704dfbe8cf478704780628dd81fb8783..19eb59b524fbb2f9452c318564faf5caa5854946 100644 (file)
@@ -6,6 +6,8 @@ Changes
 =======
 e = $error.
 
+>>> 1 new errors. Type `sol` for details.
+
 > sol
 
 Solution
@@ -24,7 +26,7 @@ Changes
 =======
 e = null.
 
-
+>>> 1 errors cleared.
 
 
 > a :- false.
@@ -49,6 +51,8 @@ Changes
 b = $error.
 c = "horse".
 
+>>> 1 new errors. Type `sol` for details.
+
 
 > sol
 
@@ -72,6 +76,7 @@ Changes
 b = true.
 c = true.
 
+>>> 1 errors cleared.
 
 
 > f(1,2). f(2,2).
index 377fa4a258e3f153f7dd22e152bac186e46d8bf4..0534d9e4869c13072b68ac96953bf5216812d6bf 100644 (file)
@@ -9,6 +9,9 @@ a(1) = 1.
 a(2) = 2.
 b = $error.
 
+>>> 1 new errors. Type `sol` for details.
+
+
 > sol
 
 Solution
@@ -42,6 +45,9 @@ Changes
 =======
 b = 0.
 
+>>> 1 errors cleared.
+
+
 > a(1) := 2. a(2) := 2. b := 0. b := a(X).
 
 Changes
index 3da43e51583869c9edd35f3349e100a3acd55147..3ae3945387e549553aa0345316f0d4ca8b28b986 100644 (file)
@@ -15,6 +15,8 @@ Changes
 =======
 a = $error.
 
+>>> 1 new errors. Type `sol` for details.
+
 > sol
 
 Solution
@@ -34,6 +36,9 @@ Changes
 =======
 a = 2.
 
+>>> 1 errors cleared.
+
+
 > sol
 
 Solution
index 78e2da5e6f37f03e47dd05a51fc74632ef335961..fa91a0201cca7becc8a917bacfd8243bb2db22b8 100644 (file)
@@ -1,5 +1,7 @@
 > x = cons(1, 2).
 
+>>> 1 new errors. Type `sol` for details.
+
 > sol
 
 Solution empty.
@@ -16,6 +18,8 @@ Failed to initialize rule:
 
 > retract_rule 0
 
+>>> 1 errors cleared.
+
 > s set= Y for Y in [3,2,1,[2,1],&f(1)].
 
 Changes
index 1dbe2d7505f2ee563c1ffadf23a9f392a8e6dda2..0c7cb9455f0559c7499966e00913bf8112edf68d 100644 (file)
@@ -12,8 +12,13 @@ Changes
 =======
 a = $error.
 
+>>> 1 new errors. Type `sol` for details.
+
+
 > b = a + 1.
 
+>>> 1 new errors. Type `sol` for details.
+
 > rules
 
 Rules
@@ -30,7 +35,7 @@ a = $error.
 
 Errors
 ======
-Error(s) in rule: <repl>
+Error(s) in rule 0: <repl>
     f(X) = f(X-1).
   RuntimeError:
     when `f(-323)` = null
@@ -50,6 +55,8 @@ Changes
 =======
 a = null.
 
+>>> 2 errors cleared.
+
 > sol
 
 Solution empty.
\ No newline at end of file