test_curses.py revision aa6c297316a62baed42f10508cf21d781b0fbee4
1# 2# Test script for the curses module 3# 4# This script doesn't actually display anything very coherent. but it 5# does call every method and function. 6# 7# Functions not tested: {def,reset}_{shell,prog}_mode, getch(), getstr(), 8# init_color() 9# Only called, not tested: getmouse(), ungetmouse() 10# 11 12import sys, tempfile, os 13 14# Optionally test curses module. This currently requires that the 15# 'curses' resource be given on the regrtest command line using the -u 16# option. If not available, nothing after this line will be executed. 17 18import unittest 19from test.test_support import requires, import_module 20requires('curses') 21curses = import_module('curses') 22curses.panel = import_module('curses.panel') 23 24 25# XXX: if newterm was supported we could use it instead of initscr and not exit 26term = os.environ.get('TERM') 27if not term or term == 'unknown': 28 raise unittest.SkipTest, "$TERM=%r, calling initscr() may cause exit" % term 29 30if sys.platform == "cygwin": 31 raise unittest.SkipTest("cygwin's curses mostly just hangs") 32 33def window_funcs(stdscr): 34 "Test the methods of windows" 35 win = curses.newwin(10,10) 36 win = curses.newwin(5,5, 5,5) 37 win2 = curses.newwin(15,15, 5,5) 38 39 for meth in [stdscr.addch, stdscr.addstr]: 40 for args in [('a'), ('a', curses.A_BOLD), 41 (4,4, 'a'), (5,5, 'a', curses.A_BOLD)]: 42 meth(*args) 43 44 for meth in [stdscr.box, stdscr.clear, stdscr.clrtobot, 45 stdscr.clrtoeol, stdscr.cursyncup, stdscr.delch, 46 stdscr.deleteln, stdscr.erase, stdscr.getbegyx, 47 stdscr.getbkgd, stdscr.getkey, stdscr.getmaxyx, 48 stdscr.getparyx, stdscr.getyx, stdscr.inch, 49 stdscr.insertln, stdscr.instr, stdscr.is_wintouched, 50 win.noutrefresh, stdscr.redrawwin, stdscr.refresh, 51 stdscr.standout, stdscr.standend, stdscr.syncdown, 52 stdscr.syncup, stdscr.touchwin, stdscr.untouchwin]: 53 meth() 54 55 stdscr.addnstr('1234', 3) 56 stdscr.addnstr('1234', 3, curses.A_BOLD) 57 stdscr.addnstr(4,4, '1234', 3) 58 stdscr.addnstr(5,5, '1234', 3, curses.A_BOLD) 59 60 stdscr.attron(curses.A_BOLD) 61 stdscr.attroff(curses.A_BOLD) 62 stdscr.attrset(curses.A_BOLD) 63 stdscr.bkgd(' ') 64 stdscr.bkgd(' ', curses.A_REVERSE) 65 stdscr.bkgdset(' ') 66 stdscr.bkgdset(' ', curses.A_REVERSE) 67 68 win.border(65, 66, 67, 68, 69 69, 70, 71, 72) 70 win.border('|', '!', '-', '_', 71 '+', '\\', '#', '/') 72 try: 73 win.border(65, 66, 67, 68, 74 69, [], 71, 72) 75 except TypeError: 76 pass 77 else: 78 raise RuntimeError, "Expected win.border() to raise TypeError" 79 80 stdscr.clearok(1) 81 82 win4 = stdscr.derwin(2,2) 83 win4 = stdscr.derwin(1,1, 5,5) 84 win4.mvderwin(9,9) 85 86 stdscr.echochar('a') 87 stdscr.echochar('a', curses.A_BOLD) 88 stdscr.hline('-', 5) 89 stdscr.hline('-', 5, curses.A_BOLD) 90 stdscr.hline(1,1,'-', 5) 91 stdscr.hline(1,1,'-', 5, curses.A_BOLD) 92 93 stdscr.idcok(1) 94 stdscr.idlok(1) 95 stdscr.immedok(1) 96 stdscr.insch('c') 97 stdscr.insdelln(1) 98 stdscr.insnstr('abc', 3) 99 stdscr.insnstr('abc', 3, curses.A_BOLD) 100 stdscr.insnstr(5, 5, 'abc', 3) 101 stdscr.insnstr(5, 5, 'abc', 3, curses.A_BOLD) 102 103 stdscr.insstr('def') 104 stdscr.insstr('def', curses.A_BOLD) 105 stdscr.insstr(5, 5, 'def') 106 stdscr.insstr(5, 5, 'def', curses.A_BOLD) 107 stdscr.is_linetouched(0) 108 stdscr.keypad(1) 109 stdscr.leaveok(1) 110 stdscr.move(3,3) 111 win.mvwin(2,2) 112 stdscr.nodelay(1) 113 stdscr.notimeout(1) 114 win2.overlay(win) 115 win2.overwrite(win) 116 win2.overlay(win, 1, 2, 3, 3, 2, 1) 117 win2.overwrite(win, 1, 2, 3, 3, 2, 1) 118 stdscr.redrawln(1,2) 119 120 stdscr.scrollok(1) 121 stdscr.scroll() 122 stdscr.scroll(2) 123 stdscr.scroll(-3) 124 125 stdscr.move(12, 2) 126 stdscr.setscrreg(10,15) 127 win3 = stdscr.subwin(10,10) 128 win3 = stdscr.subwin(10,10, 5,5) 129 stdscr.syncok(1) 130 stdscr.timeout(5) 131 stdscr.touchline(5,5) 132 stdscr.touchline(5,5,0) 133 stdscr.vline('a', 3) 134 stdscr.vline('a', 3, curses.A_STANDOUT) 135 stdscr.chgat(5, 2, 3, curses.A_BLINK) 136 stdscr.chgat(3, curses.A_BOLD) 137 stdscr.chgat(5, 8, curses.A_UNDERLINE) 138 stdscr.chgat(curses.A_BLINK) 139 stdscr.refresh() 140 141 stdscr.vline(1,1, 'a', 3) 142 stdscr.vline(1,1, 'a', 3, curses.A_STANDOUT) 143 144 if hasattr(curses, 'resize'): 145 stdscr.resize() 146 if hasattr(curses, 'enclose'): 147 stdscr.enclose() 148 149 150def module_funcs(stdscr): 151 "Test module-level functions" 152 153 for func in [curses.baudrate, curses.beep, curses.can_change_color, 154 curses.cbreak, curses.def_prog_mode, curses.doupdate, 155 curses.filter, curses.flash, curses.flushinp, 156 curses.has_colors, curses.has_ic, curses.has_il, 157 curses.isendwin, curses.killchar, curses.longname, 158 curses.nocbreak, curses.noecho, curses.nonl, 159 curses.noqiflush, curses.noraw, 160 curses.reset_prog_mode, curses.termattrs, 161 curses.termname, curses.erasechar, curses.getsyx]: 162 func() 163 164 # Functions that actually need arguments 165 if curses.tigetstr("cnorm"): 166 curses.curs_set(1) 167 curses.delay_output(1) 168 curses.echo() ; curses.echo(1) 169 170 f = tempfile.TemporaryFile() 171 stdscr.putwin(f) 172 f.seek(0) 173 curses.getwin(f) 174 f.close() 175 176 curses.halfdelay(1) 177 curses.intrflush(1) 178 curses.meta(1) 179 curses.napms(100) 180 curses.newpad(50,50) 181 win = curses.newwin(5,5) 182 win = curses.newwin(5,5, 1,1) 183 curses.nl() ; curses.nl(1) 184 curses.putp('abc') 185 curses.qiflush() 186 curses.raw() ; curses.raw(1) 187 curses.setsyx(5,5) 188 curses.tigetflag('hc') 189 curses.tigetnum('co') 190 curses.tigetstr('cr') 191 curses.tparm('cr') 192 curses.typeahead(sys.__stdin__.fileno()) 193 curses.unctrl('a') 194 curses.ungetch('a') 195 curses.use_env(1) 196 197 # Functions only available on a few platforms 198 if curses.has_colors(): 199 curses.start_color() 200 curses.init_pair(2, 1,1) 201 curses.color_content(1) 202 curses.color_pair(2) 203 curses.pair_content(curses.COLOR_PAIRS - 1) 204 curses.pair_number(0) 205 206 if hasattr(curses, 'use_default_colors'): 207 curses.use_default_colors() 208 209 if hasattr(curses, 'keyname'): 210 curses.keyname(13) 211 212 if hasattr(curses, 'has_key'): 213 curses.has_key(13) 214 215 if hasattr(curses, 'getmouse'): 216 (availmask, oldmask) = curses.mousemask(curses.BUTTON1_PRESSED) 217 # availmask indicates that mouse stuff not available. 218 if availmask != 0: 219 curses.mouseinterval(10) 220 # just verify these don't cause errors 221 curses.ungetmouse(0, 0, 0, 0, curses.BUTTON1_PRESSED) 222 m = curses.getmouse() 223 224 if hasattr(curses, 'is_term_resized'): 225 curses.is_term_resized(*stdscr.getmaxyx()) 226 if hasattr(curses, 'resizeterm'): 227 curses.resizeterm(*stdscr.getmaxyx()) 228 if hasattr(curses, 'resize_term'): 229 curses.resize_term(*stdscr.getmaxyx()) 230 231def unit_tests(): 232 from curses import ascii 233 for ch, expected in [('a', 'a'), ('A', 'A'), 234 (';', ';'), (' ', ' '), 235 ('\x7f', '^?'), ('\n', '^J'), ('\0', '^@'), 236 # Meta-bit characters 237 ('\x8a', '!^J'), ('\xc1', '!A'), 238 ]: 239 if ascii.unctrl(ch) != expected: 240 print 'curses.unctrl fails on character', repr(ch) 241 242 243def test_userptr_without_set(stdscr): 244 w = curses.newwin(10, 10) 245 p = curses.panel.new_panel(w) 246 # try to access userptr() before calling set_userptr() -- segfaults 247 try: 248 p.userptr() 249 raise RuntimeError, 'userptr should fail since not set' 250 except curses.panel.error: 251 pass 252 253def test_userptr_memory_leak(stdscr): 254 w = curses.newwin(10, 10) 255 p = curses.panel.new_panel(w) 256 obj = object() 257 nrefs = sys.getrefcount(obj) 258 for i in range(100): 259 p.set_userptr(obj) 260 261 p.set_userptr(None) 262 if sys.getrefcount(obj) != nrefs: 263 raise RuntimeError, "set_userptr leaked references" 264 265def test_userptr_segfault(stdscr): 266 panel = curses.panel.new_panel(stdscr) 267 class A: 268 def __del__(self): 269 panel.set_userptr(None) 270 panel.set_userptr(A()) 271 panel.set_userptr(None) 272 273def test_resize_term(stdscr): 274 if hasattr(curses, 'resizeterm'): 275 lines, cols = curses.LINES, curses.COLS 276 curses.resizeterm(lines - 1, cols + 1) 277 278 if curses.LINES != lines - 1 or curses.COLS != cols + 1: 279 raise RuntimeError, "Expected resizeterm to update LINES and COLS" 280 281def test_issue6243(stdscr): 282 curses.ungetch(1025) 283 stdscr.getkey() 284 285def main(stdscr): 286 curses.savetty() 287 try: 288 module_funcs(stdscr) 289 window_funcs(stdscr) 290 test_userptr_without_set(stdscr) 291 test_userptr_memory_leak(stdscr) 292 test_userptr_segfault(stdscr) 293 test_resize_term(stdscr) 294 test_issue6243(stdscr) 295 finally: 296 curses.resetty() 297 298if __name__ == '__main__': 299 curses.wrapper(main) 300 unit_tests() 301else: 302 if not sys.__stdout__.isatty(): 303 raise unittest.SkipTest("sys.__stdout__ is not a tty") 304 # testing setupterm() inside initscr/endwin 305 # causes terminal breakage 306 curses.setupterm(fd=sys.__stdout__.fileno()) 307 try: 308 stdscr = curses.initscr() 309 main(stdscr) 310 finally: 311 curses.endwin() 312 unit_tests() 313