Example #1
0
// BindByIndex binds value to the specified host parameter of the prepared statement.
// Value's type/kind is used to find the storage class.
// The leftmost SQL parameter has an index of 1.
func (s *Stmt) BindByIndex(index int, value interface{}) error {
	i := C.int(index)
	var rv C.int
	switch value := value.(type) {
	case nil:
		rv = C.sqlite3_bind_null(s.stmt, i)
	case string:
		if NullIfEmptyString && len(value) == 0 {
			rv = C.sqlite3_bind_null(s.stmt, i)
		} else {
			cs, l := cstring(value)
			rv = C.my_bind_text(s.stmt, i, cs, l)
		}
	case int:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case int64:
		rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value))
	case byte:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case bool:
		rv = C.sqlite3_bind_int(s.stmt, i, btocint(value))
	case float32:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case float64:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case []byte:
		var p *byte
		if len(value) > 0 {
			p = &value[0]
		}
		rv = C.my_bind_blob(s.stmt, i, unsafe.Pointer(p), C.int(len(value)))
	case time.Time:
		if NullIfZeroTime && value.IsZero() {
			rv = C.sqlite3_bind_null(s.stmt, i)
		} else {
			rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value.Unix()))
		}
	case ZeroBlobLength:
		rv = C.sqlite3_bind_zeroblob(s.stmt, i, C.int(value))
	case driver.Valuer:
		v, err := value.Value()
		if err != nil {
			return err
		}
		return s.BindByIndex(index, v)
	default:
		return s.BindReflect(index, value)
	}
	return s.error(rv, "Stmt.Bind")
}
Example #2
0
File: stmt.go Project: pkf/gosqlite
// BindByIndex binds value to the specified host parameter of the prepared statement.
// The leftmost SQL parameter has an index of 1.
func (s *Stmt) BindByIndex(index int, value interface{}) error {
	i := C.int(index)
	var rv C.int
	switch value := value.(type) {
	case nil:
		rv = C.sqlite3_bind_null(s.stmt, i)
	case string:
		cs, l := cstring(value)
		rv = C.my_bind_text(s.stmt, i, cs, l)
	case int:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case int64:
		rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value))
	case byte:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case bool:
		rv = C.sqlite3_bind_int(s.stmt, i, btocint(value))
	case float32:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case float64:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case []byte:
		var p *byte
		if len(value) > 0 {
			p = &value[0]
		}
		rv = C.my_bind_blob(s.stmt, i, unsafe.Pointer(p), C.int(len(value)))
	case time.Time: // At least three representations are possible: string (YYYY-MM-DD HH:MM:SS.SSS), int64 (unix time), float64 (julian day)
		// rv = C.my_bind_text(s.stmt, i, value.format("2006-01-02 15:04:05.000"))
		rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value.Unix()))
		// rv = C.sqlite3_bind_double(s.stmt, i, JulianDay(value))
	case ZeroBlobLength:
		rv = C.sqlite3_bind_zeroblob(s.stmt, i, C.int(value))
	default:
		return s.specificError("unsupported type in Bind: %T", value)
	}
	return s.error(rv, "Stmt.Bind")
}
Example #3
0
// bind binds statement parameter i (starting at 1) to the value v. The
// parameter name is only used for error reporting.
func (s *Stmt) bind(i C.int, v interface{}, name string) error {
	if v == nil {
		return nil // Unbound parameters are NULL by default
	}
	var rc C.int
	switch v := v.(type) {
	case int:
		rc = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(v))
	case int64:
		rc = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(v))
	case float64:
		rc = C.sqlite3_bind_double(s.stmt, i, C.double(v))
	case bool:
		rc = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(cBool(v)))
	case string:
		rc = C.bind_text(s.stmt, i, cStr(v), C.int(len(v)), 1)
	case []byte:
		rc = C.bind_blob(s.stmt, i, cBytes(v), C.int(len(v)), 1)
	case time.Time:
		rc = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(v.Unix()))
	case RawString:
		rc = C.bind_text(s.stmt, i, cStr(string(v)), C.int(len(v)), 0)
	case RawBytes:
		rc = C.bind_blob(s.stmt, i, cBytes(v), C.int(len(v)), 0)
	case ZeroBlob:
		rc = C.sqlite3_bind_zeroblob(s.stmt, i, C.int(v))
	default:
		if name != "" {
			return pkgErr(MISUSE, "unsupported type for %s (%T)", name, v)
		}
		return pkgErr(MISUSE, "unsupported type at index %d (%T)", int(i-1), v)
	}
	if rc != OK {
		return libErr(rc, s.conn.db)
	}
	return nil
}
Example #4
0
// BindByIndex binds value to the specified host parameter of the prepared statement.
// Value's type/kind is used to find the storage class.
// The leftmost SQL parameter has an index of 1.
func (s *Stmt) BindByIndex(index int, value interface{}) error {
	i := C.int(index)
	var rv C.int
	switch value := value.(type) {
	case nil:
		rv = C.sqlite3_bind_null(s.stmt, i)
	case string:
		if len(value) == 0 {
			if NullIfEmptyString {
				rv = C.sqlite3_bind_null(s.stmt, i)
			} else {
				rv = C.my_bind_empty_text(s.stmt, i)
			}
		} else {
			if i64 && len(value) > math.MaxInt32 {
				return s.specificError("string too big: %d at index %d", len(value), index)
			}
			rv = C.my_bind_text(s.stmt, i, C.CString(value), C.int(len(value)))
		}
	case int:
		if i64 {
			rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value))
		} else {
			rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
		}
	case int32:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case int64:
		rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value))
	case byte:
		rv = C.sqlite3_bind_int(s.stmt, i, C.int(value))
	case bool:
		rv = C.sqlite3_bind_int(s.stmt, i, btocint(value))
	case float32:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case float64:
		rv = C.sqlite3_bind_double(s.stmt, i, C.double(value))
	case []byte:
		if i64 && len(value) > math.MaxInt32 {
			return s.specificError("blob too big: %d at index %d", len(value), index)
		}
		var p *byte
		if len(value) > 0 {
			p = &value[0]
		}
		rv = C.my_bind_blob(s.stmt, i, unsafe.Pointer(p), C.int(len(value)))
	case time.Time:
		if NullIfZeroTime && value.IsZero() {
			rv = C.sqlite3_bind_null(s.stmt, i)
		} else if s.c.DefaultTimeLayout == "" {
			rv = C.sqlite3_bind_int64(s.stmt, i, C.sqlite3_int64(value.Unix()))
		} else {
			v := value.Format(s.c.DefaultTimeLayout)
			rv = C.my_bind_text(s.stmt, i, C.CString(v), C.int(len(v)))
		}
	case ZeroBlobLength:
		rv = C.sqlite3_bind_zeroblob(s.stmt, i, C.int(value))
	case driver.Valuer:
		v, err := value.Value()
		if err != nil {
			return err
		}
		return s.BindByIndex(index, v)
	default:
		return s.BindReflect(index, value)
	}
	return s.error(rv, "Stmt.Bind")
}