func (node *Limit) RewriteLimit() (*Limit, error) { if node == nil { return nil, nil } var offset, count int64 var err error newLimit := new(Limit) if node.Offset == nil { offset = 0 } else { if o, ok := node.Offset.(NumVal); !ok { return nil, errors.New("Limit.offset is not number") } else { if offset, err = strconv.ParseInt(hack.String([]byte(o)), 10, 64); err != nil { return nil, err } } } if r, ok := node.Rowcount.(NumVal); !ok { return nil, errors.New("Limit.RowCount is not number") } else { if count, err = strconv.ParseInt(hack.String([]byte(r)), 10, 64); err != nil { return nil, err } } allRowCount := strconv.FormatInt((offset + count), 10) newLimit.Rowcount = NumVal(allRowCount) return newLimit, nil }
func TestCalcPassword(t *testing.T) { /* // **** JDBC **** seed: @jx=d_3z42;sS$YrS)p| hex: 406a783d645f337a34323b73532459725329707c pass: kingshard scramble: fbc71db5ac3d7b51048d1a1d88c1677f34bcca11 */ test, _ := RandomBuf(20) hex_test := hex.EncodeToString(test) t.Logf("rnd seed: %s, %s", hack.String(test), hex_test) seed := hack.Slice("@jx=d_3z42;sS$YrS)p|") hex_seed := hex.EncodeToString(seed) t.Logf("seed: %s equal %s, pass: %v", "406a783d645f337a34323b73532459725329707c", hex_seed, "406a783d645f337a34323b73532459725329707c" == hex_seed) scramble := CalcPassword(seed, hack.Slice("kingshard")) hex_scramble := hex.EncodeToString(scramble) t.Logf("scramble: %s equal %s, pass: %v", "fbc71db5ac3d7b51048d1a1d88c1677f34bcca11", hex_scramble, "fbc71db5ac3d7b51048d1a1d88c1677f34bcca11" == hex_scramble) }
//only process last_inser_id func (c *ClientConn) handleSimpleSelect(stmt *sqlparser.SimpleSelect) error { nonStarExpr, _ := stmt.SelectExprs[0].(*sqlparser.NonStarExpr) var name string = hack.String(nonStarExpr.As) if name == "" { name = "last_insert_id()" } var column = 1 var rows [][]string var names []string = []string{ name, } var t = fmt.Sprintf("%d", c.lastInsertId) rows = append(rows, []string{t}) r := new(mysql.Resultset) var values [][]interface{} = make([][]interface{}, len(rows)) for i := range rows { values[i] = make([]interface{}, column) for j := range rows[i] { values[i][j] = rows[i][j] } } r, _ = c.buildResultset(nil, names, values) return c.writeResultset(c.status, r) }
func (c *ClientConn) limitSelectResult(r *mysql.Resultset, stmt *sqlparser.Select) error { if stmt.Limit == nil { return nil } var offset, count int64 var err error if stmt.Limit.Offset == nil { offset = 0 } else { if o, ok := stmt.Limit.Offset.(sqlparser.NumVal); !ok { return fmt.Errorf("invalid select limit %s", nstring(stmt.Limit)) } else { if offset, err = strconv.ParseInt(hack.String([]byte(o)), 10, 64); err != nil { return err } } } if o, ok := stmt.Limit.Rowcount.(sqlparser.NumVal); !ok { return fmt.Errorf("invalid limit %s", nstring(stmt.Limit)) } else { if count, err = strconv.ParseInt(hack.String([]byte(o)), 10, 64); err != nil { return err } else if count < 0 { return fmt.Errorf("invalid limit %s", nstring(stmt.Limit)) } } if offset > int64(len(r.Values)) { r.Values = nil r.RowDatas = nil return nil } if offset+count > int64(len(r.Values)) { count = int64(len(r.Values)) - offset } r.Values = r.Values[offset : offset+count] r.RowDatas = r.RowDatas[offset : offset+count] return nil }
func (c *ClientConn) dispatch(data []byte) error { c.proxy.counter.IncrClientQPS() cmd := data[0] data = data[1:] switch cmd { case mysql.COM_QUIT: c.Close() return nil case mysql.COM_QUERY: return c.handleQuery(hack.String(data)) case mysql.COM_PING: return c.writeOK(nil) case mysql.COM_INIT_DB: if err := c.useDB(hack.String(data)); err != nil { return err } else { return c.writeOK(nil) } case mysql.COM_FIELD_LIST: return c.handleFieldList(data) case mysql.COM_STMT_PREPARE: return c.handleStmtPrepare(hack.String(data)) case mysql.COM_STMT_EXECUTE: return c.handleStmtExecute(data) case mysql.COM_STMT_CLOSE: return c.handleStmtClose(data) case mysql.COM_STMT_SEND_LONG_DATA: return c.handleStmtSendLongData(data) case mysql.COM_STMT_RESET: return c.handleStmtReset(data) case mysql.COM_SET_OPTION: return c.writeEOF(0) default: msg := fmt.Sprintf("command %d not supported now", cmd) golog.Error("ClientConn", "dispatch", msg, 0) return mysql.NewError(mysql.ER_UNKNOWN_ERROR, msg) } return nil }
func EncodeValue(value interface{}) string { switch val := value.(type) { case int: return Uint64Key(val).String() case uint64: return Uint64Key(val).String() case int64: return Uint64Key(val).String() case string: return val case []byte: return hack.String(val) } panic(NewKeyError("Unexpected key variable type %T", value)) }
func (r *Resultset) GetString(row, column int) (string, error) { d, err := r.GetValue(row, column) if err != nil { return "", err } switch v := d.(type) { case string: return v, nil case []byte: return hack.String(v), nil case int64: return strconv.FormatInt(v, 10), nil case uint64: return strconv.FormatUint(v, 10), nil case float64: return strconv.FormatFloat(v, 'f', -1, 64), nil case nil: return "", nil default: return "", fmt.Errorf("data type is %T", v) } }
func NumValue(value interface{}) int64 { switch val := value.(type) { case int: return int64(val) case uint64: return int64(val) case int64: return int64(val) case string: if v, err := strconv.ParseInt(val, 10, 64); err != nil { panic(NewKeyError("invalid num format %s", v)) } else { return v } case []byte: if v, err := strconv.ParseInt(hack.String(val), 10, 64); err != nil { panic(NewKeyError("invalid num format %s", v)) } else { return v } } panic(NewKeyError("Unexpected key variable type %T", value)) }
// String returns the raw value as a string func (v Value) String() string { if v.Inner == nil { return "" } return hack.String(v.Inner.raw()) }