Search in sources :

Example 16 with ResultSetHeaderPacket

use of io.mycat.net.mysql.ResultSetHeaderPacket in project Mycat_plus by coderczp.

the class EngineCtx method writeHeader.

public void writeHeader(List<byte[]> afields, List<byte[]> bfields) {
    if (headerWrited.compareAndSet(false, true)) {
        try {
            writeLock.lock();
            // write new header
            ResultSetHeaderPacket headerPkg = new ResultSetHeaderPacket();
            headerPkg.fieldCount = afields.size() + bfields.size() - 1;
            headerPkg.packetId = incPackageId();
            LOGGER.debug("packge id " + headerPkg.packetId);
            ServerConnection sc = session.getSource();
            ByteBuffer buf = headerPkg.write(sc.allocate(), sc, true);
            // wirte a fields
            for (byte[] field : afields) {
                field[3] = incPackageId();
                buf = sc.writeToBuffer(field, buf);
            }
            // write b field
            for (int i = 1; i < bfields.size(); i++) {
                byte[] bfield = bfields.get(i);
                bfield[3] = incPackageId();
                buf = sc.writeToBuffer(bfield, buf);
            }
            // write field eof
            EOFPacket eofPckg = new EOFPacket();
            eofPckg.packetId = incPackageId();
            buf = eofPckg.write(buf, sc, true);
            sc.write(buf);
        // LOGGER.info("header outputed ,packgId:" + eofPckg.packetId);
        } finally {
            writeLock.unlock();
        }
    }
}
Also used : ResultSetHeaderPacket(io.mycat.net.mysql.ResultSetHeaderPacket) EOFPacket(io.mycat.net.mysql.EOFPacket) ServerConnection(io.mycat.server.ServerConnection) ByteBuffer(java.nio.ByteBuffer)

Example 17 with ResultSetHeaderPacket

use of io.mycat.net.mysql.ResultSetHeaderPacket in project Mycat-Server by MyCATApache.

the class MysqlInformationSchemaHandler method doWrite.

/**
 * 写入数据包
 * @param field_count
 * @param fields
 * @param c
 */
private static void doWrite(int field_count, FieldPacket[] fields, ServerConnection c) {
    ByteBuffer buffer = c.allocate();
    // write header
    ResultSetHeaderPacket header = PacketUtil.getHeader(field_count);
    byte packetId = header.packetId;
    buffer = header.write(buffer, c, true);
    // write fields
    for (FieldPacket field : fields) {
        field.packetId = ++packetId;
        buffer = field.write(buffer, c, true);
    }
    // write eof
    EOFPacket eof = new EOFPacket();
    eof.packetId = ++packetId;
    buffer = eof.write(buffer, c, true);
    // write last eof
    EOFPacket lastEof = new EOFPacket();
    lastEof.packetId = ++packetId;
    buffer = lastEof.write(buffer, c, true);
    // post write
    c.write(buffer);
}
Also used : ResultSetHeaderPacket(io.mycat.net.mysql.ResultSetHeaderPacket) EOFPacket(io.mycat.net.mysql.EOFPacket) ByteBuffer(java.nio.ByteBuffer) FieldPacket(io.mycat.net.mysql.FieldPacket)

Example 18 with ResultSetHeaderPacket

use of io.mycat.net.mysql.ResultSetHeaderPacket in project Mycat-Server by MyCATApache.

the class JDBCConnection method ouputResultSet.

