app-init
This commit is contained in:
@@ -0,0 +1,95 @@
|
||||
package mysqlserver
|
||||
|
||||
import (
|
||||
"mysql-tunnel/internal/navicat"
|
||||
)
|
||||
|
||||
func encodeColumnCount(n int) []byte {
|
||||
return appendLenencInt(nil, uint64(n))
|
||||
}
|
||||
|
||||
func encodeColumn(f navicat.Field) []byte {
|
||||
typ := byte(f.Type)
|
||||
charset := uint16(charsetUTF8MB4)
|
||||
if isNumericType(typ) || f.Flags&uint32(flagBinary) != 0 && isBlobType(typ) {
|
||||
charset = uint16(charsetBinary)
|
||||
}
|
||||
if isNumericType(typ) {
|
||||
charset = uint16(charsetBinary)
|
||||
}
|
||||
length := f.Length
|
||||
if length == 0 {
|
||||
length = uint32(len(f.Name))
|
||||
if length == 0 {
|
||||
length = 64
|
||||
}
|
||||
}
|
||||
flags := uint16(f.Flags)
|
||||
decimals := byte(0)
|
||||
if typ == typeFloat || typ == typeDouble || typ == typeNewDecimal || typ == typeDecimal {
|
||||
decimals = 31
|
||||
}
|
||||
|
||||
b := appendLenencString(nil, []byte("def"))
|
||||
b = appendLenencString(b, nil) // schema
|
||||
b = appendLenencString(b, []byte(f.Table))
|
||||
b = appendLenencString(b, []byte(f.Table))
|
||||
b = appendLenencString(b, []byte(f.Name))
|
||||
b = appendLenencString(b, []byte(f.Name))
|
||||
b = appendLenencInt(b, 0x0c)
|
||||
b = appendU16(b, charset)
|
||||
b = appendU32(b, length)
|
||||
b = append(b, typ)
|
||||
b = appendU16(b, flags)
|
||||
b = append(b, decimals, 0x00, 0x00)
|
||||
return b
|
||||
}
|
||||
|
||||
func encodeTextRow(row []navicat.Cell) []byte {
|
||||
var b []byte
|
||||
for _, c := range row {
|
||||
if c.Null {
|
||||
b = append(b, markerNull)
|
||||
continue
|
||||
}
|
||||
b = appendLenencString(b, c.Bytes)
|
||||
}
|
||||
return b
|
||||
}
|
||||
|
||||
func isBlobType(t byte) bool {
|
||||
switch t {
|
||||
case typeTinyBlob, typeMediumBlob, typeLongBlob, typeBlob:
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
func (p *packetConn) writeResultSet(res navicat.Result, caps uint32, status uint16) error {
|
||||
if err := p.writePacket(encodeColumnCount(len(res.Fields))); err != nil {
|
||||
return err
|
||||
}
|
||||
for _, f := range res.Fields {
|
||||
if err := p.writePacket(encodeColumn(f)); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
if caps&clientDeprecateEOF != 0 {
|
||||
if err := p.writeOK(0, 0, status, 0); err != nil {
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
if err := p.writePacket(encodeEOF(0, status)); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
for _, row := range res.Rows {
|
||||
if err := p.writePacket(encodeTextRow(row)); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
if caps&clientDeprecateEOF != 0 {
|
||||
return p.writeOK(uint64(res.AffectedRows), uint64(res.InsertID), status, 0)
|
||||
}
|
||||
return p.writePacket(encodeEOF(0, status))
|
||||
}
|
||||
Reference in New Issue
Block a user