#! /usr/bin/env python

# Copyright (c) 2000 Roman Milner
# See the file COPYING for more information

import sys
from time import localtime, time, mktime
import string
import exceptions
from SQLRelay import CSQLRelay

apilevel = '2.0'
threadsafety = 0
paramstyle = 'pyformat'


class Error(exceptions.StandardError):
    pass

class Warning(exceptions.StandardError):
    pass

class InterfaceError(Error):
    pass

class DatabaseError(Error):
    pass

class InternalError(DatabaseError):
    pass

class OperationalError(DatabaseError):
    pass

class ProgrammingError(DatabaseError):
    pass

class IntegrityError(DatabaseError):
    pass

class DataError(DatabaseError):
    pass

class NotSupportedError(DatabaseError):
    pass


def connect(host, port, socket, user, password, retrytime=0, tries=1):
    return SQLRConnection(host, port, socket, user, password, retrytime, tries)


class SQLRConnection:

    def __init__(self, host, port, socket, user, password, retrytime, tries):
        self.connection = CSQLRelay.sqlrcon_alloc(host, port, socket, user, password, retrytime, tries)

    def close(self):
        CSQLRelay.sqlrcon_free(self.connection)

    def commit(self):
        curs=self.cursor()
        curs.execute('commit')
        CSQLRelay.endSession(self.connection)

    def rollback(self):
        curs=self.cursor()
        curs.execute('rollback')
        CSQLRelay.endSession(self.connection)

    def cursor(self):
        return SQLRCursor(self.connection)


class SQLRCursor:


    def __init__(self, con):
        self.cursor = CSQLRelay.sqlrcur_alloc(con)
        self.arraysize = 1

    def setinputsizes(self):
        pass

    def setoutputsize(self):
        pass
        
    def execute(self, operation, parameters=None):
        self.cur_row = 0
        CSQLRelay.sendQuery(self.cursor,operation)
        the_error = CSQLRelay.errorMessage(self.cursor)
        if the_error:
            raise DatabaseError, '<pre>%s</pre>' % the_error
        self.__set_description()

    def executemany(self, operation, parameters=None):
        for i in parameters:
                execute(operation,i)

    def callproc(self, parameters=None):
        pass
        
    def fetchone(self):
        row = CSQLRelay.getRow(self.cursor,self.cur_row)
        self.cur_row = self.cur_row + 1
        return row

    def fetchmany(self, size=None):
        if not size:
            size = self.arraysize
        num_rows = CSQLRelay.rowCount(self.cursor)
        if size >= num_rows:
            size = num_rows-1
        rc = CSQLRelay.getRowRange(self.cursor, self.cur_row, size)
        self.cur_row = size
        return rc

    def fetchall(self):
        rc = []
        num_rows = CSQLRelay.rowCount(self.cursor)
        for row in range(self.cur_row, num_rows):
            row = CSQLRelay.getRow(self.cursor,self.cur_row)
            self.cur_row = self.cur_row + 1
            rc.append(row)
        return rc

    def close(self):
        pass

    def __set_description(self):
        desc = []
        col_c = CSQLRelay.colCount(self.cursor)
        if not col_c:
            self.description = []
            return None
        for field in range(col_c):
            row = []
            row.append(CSQLRelay.getColumnName(self.cursor,field),)
            row.append(CSQLRelay.getColumnType(self.cursor,field),)
            row.append(CSQLRelay.getColumnLength(self.cursor,field))
            desc.append(tuple(row))
        self.description = tuple(desc)
        return tuple(desc)