private void ouputResultSet(ServerConnection sc, String sql) throws SQLException {
    ResultSet rs = null;
    Statement stmt = null;
    try {
        stmt = con.createStatement();
        rs = stmt.executeQuery(sql);
        List<FieldPacket> fieldPks = new LinkedList<FieldPacket>();
        ResultSetUtil.resultSetToFieldPacket(sc.getCharset(), fieldPks, rs, this.isSpark);
        int colunmCount = fieldPks.size();
        ByteBuffer byteBuf = sc.allocate();
        ResultSetHeaderPacket headerPkg = new ResultSetHeaderPacket();
        headerPkg.fieldCount = fieldPks.size();
        headerPkg.packetId = ++packetId;
        byteBuf = headerPkg.write(byteBuf, sc, true);
        byteBuf.flip();
        byte[] header = new byte[byteBuf.limit()];
        byteBuf.get(header);
        byteBuf.clear();
        List<byte[]> fields = new ArrayList<byte[]>(fieldPks.size());
        Iterator<FieldPacket> itor = fieldPks.iterator();
        while (itor.hasNext()) {
            FieldPacket curField = itor.next();
            curField.packetId = ++packetId;
            byteBuf = curField.write(byteBuf, sc, false);
            byteBuf.flip();
            byte[] field = new byte[byteBuf.limit()];
            byteBuf.get(field);
            byteBuf.clear();
            fields.add(field);
        }
        EOFPacket eofPckg = new EOFPacket();
        eofPckg.packetId = ++packetId;
        byteBuf = eofPckg.write(byteBuf, sc, false);
        byteBuf.flip();
        byte[] eof = new byte[byteBuf.limit()];
        byteBuf.get(eof);
        byteBuf.clear();
        this.respHandler.fieldEofResponse(header, fields, eof, this);
        // output row
        while (rs.next()) {
            RowDataPacket curRow = new RowDataPacket(colunmCount);
            for (int i = 0; i < colunmCount; i++) {
                int j = i + 1;
                if (MysqlDefs.isBianry((byte) fieldPks.get(i).type)) {
                    curRow.add(rs.getBytes(j));
                } else if (fieldPks.get(i).type == MysqlDefs.FIELD_TYPE_DECIMAL || fieldPks.get(i).type == (MysqlDefs.FIELD_TYPE_NEW_DECIMAL - 256)) {
                    // field type is unsigned byte
                    // ensure that do not use scientific notation format
                    BigDecimal val = rs.getBigDecimal(j);
                    curRow.add(StringUtil.encode(val != null ? val.toPlainString() : null, sc.getCharset()));
                } else {
                    curRow.add(StringUtil.encode(rs.getString(j), sc.getCharset()));
                }
            }
            curRow.packetId = ++packetId;
            byteBuf = curRow.write(byteBuf, sc, false);
            byteBuf.flip();
            byte[] row = new byte[byteBuf.limit()];
            byteBuf.get(row);
            byteBuf.clear();
            this.respHandler.rowResponse(row, this);
        }
        fieldPks.clear();
        // end row
        eofPckg = new EOFPacket();
        eofPckg.packetId = ++packetId;
        byteBuf = eofPckg.write(byteBuf, sc, false);
        byteBuf.flip();
        eof = new byte[byteBuf.limit()];
        byteBuf.get(eof);
        sc.recycle(byteBuf);
        this.respHandler.rowEofResponse(eof, this);
    } finally {
        if (rs != null) {
            try {
                rs.close();
            } catch (SQLException e) {
            }
        }
        if (stmt != null) {
            try {
                stmt.close();
            } catch (SQLException e) {
            }
        }
    }
}
Also used : ResultSetHeaderPacket(io.mycat.net.mysql.ResultSetHeaderPacket) RowDataPacket(io.mycat.net.mysql.RowDataPacket) EOFPacket(io.mycat.net.mysql.EOFPacket) ByteBuffer(java.nio.ByteBuffer) BigDecimal(java.math.BigDecimal) FieldPacket(io.mycat.net.mysql.FieldPacket)

Example 19 with ResultSetHeaderPacket

use of io.mycat.net.mysql.ResultSetHeaderPacket in project Mycat-Server by MyCATApache.

the class MultiNodeQueryHandler method fieldEofResponse.

