Commits

Hiroyoshi Komatsu committed c03f5e5 Merge

Merged in Machielo/corenlp-python/resiliency (pull request #3)

Added server recovery

  • Participants
  • Parent commits 4732083, b4accc7

Comments (0)

Files changed (1)

corenlp/corenlp.py

         return repr(self.value)
 
 
+class OutOfMemoryError(Exception):
+
+    def __init__(self, value):
+        self.value = value
+
+    def __str__(self):
+        return repr(self.value)
+
+
 def init_corenlp_command(corenlp_path, memory, properties):
     """
     Checks the location of the jar files.
     Can be run as a JSON-RPC server or imported as a module.
     """
 
-    def __init__(self, corenlp_path=DIRECTORY, memory="3g", properties='default.properties'):
-        """
-        Checks the location of the jar files.
-        Spawns the server as a process.
-        """
-
-        # spawn the server
-        start_corenlp = init_corenlp_command(corenlp_path, memory, properties)
+    def _spawn_corenlp(self):
         if VERBOSE:
-            print start_corenlp
-        self.corenlp = pexpect.spawn(start_corenlp)
+            print self.start_corenlp
+        self.corenlp = pexpect.spawn(self.start_corenlp, maxread=8192, searchwindowsize=80)
 
         # show progress bar while loading the models
         if VERBOSE:
             pbar.finish()
 
         # interactive shell
-        self.corenlp.expect("\nNLP> ", timeout=3)
+        self.corenlp.expect("\nNLP> ")
+
+    def __init__(self, corenlp_path=DIRECTORY, memory="3g", properties='default.properties', serving=False):
+        """
+        Checks the location of the jar files.
+        Spawns the server as a process.
+        """
+
+        # spawn the server
+        self.serving = serving
+        self.start_corenlp = init_corenlp_command(corenlp_path, memory, properties)
+        self._spawn_corenlp()
 
     def close(self, force=True):
         self.corenlp.terminate(force)
             print >>sys.stderr, {'error': "CoreNLP terminates abnormally while parsing",
                                  'input': to_send,
                                  'output': incoming}
-            self.corenlp.close()
             raise ProcessError("CoreNLP process terminates abnormally while parsing")
         elif t == 3:
             # out of memory
             print >>sys.stderr, {'error': "WARNING: Parsing of sentence failed, possibly because of out of memory.",
                                  'input': to_send,
                                  'output': incoming}
-            return
+            raise OutOfMemoryError
 
         if VERBOSE:
             print "%s\n%s" % ('=' * 40, incoming)
         reads in the result, parses the results and returns a list
         with one dictionary entry for each parsed sentence.
         """
-        return self._parse(text)
+        try:
+            r = self._parse(text)
+            return r
+        except Exception as e:
+            print e  # Should probably log somewhere instead of printing
+            self.corenlp.close()
+            self._spawn_corenlp()
+            if self.serving:  # We don't want to raise the exception when acting as a server
+                return []
+            raise e
 
     def parse(self, text):
         """
     try:
         server = SimpleJSONRPCServer((options.host, int(options.port)))
 
-        nlp = StanfordCoreNLP(options.corenlp, properties=options.properties)
+        nlp = StanfordCoreNLP(options.corenlp, properties=options.properties, serving=True)
         server.register_function(nlp.parse)
+        server.register_function(nlp.raw_parse)
 
         print 'Serving on http://%s:%s' % (options.host, options.port)
         # server.serve()