Changeset 809
- Timestamp:
- 03/08/07 16:45:36 (2 years ago)
- Files:
-
- pg8000/trunk/pg8000.py (modified) (10 diffs)
- pg8000/trunk/pg8000-test.py (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
pg8000/trunk/pg8000.py
r808 r809 196 196 # parameter is provided and the database does not request password 197 197 # authentication, then the password will not be used. 198 # 199 # @keyparam socket_timeout Socket connect timeout measured in seconds. 200 # Defaults to 60 seconds. 198 201 class Connection(Cursor): 199 202 … … 207 210 iterate_dicts = False 208 211 209 def __init__(self, host, user, port=5432, database=None, password=None ):212 def __init__(self, host, user, port=5432, database=None, password=None, socket_timeout=60): 210 213 self._row_desc = None 211 214 try: 212 self.c = Protocol.Connection(host, port )215 self.c = Protocol.Connection(host, port, socket_timeout=socket_timeout) 213 216 self.c.connect() 214 217 self.c.authenticate(user, password=password, database=database) … … 507 510 createFromData = staticmethod(createFromData) 508 511 512 class ParameterDescription(object): 513 def __init__(self, type_oids): 514 self.type_oids = type_oids 515 def createFromData(data): 516 count = struct.unpack("!h", data[:2])[0] 517 type_oids = struct.unpack("!" + "i"*count, data[2:]) 518 return Protocol.ParameterDescription(type_oids) 519 createFromData = staticmethod(createFromData) 520 509 521 class RowDescription(object): 510 522 def __init__(self, fields): … … 553 565 554 566 class Connection(object): 555 def __init__(self, host=None, port=5432 ):567 def __init__(self, host=None, port=5432, socket_timeout=60): 556 568 self._state = "unconnected" 557 569 self._client_encoding = "ascii" … … 559 571 self._port = port 560 572 self._sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 573 self._sock.settimeout(socket_timeout) 561 574 self._backend_key_data = None 562 575 … … 618 631 param_types, param_fc = [x[0] for x in type_info], [x[1] for x in type_info] # zip(*type_info) -- fails on empty arr 619 632 self._send(Protocol.Parse(statement, qs, param_types)) 620 # The Types functions have the ability to "prefer" a certain output 621 # format from the server, however... we need to know the output 622 # type before we can know the output format. we don't get the 623 # types until we bind, which is where we need to specify the format 624 # codes. So, we need to go with text format for all outputs from 625 # the server, even though it'd be nice to have the flexibility to 626 # get some return values in bin and some in txt. 627 self._send(Protocol.Bind(portal, statement, param_fc, params, (0,), self._client_encoding)) 628 self._send(Protocol.DescribePortal(portal)) 633 self._send(Protocol.DescribePreparedStatement(statement)) 629 634 self._send(Protocol.Flush()) 630 635 while 1: 631 636 msg = self._read_message() 637 print repr(msg) 632 638 if isinstance(msg, Protocol.ParseComplete): 633 639 # ok, good. 634 640 pass 635 elif isinstance(msg, Protocol.BindComplete): 636 # good news everybody! 641 elif isinstance(msg, Protocol.ParameterDescription): 642 # well, we don't really care -- we're going to send whatever 643 # we want and let the database deal with it. But thanks 644 # anyways! 637 645 pass 638 646 elif isinstance(msg, Protocol.NoData): 639 647 # No data means we should execute this command right away. 640 # There's no need to rebind like we were planning to, since641 # there are no return format codes. Just execute and sync.642 648 self._send(Protocol.Execute(portal, 0)) 643 649 self._send(Protocol.Sync()) … … 655 661 raise InternalError("unexpected response") 656 662 elif isinstance(msg, Protocol.RowDescription): 657 return msg 663 row_desc = msg 664 break 658 665 elif isinstance(msg, Protocol.ErrorResponse): 659 666 raise msg.createException() 660 667 else: 661 668 raise InternalError("Unexpected response msg %r" % (msg)) 669 670 # We've got row_desc that allows us to identify what we're going to 671 # get back from this statement. Now we can Bind values. 672 output_fc = [Types.py_type_info(f) for f in row_desc.fields] 673 print repr(output_fc) 674 self._send(Protocol.Bind(portal, statement, param_fc, params, output_fc, self._client_encoding)) 675 print "bind" 676 self._send(Protocol.Flush()) 677 print "flush" 678 while 1: 679 msg = self._read_message() 680 print repr(msg) 681 if isinstance(msg, Protocol.BindComplete): 682 # good news everybody! 683 #return row_desc 684 pass 685 elif isinstance(msg, Protocol.ErrorResponse): 686 raise msg.createException() 687 else: 688 raise InternalError("Unexpected response msg %r" % (msg)) 689 690 662 691 663 692 def fetch_rows(self, portal, row_count, row_desc): … … 738 767 "s": PortalSuspended, 739 768 "n": NoData, 769 "t": ParameterDescription, 740 770 } 741 771 … … 789 819 def py_type_info(description): 790 820 type_oid = description['type_oid'] 791 data = Types.pg_types.get(typ )821 data = Types.pg_types.get(type_oid) 792 822 if data == None: 793 823 raise NotSupportedError("type oid %r not mapped to py type" % type_oid) … … 812 842 else: 813 843 raise InternalError("no conversion fuction for type oid %r" % type_oid) 814 return type_oid844 return format 815 845 py_type_info = staticmethod(py_type_info) 816 846 pg8000/trunk/pg8000-test.py
r808 r809 6 6 import pg8000 7 7 8 db = pg8000.Connection(host=' localhost', user='mfenniak')8 db = pg8000.Connection(host='joy.fenniak.net', user='Mathieu Fenniak', database="software", password="hello", socket_timeout=5) 9 9 db.iterate_dicts = True 10 10 11 11 cur1 = pg8000.Cursor(db) 12 12 13 cur1.execute("DROP TABLE t1")14 cur1.execute("CREATE TABLE t1 (f1 int primary key, f2 int not null, f3 varchar(50) not null)")15 cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 1, 1, "hello")16 cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 2, 10, u"he\u0173llo")17 cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 3, 100, "hello")18 cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 4, 1000, "hello")19 cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 5, 10000, "hello")13 #cur1.execute("DROP TABLE t1") 14 #cur1.execute("CREATE TABLE t1 (f1 int primary key, f2 int not null, f3 varchar(50) not null)") 15 #cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 1, 1, "hello") 16 #cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 2, 10, u"he\u0173llo") 17 #cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 3, 100, "hello") 18 #cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 4, 1000, "hello") 19 #cur1.execute("INSERT INTO t1 (f1, f2, f3) VALUES ($1, $2, $3)", 5, 10000, "hello") 20 20 21 print "begin query..."22 cur1.execute("SELECT * FROM t1")23 i = 024 for row1 in cur1:25 i = i + 126 print i, repr(row1)27 db.execute("SELECT * FROM t1 WHERE f1 > $1", row1['f1'])28 for row2 in db:29 print "\t", repr(row2)30 print "end query..."21 #print "begin query..." 22 #cur1.execute("SELECT * FROM t1") 23 #i = 0 24 #for row1 in cur1: 25 # i = i + 1 26 # print i, repr(row1) 27 # db.execute("SELECT * FROM t1 WHERE f1 > $1", row1['f1']) 28 # for row2 in db: 29 # print "\t", repr(row2) 30 #print "end query..." 31 31 32 32 print "Beginning type checks..."
