func (fltr *Filter) write(buf []byte, offset int) (int, error) { var err error // Write name. len := copy(buf[offset+1:], fltr.name) buf[offset] = byte(len) offset += len + 1 // Write particle type. buf[offset] = byte(fltr.valueParticleType) offset++ // Write filter begin. len, err = fltr.begin.write(buf, offset+4) if err != nil { return -1, err } Buffer.Int32ToBytes(int32(len), buf, offset) offset += len + 4 // Write filter end. len, err = fltr.end.write(buf, offset+4) if err != nil { return -1, err } Buffer.Int32ToBytes(int32(len), buf, offset) offset += len + 4 return offset, nil }
// Header write for write operations. func (cmd *baseCommand) writeHeaderWithPolicy(policy *WritePolicy, readAttr int, writeAttr int, fieldCount int, operationCount int) { // Set flags. generation := int32(0) infoAttr := 0 switch policy.RecordExistsAction { case UPDATE: case UPDATE_ONLY: infoAttr |= _INFO3_UPDATE_ONLY case REPLACE: infoAttr |= _INFO3_CREATE_OR_REPLACE case REPLACE_ONLY: infoAttr |= _INFO3_REPLACE_ONLY case CREATE_ONLY: writeAttr |= _INFO2_CREATE_ONLY } switch policy.GenerationPolicy { case NONE: case EXPECT_GEN_EQUAL: generation = policy.Generation writeAttr |= _INFO2_GENERATION case EXPECT_GEN_GT: generation = policy.Generation writeAttr |= _INFO2_GENERATION_GT } if policy.CommitLevel == COMMIT_MASTER { infoAttr |= _INFO3_COMMIT_MASTER } if policy.ConsistencyLevel == CONSISTENCY_ALL { readAttr |= _INFO1_CONSISTENCY_ALL } // Write all header data except total size which must be written last. cmd.dataBuffer[8] = _MSG_REMAINING_HEADER_SIZE // Message header length. cmd.dataBuffer[9] = byte(readAttr) cmd.dataBuffer[10] = byte(writeAttr) cmd.dataBuffer[11] = byte(infoAttr) cmd.dataBuffer[12] = 0 // unused cmd.dataBuffer[13] = 0 // clear the result code Buffer.Int32ToBytes(generation, cmd.dataBuffer, 14) Buffer.Int32ToBytes(policy.Expiration, cmd.dataBuffer, 18) // Initialize timeout. It will be written later. cmd.dataBuffer[22] = 0 cmd.dataBuffer[23] = 0 cmd.dataBuffer[24] = 0 cmd.dataBuffer[25] = 0 Buffer.Int16ToBytes(int16(fieldCount), cmd.dataBuffer, 26) Buffer.Int16ToBytes(int16(operationCount), cmd.dataBuffer, 28) cmd.dataOffset = int(_MSG_TOTAL_HEADER_SIZE) }
func (cmd *baseCommand) writeOperationForBin(bin *Bin, operation OperationType) error { nameLength := copy(cmd.dataBuffer[(cmd.dataOffset+int(_OPERATION_HEADER_SIZE)):], bin.Name) // check for float support cmd.checkServerCompatibility(bin.Value) valueLength, err := bin.Value.write(cmd.dataBuffer, cmd.dataOffset+int(_OPERATION_HEADER_SIZE)+nameLength) if err != nil { return err } Buffer.Int32ToBytes(int32(nameLength+valueLength+4), cmd.dataBuffer, cmd.dataOffset) cmd.dataOffset += 4 cmd.dataBuffer[cmd.dataOffset] = (byte(operation)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(bin.Value.GetType())) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(0)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(nameLength)) cmd.dataOffset++ cmd.dataOffset += nameLength + valueLength return nil }
func (cmd *baseCommand) writeOperationForOperationType(operation OperationType) { Buffer.Int32ToBytes(int32(4), cmd.dataBuffer, cmd.dataOffset) cmd.dataOffset += 4 cmd.dataBuffer[cmd.dataOffset] = (byte(operation)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (0) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (0) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (0) cmd.dataOffset++ }
func (cmd *baseCommand) writeOperationForBinName(name string, operation OperationType) { nameLength := copy(cmd.dataBuffer[(cmd.dataOffset+int(_OPERATION_HEADER_SIZE)):], name) Buffer.Int32ToBytes(int32(nameLength+4), cmd.dataBuffer, cmd.dataOffset) cmd.dataOffset += 4 cmd.dataBuffer[cmd.dataOffset] = (byte(operation)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(0)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(0)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(nameLength)) cmd.dataOffset++ cmd.dataOffset += nameLength }
func (cmd *baseCommand) writeOperationForOperation(operation *Operation) error { nameLength := copy(cmd.dataBuffer[(cmd.dataOffset+int(_OPERATION_HEADER_SIZE)):], operation.BinName) valueLength, err := operation.BinValue.write(cmd.dataBuffer, cmd.dataOffset+int(_OPERATION_HEADER_SIZE)+nameLength) if err != nil { return err } Buffer.Int32ToBytes(int32(nameLength+valueLength+4), cmd.dataBuffer, cmd.dataOffset) cmd.dataOffset += 4 cmd.dataBuffer[cmd.dataOffset] = (byte(operation.OpType)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(operation.BinValue.GetType())) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(0)) cmd.dataOffset++ cmd.dataBuffer[cmd.dataOffset] = (byte(nameLength)) cmd.dataOffset++ cmd.dataOffset += nameLength + valueLength return nil }
func (pckr *packer) PackInt(valType int, val int32) { pckr.buffer.WriteByte(byte(valType)) pos := pckr.grow(_b4) Buffer.Int32ToBytes(val, pckr.buffer.Bytes(), pos) }
func (cmd *baseCommand) execute(ifc command) (err error) { policy := ifc.getPolicy(ifc).GetBasePolicy() iterations := 0 // set timeout outside the loop limit := time.Now().Add(policy.Timeout) // Execute command until successful, timed out or maximum iterations have been reached. for { // too many retries if iterations++; (policy.MaxRetries > 0) && (iterations > policy.MaxRetries+1) { return NewAerospikeError(TIMEOUT, "command execution timed out: Exceeded number of retries. See `Policy.MaxRetries`") } // Sleep before trying again, after the first iteration if iterations > 1 && policy.SleepBetweenRetries > 0 { time.Sleep(policy.SleepBetweenRetries) } // check for command timeout if policy.Timeout > 0 && time.Now().After(limit) { break } node, err := ifc.getNode(ifc) if err != nil { // Node is currently inactive. Retry. continue } // set command node, so when you return a record it has the node cmd.node = node cmd.conn, err = node.GetConnection(policy.Timeout) if err != nil { // Socket connection error has occurred. Decrease health and retry. node.DecreaseHealth() Logger.Warn("Node " + node.String() + ": " + err.Error()) continue } // Draw a buffer from buffer pool, and make sure it will be put back cmd.dataBuffer = bufPool.Get() // defer bufPool.Put(cmd.dataBuffer) // Set command buffer. err = ifc.writeBuffer(ifc) if err != nil { // All runtime exceptions are considered fatal. Do not retry. // Close socket to flush out possible garbage. Do not put back in pool. node.InvalidateConnection(cmd.conn) return err } // Reset timeout in send buffer (destined for server) and socket. Buffer.Int32ToBytes(int32(policy.Timeout/time.Millisecond), cmd.dataBuffer, 22) // Send command. _, err = cmd.conn.Write(cmd.dataBuffer[:cmd.dataOffset]) if err != nil { // IO errors are considered temporary anomalies. Retry. // Close socket to flush out possible garbage. Do not put back in pool. node.InvalidateConnection(cmd.conn) Logger.Warn("Node " + node.String() + ": " + err.Error()) // IO error means connection to server node is unhealthy. // Reflect cmd status. node.DecreaseHealth() continue } // Parse results. err = ifc.parseResult(ifc, cmd.conn) if err != nil { // close the connection // cancelling/closing the batch/multi commands will return an error, which will // close the connection to throw away its data and signal the server about the // situation. We will not put back the connection in the buffer. if KeepConnection(err) { // Put connection back in pool. node.PutConnection(cmd.conn) } else { node.InvalidateConnection(cmd.conn) } return err } // Reflect healthy status. node.RestoreHealth() // Put connection back in pool. node.PutConnection(cmd.conn) // put back buffer to the pool bufPool.Put(cmd.dataBuffer) // command has completed successfully. Exit method. return nil } // execution timeout return NewAerospikeError(TIMEOUT, "command execution timed out: See `Policy.Timeout`") }
func (cmd *baseCommand) writeFieldHeader(size int, ftype FieldType) { Buffer.Int32ToBytes(int32(size+1), cmd.dataBuffer, cmd.dataOffset) cmd.dataOffset += 4 cmd.dataBuffer[cmd.dataOffset] = (byte(ftype)) cmd.dataOffset++ }
func (acmd *AdminCommand) writeFieldHeader(id byte, size int) { Buffer.Int32ToBytes(int32(size+1), acmd.dataBuffer, acmd.dataOffset) acmd.dataOffset += 4 acmd.dataBuffer[acmd.dataOffset] = id acmd.dataOffset++ }