Browse Source

Merge branch 'offbyone/ncurses-ui-layout'

Conflicts:
	celery/events/cursesmon.py
Ask Solem 14 years ago
parent
commit
bc4cfe474a
1 changed files with 54 additions and 23 deletions
  1. 54 23
      celery/events/cursesmon.py

+ 54 - 23
celery/events/cursesmon.py

@@ -14,6 +14,7 @@ from celery.app import app_or_default
 from celery.utils import abbr, abbrtask
 
 BORDER_SPACING = 4
+LEFT_BORDER_OFFSET = 3
 UUID_WIDTH = 36
 STATE_WIDTH = 8
 TIMESTAMP_WIDTH = 8
@@ -29,7 +30,6 @@ class CursesMonitor(object):
     selected_task = None
     selected_position = 0
     selected_str = "Selected: "
-    limit = 20
     foreground = curses.COLOR_BLACK
     background = curses.COLOR_WHITE
     online_str = "Workers online: "
@@ -78,11 +78,30 @@ class CursesMonitor(object):
             self.screen_width = len(row[:mx])
         return row[:mx]
 
+    @property
+    def screen_width(self):
+        _, mx = self.win.getmaxyx()
+        return mx
+
+    @property
+    def screen_height(self):
+        my, _ = self.win.getmaxyx()
+        return my
+
     @property
     def display_width(self):
         _, mx = self.win.getmaxyx()
         return mx - BORDER_SPACING
 
+    @property
+    def display_height(self):
+        my, _ = self.win.getmaxyx()
+        return my - 10
+
+    @property
+    def limit(self):
+        return self.display_height
+
     def find_position(self):
         if not self.tasks:
             return 0
@@ -274,10 +293,30 @@ class CursesMonitor(object):
         return self.alert(alert_callback,
                 "Task Result for %s" % self.selected_task)
 
+    def display_task_row(self, lineno, task):
+        state_color = self.state_colors.get(task.state)
+        attr = curses.A_NORMAL
+        if task.uuid== self.selected_task:
+            attr = curses.A_STANDOUT
+        timestamp = datetime.fromtimestamp(
+                        task.timestamp or time.time())
+        timef = timestamp.strftime("%H:%M:%S")
+        line = self.format_row(task.uuid, task.name,
+                               task.worker.hostname,
+                               timef, task.state)
+        self.win.addstr(lineno, LEFT_BORDER_OFFSET, line, attr)
+
+        if state_color:
+            self.win.addstr(lineno, len(line) - STATE_WIDTH + BORDER_SPACING - 1,
+                            task.state, state_color | attr)
+        if task.ready:
+            task.visited = time.time()
+
+
     def draw(self):
         win = self.win
         self.handle_keypress()
-        x = 3
+        x = LEFT_BORDER_OFFSET
         y = blank_line = count(2).next
         my, mx = win.getmaxyx()
         win.erase()
@@ -290,30 +329,17 @@ class CursesMonitor(object):
                 curses.A_BOLD | curses.A_UNDERLINE)
         tasks = self.tasks
         if tasks:
-            for uuid, task in tasks:
+            for row, (uuid, task) in enumerate(tasks):
+                if row > self.display_height:
+                    break
+
                 if task.uuid:
-                    state_color = self.state_colors.get(task.state)
-                    attr = curses.A_NORMAL
-                    if task.uuid == self.selected_task:
-                        attr = curses.A_STANDOUT
-                    timestamp = datetime.fromtimestamp(
-                                    task.timestamp or time.time())
-                    timef = timestamp.strftime("%H:%M:%S")
-                    line = self.format_row(uuid, task.name,
-                                           task.worker.hostname,
-                                           timef, task.state)
                     lineno = y()
-                    win.addstr(lineno, x, line, attr)
-                    if state_color:
-                        win.addstr(lineno,
-                                len(line) - STATE_WIDTH + BORDER_SPACING - 1,
-                                task.state, state_color | attr)
-                    if task.ready:
-                        task.visited = time.time()
+                self.display_task_row(lineno, task)
 
         # -- Footer
         blank_line()
-        win.hline(my - 6, x, curses.ACS_HLINE, self.screen_width)
+        win.hline(my - 6, x, curses.ACS_HLINE, self.screen_width - 4)
 
         # Selected Task Info
         if self.selected_task:
@@ -364,10 +390,15 @@ class CursesMonitor(object):
                 curses.A_DIM)
 
         # Help
-        win.addstr(my - 2, x, self.help_title, curses.A_BOLD)
-        win.addstr(my - 2, x + len(self.help_title), self.help, curses.A_DIM)
+        self.safe_add_str(my - 2, x, self.help_title, curses.A_BOLD)
+        self.safe_add_str(my - 2, x + len(self.help_title), self.help, curses.A_DIM)
         win.refresh()
 
+    def safe_add_str(self, y, x, string, *args, **kwargs):
+        if x + len(string) > self.screen_width:
+            string = string[:self.screen_width - x]
+        self.win.addstr(y, x, string, *args, **kwargs)
+
     def init_screen(self):
         self.win = curses.initscr()
         self.win.nodelay(True)