Dne 24.10.2013 11:46, Harriv napsal(a): > > > I don't need main thread to be responsive, I want to read the data as > soon as possible. It's possible to control the tracing from command line > or another application, or I can use multiprocessing module to help. > > How to do that? How to get data before trace has stopped? > > It's probably possible to pipe the output of fbtracemgr to Python > program, but I'm still interested how to do it with plain Python program.
You were on right track with svc.readline(), as it returns with data if there are any trace data at server. If it do not returns, then there are no data which means that no events happen in database that match your trace config. If you're sure it should report something, then check your trace config as problem is most likely there. If you want to read everything that trace session returns immediately as it's available, use simple loop over service (service object acts similarly like file object here), for example: svc = fdb.sevices.connect(...) for line in svc: print line However, it never stops looping until trace session is canceled by other means. Here is sample script that traces all SELECT statements in given database and shows information when select finishes: import fdb import argparse import os def main(): parser = argparse.ArgumentParser(description="Tool to analyze index usage.") parser.add_argument('database', help="Full path to database.") parser.add_argument('-o','--host', help="Server host.") parser.add_argument('-u','--user', default=os.environ.get('ISC_USER', 'sysdba'), help="User name") parser.add_argument('-p','--password', default=os.environ.get('ISC_PASSWORD', None), help="User password") args = parser.parse_args() # We need password if not args.password: print "A password is required to use the Services Manager." print parser.print_help() return trace_config = """<database %s> enabled true log_statement_finish true print_plan true include_filter %%SELECT%% exclude_filter %%RDB$%% time_threshold 0 max_sql_length 2048 </database> """ try: if args.host: svc_host = args.host + ':service_mgr' else: svc_host = 'service_mgr' svc = fdb.services.connect(host=svc_host,user=args.user,password=args.password) trace_id = svc.trace_start(config=trace_config % args.database) trace_start = datetime.datetime.now() print "Trace session %i started." % trace_id except Exception as e: print e exit print "Use tracex.py to stop this trace session." try: for line in svc: print line except Exception as e: print 'Trace ended with exception:\n%s\n' % str(e) else: print "Trace session stopped" svc.close() if __name__ == '__main__': main() To control trace services you can use next script (tracex.py mentioned in previous one): import fdb import argparse import os def main(): parser = argparse.ArgumentParser(description="Tool to manage trace sessions") parser.add_argument('-o','--host', help="Server host.") parser.add_argument('-u','--user', default=os.environ.get('ISC_USER', 'sysdba'), help="User name") parser.add_argument('-p','--password', default=os.environ.get('ISC_PASSWORD', None), help="User password") parser.add_argument('-l','--list', action='store_true', help="List trace sessions.") parser.add_argument('-s','--suspend', type=int, metavar='SESSION_ID', help="Pause trace # session.") parser.add_argument('-r','--resume', type=int, metavar='SESSION_ID', help="resume trace # session.") parser.add_argument('-c','--cancel', type=int, metavar='SESSION_ID', help="cancel trace # session.") args = parser.parse_args() if not args.password: print "A password is required to use the Services Manager." print parser.print_help() return if args.host: svc_host = args.host + ':service_mgr' else: svc_host = 'service_mgr' svc = fdb.services.connect(host=svc_host,user=args.user,password=args.password) if args.list: sessions = svc.trace_list() if len(sessions.keys()) == 0: print "No trace sessions." else: for sid, data in sessions.items(): print "Trace session %i" % sid if data.has_key('name'): print " name:", data['name'] print " date:", data['date'].strftime('%Y-%m-%d %H:%M:%S') print " user:", data['user'] print " flags:", ', '.join(data['flags']) elif args.suspend: try: print svc.trace_suspend(args.suspend) except Exception as e: print "ERROR:" print e.args elif args.resume: try: print svc.trace_resume(args.resume) except Exception as e: print "ERROR:" print e.args elif args.cancel: try: print svc.trace_stop(args.cancel) except Exception as e: print "ERROR:" print e.args if __name__ == '__main__': main() best regards Pavel Cisar IBPhoenix