@Override
public void fieldEofResponse(byte[] header, List<byte[]> fields, byte[] eof, BackendConnection conn) {
    // huangyiming add
    this.header = header;
    this.fields = fields;
    MiddlerResultHandler middlerResultHandler = session.getMiddlerResultHandler();
    /*if(null !=middlerResultHandler ){
			return;
		}*/
    this.netOutBytes += header.length;
    this.netOutBytes += eof.length;
    for (int i = 0, len = fields.size(); i < len; ++i) {
        byte[] field = fields.get(i);
        this.netOutBytes += field.length;
    }
    ServerConnection source = null;
    if (fieldsReturned) {
        return;
    }
    lock.lock();
    try {
        if (fieldsReturned) {
            return;
        }
        fieldsReturned = true;
        boolean needMerg = (dataMergeSvr != null) && dataMergeSvr.getRrs().needMerge();
        Set<String> shouldRemoveAvgField = new HashSet<>();
        Set<String> shouldRenameAvgField = new HashSet<>();
        if (needMerg) {
            Map<String, Integer> mergeColsMap = dataMergeSvr.getRrs().getMergeCols();
            if (mergeColsMap != null) {
                for (Map.Entry<String, Integer> entry : mergeColsMap.entrySet()) {
                    String key = entry.getKey();
                    int mergeType = entry.getValue();
                    if (MergeCol.MERGE_AVG == mergeType && mergeColsMap.containsKey(key + "SUM")) {
                        shouldRemoveAvgField.add((key + "COUNT").toUpperCase());
                        shouldRenameAvgField.add((key + "SUM").toUpperCase());
                    }
                }
            }
        }
        source = session.getSource();
        ByteBuffer buffer = source.allocate();
        fieldCount = fields.size();
        if (shouldRemoveAvgField.size() > 0) {
            ResultSetHeaderPacket packet = new ResultSetHeaderPacket();
            packet.packetId = ++packetId;
            packet.fieldCount = fieldCount - shouldRemoveAvgField.size();
            buffer = packet.write(buffer, source, true);
        } else {
            header[3] = ++packetId;
            buffer = source.writeToBuffer(header, buffer);
        }
        String primaryKey = null;
        if (rrs.hasPrimaryKeyToCache()) {
            String[] items = rrs.getPrimaryKeyItems();
            priamaryKeyTable = items[0];
            primaryKey = items[1];
        }
        Map<String, ColMeta> columToIndx = new HashMap<String, ColMeta>(fieldCount);
        for (int i = 0, len = fieldCount; i < len; ++i) {
            boolean shouldSkip = false;
            byte[] field = fields.get(i);
            if (needMerg) {
                FieldPacket fieldPkg = new FieldPacket();
                fieldPkg.read(field);
                fieldPackets.add(fieldPkg);
                String fieldName = new String(fieldPkg.name).toUpperCase();
                if (columToIndx != null && !columToIndx.containsKey(fieldName)) {
                    if (shouldRemoveAvgField.contains(fieldName)) {
                        shouldSkip = true;
                        fieldPackets.remove(fieldPackets.size() - 1);
                    }
                    if (shouldRenameAvgField.contains(fieldName)) {
                        String newFieldName = fieldName.substring(0, fieldName.length() - 3);
                        fieldPkg.name = newFieldName.getBytes();
                        fieldPkg.packetId = ++packetId;
                        shouldSkip = true;
                        // 处理AVG字段位数和精度, AVG位数 = SUM位数 - 14
                        fieldPkg.length = fieldPkg.length - 14;
                        // AVG精度 = SUM精度 + 4
                        fieldPkg.decimals = (byte) (fieldPkg.decimals + 4);
                        buffer = fieldPkg.write(buffer, source, false);
                        // 还原精度
                        fieldPkg.decimals = (byte) (fieldPkg.decimals - 4);
                    }
                    ColMeta colMeta = new ColMeta(i, fieldPkg.type);
                    colMeta.decimals = fieldPkg.decimals;
                    columToIndx.put(fieldName, colMeta);
                }
            } else {
                FieldPacket fieldPkg = new FieldPacket();
                fieldPkg.read(field);
                fieldPackets.add(fieldPkg);
                fieldCount = fields.size();
                if (primaryKey != null && primaryKeyIndex == -1) {
                    // find primary key index
                    String fieldName = new String(fieldPkg.name);
                    if (primaryKey.equalsIgnoreCase(fieldName)) {
                        primaryKeyIndex = i;
                    }
                }
            }
            if (!shouldSkip) {
                field[3] = ++packetId;
                buffer = source.writeToBuffer(field, buffer);
            }
        }
        eof[3] = ++packetId;
        buffer = source.writeToBuffer(eof, buffer);
        if (null == middlerResultHandler) {
            // session.getSource().write(row);
            source.write(buffer);
        }
        if (dataMergeSvr != null) {
            dataMergeSvr.onRowMetaData(columToIndx, fieldCount);
        }
    } catch (Exception e) {
        handleDataProcessException(e);
    } finally {
        lock.unlock();
    }
}
Also used : ResultSetHeaderPacket(io.mycat.net.mysql.ResultSetHeaderPacket) ColMeta(io.mycat.sqlengine.mpp.ColMeta) HashMap(java.util.HashMap) ServerConnection(io.mycat.server.ServerConnection) ByteBuffer(java.nio.ByteBuffer) IOException(java.io.IOException) HashMap(java.util.HashMap) Map(java.util.Map) FieldPacket(io.mycat.net.mysql.FieldPacket) HashSet(java.util.HashSet)

Example 20 with ResultSetHeaderPacket

use of io.mycat.net.mysql.ResultSetHeaderPacket in project Mycat-Server by MyCATApache.

the class PostgreSQLBackendConnectionHandler method doProcessBusinessQuery.

/**
 *************
 *  处理简单查询结果 ,每一个查询都是一件 CommandComplete 为结束
 * @param con PostgreSQL 后端连接
 * @param response
 * @param commandComplete
 */
