"Each database connection can be configured with its own date
output format. In order to extract date strings from output buffers
holding multiple date strings in fixed-width fields, we need to know
-the length of that format.")))
+the length of that format.")
+ (server-version
+ :type string
+ :initarg :server-version
+ :reader server-version
+ :documentation
+ "Version string of Oracle server.")
+ (major-version-number
+ :type (or null fixnum)
+ :initarg :major-version-number
+ :reader major-version-number
+ :documentation
+ "The major version number of Oracle, should be 8, 9, or 10")))
;;; Handle the messy case of return code=+oci-error+, querying the
(errcode :long))
(setf (uffi:deref-array errbuf '(:array :unsigned-char) 0) (code-char 0)) ; i.e. init to empty string
(setf (uffi:deref-pointer errcode :long) 0)
- (oci-error-get (uffi:deref-pointer errhp '(* :void)) 1 "" (c-& errcode :unsigned-char)
- (c-& errbuf :unsigned-char) +errbuf-len+ +oci-htype-error+)
+ (oci-error-get (uffi:deref-pointer errhp void-pointer) 1
+ (uffi:make-null-pointer :unsigned-char)
+ errcode errbuf +errbuf-len+ +oci-htype-error+)
(let ((subcode (uffi:deref-pointer errcode :long)))
(unless (and nulls-ok (= subcode +null-value-returned+))
(error 'clsql-sql-error
:database database
:errno subcode
+ :expression nil
:error (uffi:convert-from-foreign-string errbuf)))))))
(nulls-ok
(error 'clsql-sql-error
:database database
- :error "can't handle NULLS-OK without ERRHP"))
+ :message "can't handle NULLS-OK without ERRHP"))
(t
(error 'clsql-sql-error
:database database
- :error "OCI Error (and no ERRHP available to find subcode)"))))
+ :message "OCI Error (and no ERRHP available to find subcode)"))))
;;; Require an OCI success code.
;;;
(declare (type (mod #.+n-buf-rows+) string-index))
(declare (type (and unsigned-byte fixnum) size))
(let* ((raw (uffi:convert-from-foreign-string
- (uffi:pointer-address (uffi:deref-array arrayptr '(:array :unsigned-char) (* string-index size)))))
+ (+ (uffi:pointer-address arrayptr) (* string-index size))))
(trimmed (string-trim " " raw)))
(if (equal trimmed "NULL") nil trimmed)))
; (sql:query "select '',OWNER,TABLE_NAME,TABLE_TYPE,'' from all_catalog"))
-(defmethod list-all-user-database-tables ((db oracle-database))
- (unless db
- (setf db clsql:*default-database*))
+(defmethod database-list-tables ((database oracle-database) &key owner)
+ (mapcar #'car
+ (database-query "select table_name from user_tables"
+ database nil nil))
+ #+nil
(values (database-query "select TABLE_NAME from all_catalog
- where owner <> 'PUBLIC' and owner <> 'SYSTEM' and owner <> 'SYS'"
+ where owner not in ('PUBLIC','SYSTEM','SYS','WMSYS','EXFSYS','CTXSYS','WKSYS','WK_TEST','MDSYS','DMSYS','OLAPSYS','ORDSYS','XDB')"
db nil nil)))
-(defmethod database-list-tables ((database oracle-database)
- &key (system-tables nil) owner)
- (if system-tables
- (database-query "select table_name from all_catalog" database nil nil)
- (database-query "select table_name from all_catalog where owner <> 'PUBLIC' and owner <> 'SYSTEM' and owner <> 'SYS'"
- database nil nil)))
+(defmethod database-list-views ((database oracle-database)
+ &key owner)
+ ;; (database-query "select table_name from all_catalog" database nil nil)
+ (mapcar #'car
+ (database-query "select view_name from user_views" database nil nil)))
;; Return a list of all columns in TABLE.
-;;
-;; The Allegro version of this also returned a second value.
(defmethod list-all-table-columns (table (db oracle-database))
(declare (type string table))
1))) ; string
preresult))
+(defmethod database-list-indexes ((database oracle-database)
+ &key (owner nil))
+ (mapcar #'car
+ (database-query "select index_name from user_indexes" database nil nil)))
+
(defmethod database-list-attributes (table (database oracle-database) &key owner)
(let* ((relname (etypecase table
(clsql-sys::sql-ident
(mapcar #'car
(database-query
(format nil
- "select user_tab_columns,column_name from user_tab_columns where user_tab_columns.table_name=~A"
+ "select user_tab_columns,column_name from user_tab_columns where user_tab_columns.table_name='~A'"
relname)
database nil nil))))
(uffi:def-type short-pointer '(* :short))
(uffi:def-type double-pointer '(* :double))
+;;; the result of a database query: a cursor through a table
+(defstruct (oracle-result-set (:print-function print-query-cursor)
+ (:conc-name qc-)
+ (:constructor %make-query-cursor))
+ (db (error "missing DB") ; db conn. this table is associated with
+ :type db
+ :read-only t)
+ (stmthp (error "missing STMTHP") ; the statement handle used to create
+;; :type alien ; this table. owned by the QUERY-CURSOR
+ :read-only t) ; object, deallocated on CLOSE-QUERY
+ (cds) ; (error "missing CDS") ; column descriptors
+; :type (simple-array cd 1)
+ ; :read-only t)
+ (n-from-oci
+ 0 ; buffered rows: number of rows recv'd
+ :type (integer 0 #.+n-buf-rows+)) ; from the database on the last read
+ (n-to-dbi
+ 0 ; number of buffered rows returned, i.e.
+ :type (integer 0 #.+n-buf-rows+)) ; the index, within the buffered rows,
+ ; of the next row which hasn't already
+ ; been returned
+ (total-n-from-oci
+ 0 ; total number of bytes recv'd from OCI
+ :type unsigned-byte) ; in all reads
+ (oci-end-seen-p nil)) ; Have we seen the end of OCI
+ ; data, i.e. OCI returning
+ ; less data than we requested?
+ ; OCI doesn't seem to like us
+ ; to try to read more data
+ ; from it after that..
+
+
(defun fetch-row (qc &optional (eof-errorp t) eof-value)
- (declare (optimize (speed 3)))
+ ;;(declare (optimize (speed 3)))
(cond ((zerop (qc-n-from-oci qc))
(if eof-errorp
(error 'clsql-error :message
(value
(let ((arb (foreign-resource-buffer (cd-indicators cd))))
(declare (type short-pointer arb))
- (unless (= (uffi:deref-array arb :int irow) -1)
+ (unless (= (uffi:deref-array arb '(:array :int) irow) -1)
(ecase (cd-oci-data-type cd)
(#.SQLT-STR (deref-oci-string b irow (cd-sizeof cd)))
(#.SQLT-FLT (uffi:deref-array b '(:array :double) irow))
:nulls-ok t))))
(uffi:with-foreign-object (rowcount :long)
(oci-attr-get (uffi:deref-pointer (qc-stmthp qc) void-pointer) +oci-htype-stmt+
- (c-& rowcount :long) nil +oci-attr-row-count+
+ rowcount
+ (uffi:make-null-pointer :unsigned-long)
+ +oci-attr-row-count+
(uffi:deref-pointer errhp void-pointer))
(setf (qc-n-from-oci qc)
(- (uffi:deref-pointer rowcount :long) (qc-total-n-from-oci qc)))
(defun sql-stmt-exec (sql-stmt-string db &key types)
(with-slots (envhp svchp errhp)
db
- (let ((stmthp (uffi:allocate-foreign-object (* :void))))
+ (let ((stmthp (uffi:allocate-foreign-object void-pointer)))
(uffi:with-foreign-object (stmttype :unsigned-short)
- (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) (c-& stmthp void-pointer) +oci-htype-stmt+ 0 nil)
- (oci-stmt-prepare (uffi:deref-pointer stmthp void-pointer) (uffi:deref-pointer errhp void-pointer)
- sql-stmt-string (length sql-stmt-string)
+ (oci-handle-alloc (uffi:deref-pointer envhp void-pointer)
+ stmthp
+ +oci-htype-stmt+ 0 +null-void-pointer-pointer+)
+ (oci-stmt-prepare (uffi:deref-pointer stmthp void-pointer)
+ (uffi:deref-pointer errhp void-pointer)
+ (uffi:convert-to-cstring sql-stmt-string)
+ (length sql-stmt-string)
+oci-ntv-syntax+ +oci-default+ :database db)
- (oci-attr-get (uffi:deref-pointer stmthp void-pointer) +oci-htype-stmt+
- (c-& stmttype :unsigned-short) nil +oci-attr-stmt-type+
- (uffi:deref-pointer errhp void-pointer) :database db)
+ (oci-attr-get (uffi:deref-pointer stmthp void-pointer)
+ +oci-htype-stmt+
+ stmttype
+ (uffi:make-null-pointer :unsigned-int)
+ +oci-attr-stmt-type+
+ (uffi:deref-pointer errhp void-pointer)
+ :database db)
(let* ((select-p (= (uffi:deref-pointer stmttype :unsigned-short) 1))
(iters (if select-p 0 1)))
- (oci-stmt-execute (uffi:deref-pointer svchp void-pointer) (uffi:deref-pointer stmthp void-pointer)
+ (oci-stmt-execute (uffi:deref-pointer svchp void-pointer)
+ (uffi:deref-pointer stmthp void-pointer)
(uffi:deref-pointer errhp void-pointer)
- iters 0 nil nil +oci-default+ :database db)
+ iters 0 +null-void-pointer+ +null-void-pointer+ +oci-default+
+ :database db)
(cond (select-p
(make-query-cursor db stmthp types))
(t
(defun make-query-cursor-cds (database stmthp types)
- (declare (optimize (speed 3))
+ (declare (optimize (safety 3) #+nil (speed 3))
(type oracle-database database)
(type pointer-pointer-void stmthp))
(with-slots (errhp)
database
(unless (eq types :auto)
(error "unsupported TYPES value"))
- (uffi:with-foreign-objects ((dtype :unsigned-short)
+ (uffi:with-foreign-objects ((dtype-foreign :unsigned-short)
(parmdp (* :void))
(precision :byte)
(scale :byte)
(sizeof nil))
(do ((icolumn 0 (1+ icolumn))
(cds-as-reversed-list nil))
- ((not (eql (oci-param-get (uffi:deref-pointer stmthp void-pointer) +oci-htype-stmt+
+ ((not (eql (oci-param-get (uffi:deref-pointer stmthp void-pointer)
+ +oci-htype-stmt+
(uffi:deref-pointer errhp void-pointer)
- (uffi:pointer-address parmdp)
+ parmdp
(1+ icolumn) :database database)
+oci-success+))
(coerce (reverse cds-as-reversed-list) 'simple-vector))
;; Decode type of ICOLUMNth column into a type we're prepared to
;; handle in Lisp.
- (oci-attr-get parmdp +oci-dtype-param+ (uffi:pointer-address dtype)
- nil +oci-attr-data-type+ (uffi:deref-pointer errhp void-pointer))
- (case dtype
- (#.SQLT-DATE
- (setf buffer (acquire-foreign-resource char (* 32 +n-buf-rows+)))
- (setf sizeof 32 dtype #.SQLT-STR))
- (2 ;; number
- ;;(oci-attr-get parmdp +oci-dtype-param+
- ;;(addr precision) nil +oci-attr-precision+
- ;;(uffi:deref-pointer errhp))
- (oci-attr-get parmdp +oci-dtype-param+
- (uffi:pointer-address scale) nil +oci-attr-scale+
- (uffi:deref-pointer errhp void-pointer))
- (cond
- ((zerop scale)
- (setf buffer (acquire-foreign-resource signed +n-buf-rows+)
- sizeof 4 ;; sizeof(int)
- dtype #.SQLT-INT))
- (t
- (setf buffer (acquire-foreign-resource double-float +n-buf-rows+)
- sizeof 8 ;; sizeof(double)
- dtype #.SQLT-FLT))))
- (t ; Default to SQL-STR
- (setf colsize 0
- dtype #.SQLT-STR)
- (oci-attr-get parmdp +oci-dtype-param+ (uffi:pointer-address colsize)
- (uffi:pointer-address colsizesize) +oci-attr-data-size+
- (uffi:deref-pointer errhp void-pointer))
- (let ((colsize-including-null (1+ colsize)))
- (setf buffer (acquire-foreign-resource char (* +n-buf-rows+ colsize-including-null)))
- (setf sizeof colsize-including-null))))
- (let ((retcodes (acquire-foreign-resource short +n-buf-rows+))
- (indicators (acquire-foreign-resource short +n-buf-rows+)))
- (push (make-cd :name "col" ;(subseq colname 0 colnamelen)
- :sizeof sizeof
- :buffer buffer
- :oci-data-type dtype
- :retcodes retcodes
- :indicators indicators)
- cds-as-reversed-list)
- (oci-define-by-pos (uffi:deref-pointer stmthp void-pointer)
- (uffi:pointer-address defnp)
- (uffi:deref-pointer errhp void-pointer)
- (1+ icolumn) ; OCI 1-based indexing again
- (foreign-resource-buffer buffer)
- sizeof
- dtype
- (foreign-resource-buffer indicators)
- nil
- (foreign-resource-buffer retcodes)
- +oci-default+)))))))
-
+ (oci-attr-get (uffi:deref-pointer parmdp void-pointer)
+ +oci-dtype-param+
+ dtype-foreign
+ (uffi:make-null-pointer :int) +oci-attr-data-type+
+ (uffi:deref-pointer errhp void-pointer))
+ (let ((dtype (uffi:deref-pointer dtype-foreign :unsigned-short)))
+ (case dtype
+ (#.SQLT-DATE
+ (setf buffer (acquire-foreign-resource :char (* 32 +n-buf-rows+)))
+ (setf sizeof 32 dtype #.SQLT-STR))
+ (2 ;; number
+ ;;(oci-attr-get parmdp +oci-dtype-param+
+ ;;(addr precision) nil +oci-attr-precision+
+ ;;(uffi:deref-pointer errhp))
+ (oci-attr-get (uffi:deref-pointer parmdp void-pointer)
+ +oci-dtype-param+
+ scale
+ (uffi:make-null-pointer :int) +oci-attr-scale+
+ (uffi:deref-pointer errhp void-pointer))
+ (cond
+ ((zerop scale)
+ (setf buffer (acquire-foreign-resource :init +n-buf-rows+)
+ sizeof 4 ;; sizeof(int)
+ dtype #.SQLT-INT))
+ (t
+ (setf buffer (acquire-foreign-resource :double +n-buf-rows+)
+ sizeof 8 ;; sizeof(double)
+ dtype #.SQLT-FLT))))
+ (t ; Default to SQL-STR
+ (setf (uffi:deref-pointer colsize :unsigned-long) 0
+ dtype #.SQLT-STR)
+ (oci-attr-get (uffi:deref-pointer parmdp void-pointer)
+ +oci-dtype-param+
+ colsize
+ (uffi:make-null-pointer :int) ;; (uffi:pointer-address colsizesize)
+ +oci-attr-data-size+
+ (uffi:deref-pointer errhp void-pointer))
+ (let ((colsize-including-null (1+ (uffi:deref-pointer colsize :unsigned-long))))
+ (setf buffer (acquire-foreign-resource
+ :char (* +n-buf-rows+ colsize-including-null)))
+ (setf sizeof colsize-including-null))))
+ (let ((retcodes (acquire-foreign-resource :short +n-buf-rows+))
+ (indicators (acquire-foreign-resource :short +n-buf-rows+)))
+ (push (make-cd :name "col" ;(subseq colname 0 colnamelen)
+ :sizeof sizeof
+ :buffer buffer
+ :oci-data-type dtype
+ :retcodes retcodes
+ :indicators indicators)
+ cds-as-reversed-list)
+ (oci-define-by-pos (uffi:deref-pointer stmthp void-pointer)
+ defnp
+ (uffi:deref-pointer errhp void-pointer)
+ (1+ icolumn) ; OCI 1-based indexing again
+ (foreign-resource-buffer buffer)
+ sizeof
+ dtype
+ (foreign-resource-buffer indicators)
+ (uffi:make-null-pointer :unsigned-short)
+ (foreign-resource-buffer retcodes)
+ +oci-default+))))))))
+
;; Release the resources associated with a QUERY-CURSOR.
(defun close-query (qc)
(values))
-(defmethod print-object ((db oracle-database) stream)
- (print-unreadable-object (db stream :type t :identity t)
- (format stream "\"/~a/~a\""
- (slot-value db 'data-source-name)
- (slot-value db 'user))))
-
-
(defmethod database-name-from-spec (connection-spec (database-type (eql :oracle)))
- (check-connection-spec connection-spec database-type (user password dsn))
- (destructuring-bind (user password dsn)
- connection-spec
+ (check-connection-spec connection-spec database-type (dsn user password))
+ (destructuring-bind (dsn user password) connection-spec
(declare (ignore password))
- (concatenate 'string "/" dsn "/" user)))
+ (concatenate 'string dsn "/" user)))
(defmethod database-connect (connection-spec (database-type (eql :oracle)))
- (check-connection-spec connection-spec database-type (user password dsn))
- (destructuring-bind (user password data-source-name)
+ (check-connection-spec connection-spec database-type (dsn user password))
+ (destructuring-bind (data-source-name user password)
connection-spec
(let ((envhp (uffi:allocate-foreign-object (* :void)))
(errhp (uffi:allocate-foreign-object (* :void)))
;; handle errors very gracefully (since they're part of the
;; error-handling mechanism themselves) so we just assert they
;; work.
- (setf (uffi:deref-pointer envhp void-pointer) nil)
+ (setf (uffi:deref-pointer envhp void-pointer) +null-void-pointer+)
#+oci-8-1-5
(progn
- (oci-env-create (c-& envhp void-pointer) +oci-default+ nil nil nil nil 0 nil)
- (oci-handle-alloc (uffi:deref-pointer envhp void-pointer)
- (c-& errhp void-pointer) +oci-htype-error+ 0 nil))
+ (oci-env-create envhp +oci-default+ nil nil nil nil 0 nil)
+ (oci-handle-alloc envhp
+ (c-& errhp void-pointer) +oci-htype-error+ 0
+ +null-void-pointer-pointer+))
#-oci-8-1-5
(progn
- (oci-initialize +oci-object+ nil nil nil nil)
- (ignore-errors (oci-handle-alloc nil (c-& envhp void-pointer) +oci-htype-env+ 0 nil)) ;no testing return
- (oci-env-init (c-& envhp void-pointer) +oci-default+ 0 nil)
- (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) (c-& errhp void-pointer) +oci-htype-error+ 0 nil)
- (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) (c-& srvhp void-pointer) +oci-htype-server+ 0 nil)
- ;;(osucc (oci-server-attach srvhp errhp nil 0 +oci-default+))
- (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) (c-& svchp void-pointer) +oci-htype-svcctx+ 0 nil)
+ (oci-initialize +oci-object+ +null-void-pointer+ +null-void-pointer+
+ +null-void-pointer+ +null-void-pointer-pointer+)
+ (ignore-errors (oci-handle-alloc +null-void-pointer+ envhp
+ +oci-htype-env+ 0
+ +null-void-pointer-pointer+)) ;no testing return
+ (oci-env-init envhp +oci-default+ 0 +null-void-pointer-pointer+)
+ (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) errhp
+ +oci-htype-error+ 0 +null-void-pointer-pointer+)
+ (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) srvhp
+ +oci-htype-server+ 0 +null-void-pointer-pointer+)
+ (oci-server-attach (uffi:deref-pointer srvhp void-pointer)
+ (uffi:deref-pointer errhp void-pointer)
+ (uffi:make-null-pointer :unsigned-char)
+ 0 +oci-default+)
+ (oci-handle-alloc (uffi:deref-pointer envhp void-pointer) svchp
+ +oci-htype-svcctx+ 0 +null-void-pointer-pointer+)
+ (oci-attr-set (uffi:deref-pointer svchp void-pointer)
+ +oci-htype-svcctx+
+ (uffi:deref-pointer srvhp void-pointer) 0 +oci-attr-server+
+ (uffi:deref-pointer errhp void-pointer))
;; oci-handle-alloc((dvoid *)encvhp, (dvoid **)&stmthp, OCI_HTYPE_STMT, 0, 0);
- #+nil
- (oci-attr-set (uffi:deref-pointer svchp void-pointer) +oci-htype-svcctx+
- (uffi:deref-pointer srvhp void-pointer) 0 +oci-attr-server+ errhp)
+ ;;#+nil
)
-
- #+nil
- (format t "Logging in as user '~A' to database ~A~%"
- user password data-source-name)
- (oci-logon (uffi:deref-pointer envhp void-pointer) (uffi:deref-pointer errhp void-pointer) (c-& svchp void-pointer)
- user (length user)
- password (length password)
- data-source-name (length data-source-name))
- (let ((db (make-instance 'oracle-database
- :name (database-name-from-spec connection-spec
- database-type)
- :envhp envhp
- :errhp errhp
- :db-type :oracle
- :svchp svchp
- :dsn data-source-name
- :user user)))
- ;; :date-format-length (1+ (length date-format)))))
- (clsql:execute-command
- (format nil "alter session set NLS_DATE_FORMAT='~A'"
- (date-format db)) :database db)
+ (let (db server-version)
+ (uffi:with-foreign-object (buf (:array :unsigned-char #.+errbuf-len+))
+ (oci-server-version (uffi:deref-pointer svchp void-pointer)
+ (uffi:deref-pointer errhp void-pointer)
+ buf +errbuf-len+ +oci-htype-svcctx+)
+ (setf server-version (uffi:convert-from-foreign-string buf)))
+ (setq db (make-instance 'oracle-database
+ :name (database-name-from-spec connection-spec
+ database-type)
+ :envhp envhp
+ :errhp errhp
+ :database-type :oracle
+ :svchp svchp
+ :dsn data-source-name
+ :user user
+ :server-version server-version
+ :major-version-number (major-version-from-string
+ server-version)))
+
+ (oci-logon (uffi:deref-pointer envhp void-pointer)
+ (uffi:deref-pointer errhp void-pointer)
+ svchp
+ (uffi:convert-to-cstring user) (length user)
+ (uffi:convert-to-cstring password) (length password)
+ (uffi:convert-to-cstring data-source-name) (length data-source-name)
+ :database db)
+ ;; :date-format-length (1+ (length date-format)))))
+ (setf (slot-value db 'clsql-sys::state) :open)
+ (database-execute-command
+ (format nil "alter session set NLS_DATE_FORMAT='~A'" (date-format db)) db)
db))))
+(defun major-version-from-string (str)
+ (cond
+ ((search " 10g " str)
+ 10)
+ ((search " 9g " str)
+ 10)))
+
+
;; Close a database connection.
(defmethod database-disconnect ((database oracle-database))
(defmethod database-query (query-expression (database oracle-database) result-types field-names)
(let ((cursor (sql-stmt-exec query-expression database :types :auto)))
- (declare (type (or query-cursor null) cursor))
+ ;; (declare (type (or query-cursor null) cursor))
(if (null cursor) ; No table was returned.
(values)
(do ((reversed-result nil))
".NEXTVAL FROM dual"
) :database database)))
+(defmethod database-list-sequences ((database oracle-database) &key owner)
+ (mapcar #'car (database-query "select sequence_name from user_sequences"
+ database nil nil)))
-(defmethod database-execute-command
- (sql-expression (database oracle-database))
+(defmethod database-execute-command (sql-expression (database oracle-database))
(database-query sql-expression database nil nil)
;; HACK HACK HACK
(database-query "commit" database nil nil)
(cd-oci-data-type cd)
(cd-sizeof cd))))
-;;; the result of a database query: a cursor through a table
-(defstruct (oracle-result-set (:print-function print-query-cursor)
- (:conc-name "QC-")
- (:constructor %make-query-cursor))
- (db (error "missing DB") ; db conn. this table is associated with
- :type db
- :read-only t)
- (stmthp (error "missing STMTHP") ; the statement handle used to create
-;; :type alien ; this table. owned by the QUERY-CURSOR
- :read-only t) ; object, deallocated on CLOSE-QUERY
- (cds) ; (error "missing CDS") ; column descriptors
-; :type (simple-array cd 1)
-; :read-only t)
- (n-from-oci 0 ; buffered rows: number of rows recv'd
- :type (integer 0 #.+n-buf-rows+)) ; from the database on the last read
- (n-to-dbi 0 ; number of buffered rows returned, i.e.
- :type (integer 0 #.+n-buf-rows+)) ; the index, within the buffered rows,
- ; of the next row which hasn't already
- ; been returned
- (total-n-from-oci 0 ; total number of bytes recv'd from OCI
- :type unsigned-byte) ; in all reads
- (oci-end-seen-p nil)) ; Have we seen the end of OCI
- ; data, i.e. OCI returning
- ; less data than we requested?
- ; OCI doesn't seem to like us
- ; to try to read more data
- ; from it after that..
-
(defun print-query-cursor (qc stream depth)
(declare (ignore depth))
(print-unreadable-object (qc stream :type t :identity t)
buf)))
+;; Specifications
+
+(defmethod db-type-has-bigint? ((type (eql :oracle)))
+ nil)
+
+(defmethod db-type-has-fancy-math? ((db-type (eql :postgresql)))
+ t)