private void doProcessBusinessQuery(PostgreSQLBackendConnection con, SelectResponse response, CommandComplete commandComplete) {
    RowDescription rowHd = response.getDescription();
    List<FieldPacket> fieldPks = PgPacketApaterUtils.rowDescConvertFieldPacket(rowHd);
    List<RowDataPacket> rowDatas = new ArrayList<>();
    for (DataRow dataRow : response.getDataRows()) {
        rowDatas.add(PgPacketApaterUtils.rowDataConvertRowDataPacket(dataRow));
    }
    BufferArray bufferArray = MycatServer.getInstance().getBufferPool().allocateArray();
    ResultSetHeaderPacket headerPkg = new ResultSetHeaderPacket();
    headerPkg.fieldCount = fieldPks.size();
    headerPkg.packetId = ++packetId;
    headerPkg.write(bufferArray);
    byte[] header = bufferArray.writeToByteArrayAndRecycle();
    List<byte[]> fields = new ArrayList<byte[]>(fieldPks.size());
    Iterator<FieldPacket> itor = fieldPks.iterator();
    while (itor.hasNext()) {
        bufferArray = MycatServer.getInstance().getBufferPool().allocateArray();
        FieldPacket curField = itor.next();
        curField.packetId = ++packetId;
        curField.write(bufferArray);
        byte[] field = bufferArray.writeToByteArrayAndRecycle();
        fields.add(field);
        itor.remove();
    }
    bufferArray = MycatServer.getInstance().getBufferPool().allocateArray();
    EOFPacket eofPckg = new EOFPacket();
    eofPckg.packetId = ++packetId;
    eofPckg.write(bufferArray);
    byte[] eof = bufferArray.writeToByteArrayAndRecycle();
    if (con.getResponseHandler() != null) {
        con.getResponseHandler().fieldEofResponse(header, fields, eof, con);
    } else {
        LOGGER.error("响应句柄为空");
    }
    // output row
    for (RowDataPacket curRow : rowDatas) {
        bufferArray = MycatServer.getInstance().getBufferPool().allocateArray();
        curRow.packetId = ++packetId;
        curRow.write(bufferArray);
        byte[] row = bufferArray.writeToByteArrayAndRecycle();
        con.getResponseHandler().rowResponse(row, con);
    }
    // end row
    bufferArray = MycatServer.getInstance().getBufferPool().allocateArray();
    eofPckg = new EOFPacket();
    eofPckg.packetId = ++packetId;
    eofPckg.write(bufferArray);
    eof = bufferArray.writeToByteArrayAndRecycle();
    if (con.getResponseHandler() != null) {
        con.getResponseHandler().rowEofResponse(eof, con);
    } else {
        LOGGER.error("响应句柄为空");
    }
}
Also used : ResultSetHeaderPacket(io.mycat.net.mysql.ResultSetHeaderPacket) RowDataPacket(io.mycat.net.mysql.RowDataPacket) ArrayList(java.util.ArrayList) EOFPacket(io.mycat.net.mysql.EOFPacket) DataRow(io.mycat.backend.postgresql.packet.DataRow) RowDescription(io.mycat.backend.postgresql.packet.RowDescription) BufferArray(io.mycat.buffer.BufferArray) FieldPacket(io.mycat.net.mysql.FieldPacket)

Aggregations

ResultSetHeaderPacket (io.mycat.net.mysql.ResultSetHeaderPacket)22 ByteBuffer (java.nio.ByteBuffer)19 EOFPacket (io.mycat.net.mysql.EOFPacket)18 FieldPacket (io.mycat.net.mysql.FieldPacket)18 RowDataPacket (io.mycat.net.mysql.RowDataPacket)13 ServerConnection (io.mycat.server.ServerConnection)4 Procedure (io.mycat.route.Procedure)2 ProcedureParameter (io.mycat.route.ProcedureParameter)2 RouteResultset (io.mycat.route.RouteResultset)2 RouteResultsetNode (io.mycat.route.RouteResultsetNode)2 ColMeta (io.mycat.sqlengine.mpp.ColMeta)2 IOException (java.io.IOException)2 BigDecimal (java.math.BigDecimal)2 HashMap (java.util.HashMap)2 HashSet (java.util.HashSet)2 Map (java.util.Map)2 DataRow (io.mycat.backend.postgresql.packet.DataRow)1 RowDescription (io.mycat.backend.postgresql.packet.RowDescription)1 BufferArray (io.mycat.buffer.BufferArray)1 ArrayList (java.util.ArrayList)1