Search in sources :

Example 66 with ByteBuf

use of com.couchbase.client.core.deps.io.netty.buffer.ByteBuf in project couchbase-jvm-clients by couchbase.

the class FeatureNegotiatingHandler method extractFeaturesFromBody.

/**
 * Helper method to safely extract the negotiated server features from the
 * body of the memcache payload.
 *
 * @param response the response to extract from.
 * @return the list of server features, may be empty but never null.
 */
private Set<ServerFeature> extractFeaturesFromBody(final ByteBuf response) {
    Optional<ByteBuf> body = MemcacheProtocol.body(response);
    Set<ServerFeature> negotiated = EnumSet.noneOf(ServerFeature.class);
    List<ServerFeature> unsolicited = new ArrayList<>();
    if (!body.isPresent()) {
        return negotiated;
    }
    while (body.get().isReadable()) {
        try {
            short featureRaw = body.get().readShort();
            ServerFeature feature = ServerFeature.from(featureRaw);
            if (features.contains(feature)) {
                negotiated.add(feature);
            } else {
                unsolicited.add(feature);
            }
        } catch (Exception ex) {
            interceptedConnectPromise.tryFailure(new CouchbaseException("Error while parsing negotiated server features.", ex));
        }
    }
    if (!unsolicited.isEmpty()) {
        endpointContext.environment().eventBus().publish(new UnsolicitedFeaturesReturnedEvent(ioContext, unsolicited));
    }
    return negotiated;
}
Also used : CouchbaseException(com.couchbase.client.core.error.CouchbaseException) UnsolicitedFeaturesReturnedEvent(com.couchbase.client.core.cnc.events.io.UnsolicitedFeaturesReturnedEvent) ArrayList(java.util.ArrayList) ByteBuf(com.couchbase.client.core.deps.io.netty.buffer.ByteBuf) CouchbaseException(com.couchbase.client.core.error.CouchbaseException) TimeoutException(java.util.concurrent.TimeoutException)

Example 67 with ByteBuf

use of com.couchbase.client.core.deps.io.netty.buffer.ByteBuf in project couchbase-jvm-clients by couchbase.

the class QueryRequest method encode.

@Override
public FullHttpRequest encode() {
    ByteBuf content = Unpooled.wrappedBuffer(query);
    FullHttpRequest request = new DefaultFullHttpRequest(HttpVersion.HTTP_1_1, HttpMethod.POST, URI, content);
    request.headers().set(HttpHeaderNames.CONTENT_TYPE, HttpHeaderValues.APPLICATION_JSON);
    request.headers().set(HttpHeaderNames.CONTENT_LENGTH, content.readableBytes());
    request.headers().set(HttpHeaderNames.USER_AGENT, context().environment().userAgent().formattedLong());
    authenticator.authHttpRequest(serviceType(), request);
    return request;
}
Also used : FullHttpRequest(com.couchbase.client.core.deps.io.netty.handler.codec.http.FullHttpRequest) DefaultFullHttpRequest(com.couchbase.client.core.deps.io.netty.handler.codec.http.DefaultFullHttpRequest) DefaultFullHttpRequest(com.couchbase.client.core.deps.io.netty.handler.codec.http.DefaultFullHttpRequest) ByteBuf(com.couchbase.client.core.deps.io.netty.buffer.ByteBuf)

Example 68 with ByteBuf

use of com.couchbase.client.core.deps.io.netty.buffer.ByteBuf in project couchbase-jvm-clients by couchbase.

the class SubdocMutateRequest method decode.

@Override
public SubdocMutateResponse decode(final ByteBuf response, KeyValueChannelContext ctx) {
    Optional<ByteBuf> maybeBody = body(response);
    short rawOverallStatus = status(response);
    ResponseStatus overallStatus = decodeStatus(response);
    Optional<CouchbaseException> error = Optional.empty();
    SubDocumentField[] values = null;
    if (maybeBody.isPresent()) {
        ByteBuf body = maybeBody.get();
        // If there's a multi-mutation failure we only get the first failure back
        if (rawOverallStatus == Status.SUBDOC_MULTI_PATH_FAILURE.status() || rawOverallStatus == Status.SUBDOC_MULTI_PATH_FAILURE_DELETED.status()) {
            byte index = body.readByte();
            short opStatusRaw = body.readShort();
            SubDocumentOpResponseStatus opStatus = decodeSubDocumentStatus(opStatusRaw);
            Command c = commands.get(index);
            error = Optional.of(mapSubDocumentError(this, opStatus, c.path, c.originalIndex));
            values = new SubDocumentField[0];
        } else if (overallStatus.success()) {
            // "For successful multi mutations, there will be zero or more results; each of the results containing a value."
            values = new SubDocumentField[commands.size()];
            // Check we can read index (1 byte) and status (2 bytes), else we're done
            int INDEX_PLUS_STATUS_FIELDS_BYTES = 3;
            while (body.isReadable(INDEX_PLUS_STATUS_FIELDS_BYTES)) {
                byte index = body.readByte();
                Command command = commands.get(index);
                // "Status of the mutation. If the status indicates success, the next two fields are applicable. If it is an
                // error then the result has been fully read"
                short statusRaw = body.readShort();
                SubDocumentOpResponseStatus status = decodeSubDocumentStatus(statusRaw);
                if (status != SubDocumentOpResponseStatus.SUCCESS) {
                    CouchbaseException err = mapSubDocumentError(this, status, command.path, command.originalIndex);
                    SubDocumentField op = new SubDocumentField(status, Optional.of(err), Bytes.EMPTY_BYTE_ARRAY, command.path, command.type);
                    values[command.originalIndex] = op;
                } else {
                    int valueLength = body.readInt();
                    byte[] value = new byte[valueLength];
                    body.readBytes(value, 0, valueLength);
                    SubDocumentField op = new SubDocumentField(status, Optional.empty(), value, command.path, command.type);
                    values[command.originalIndex] = op;
                }
            }
        }
    }
    if (values == null) {
        values = new SubDocumentField[0];
    }
    // Handle any document-level failures here
    if (rawOverallStatus == Status.SUBDOC_DOC_NOT_JSON.status()) {
        SubDocumentErrorContext e = createSubDocumentExceptionContext(SubDocumentOpResponseStatus.DOC_NOT_JSON);
        error = Optional.of(new DocumentNotJsonException(e));
    } else if (rawOverallStatus == Status.SUBDOC_DOC_TOO_DEEP.status()) {
        SubDocumentErrorContext e = createSubDocumentExceptionContext(SubDocumentOpResponseStatus.DOC_TOO_DEEP);
        error = Optional.of(new DocumentTooDeepException(e));
    } else if (rawOverallStatus == Status.SUBDOC_XATTR_INVALID_KEY_COMBO.status()) {
        SubDocumentErrorContext e = createSubDocumentExceptionContext(SubDocumentOpResponseStatus.XATTR_INVALID_KEY_COMBO);
        error = Optional.of(new XattrInvalidKeyComboException(e));
    } else if (rawOverallStatus == Status.SUBDOC_CAN_ONLY_REVIVE_DELETED_DOCUMENTS.status()) {
        SubDocumentErrorContext e = createSubDocumentExceptionContext(SubDocumentOpResponseStatus.CAN_ONLY_REVIVE_DELETED_DOCUMENTS);
        error = Optional.of(new DocumentAlreadyAliveException(e));
    }
    // Do not handle SUBDOC_INVALID_COMBO here, it indicates a client-side bug
    return new SubdocMutateResponse(overallStatus, error, values, cas(response), extractToken(ctx.mutationTokensEnabled(), partition(), response, ctx.bucket().get()));
}
Also used : DocumentNotJsonException(com.couchbase.client.core.error.subdoc.DocumentNotJsonException) CompositeByteBuf(com.couchbase.client.core.deps.io.netty.buffer.CompositeByteBuf) ByteBuf(com.couchbase.client.core.deps.io.netty.buffer.ByteBuf) SubDocumentErrorContext(com.couchbase.client.core.error.context.SubDocumentErrorContext) DocumentAlreadyAliveException(com.couchbase.client.core.error.subdoc.DocumentAlreadyAliveException) CouchbaseException(com.couchbase.client.core.error.CouchbaseException) ResponseStatus(com.couchbase.client.core.msg.ResponseStatus) DocumentTooDeepException(com.couchbase.client.core.error.subdoc.DocumentTooDeepException) XattrInvalidKeyComboException(com.couchbase.client.core.error.subdoc.XattrInvalidKeyComboException)

Example 69 with ByteBuf

use of com.couchbase.client.core.deps.io.netty.buffer.ByteBuf in project couchbase-jvm-clients by couchbase.

the class BaseEndpointIntegrationTest method startLocalServer.

private LocalServerController startLocalServer(final DefaultEventLoopGroup eventLoopGroup) {
    final LocalServerController localServerController = new LocalServerController();
    ServerBootstrap bootstrap = new ServerBootstrap().group(eventLoopGroup).localAddress(new LocalAddress("server")).childHandler(new ChannelInitializer<Channel>() {

        @Override
        protected void initChannel(Channel ch) {
            ch.pipeline().addLast(new SimpleChannelInboundHandler<ByteBuf>() {

                @Override
                protected void channelRead0(ChannelHandlerContext ctx, ByteBuf msg) {
                }

                @Override
                public void channelActive(ChannelHandlerContext ctx) {
                    localServerController.channel.set(ctx.channel());
                    localServerController.connectAttempts.incrementAndGet();
                    ctx.fireChannelActive();
                }
            });
        }
    }).channel(LocalServerChannel.class);
    bootstrap.bind().awaitUninterruptibly();
    return localServerController;
}
Also used : LocalAddress(com.couchbase.client.core.deps.io.netty.channel.local.LocalAddress) Channel(com.couchbase.client.core.deps.io.netty.channel.Channel) LocalServerChannel(com.couchbase.client.core.deps.io.netty.channel.local.LocalServerChannel) ChannelHandlerContext(com.couchbase.client.core.deps.io.netty.channel.ChannelHandlerContext) ChannelInitializer(com.couchbase.client.core.deps.io.netty.channel.ChannelInitializer) ByteBuf(com.couchbase.client.core.deps.io.netty.buffer.ByteBuf) ServerBootstrap(com.couchbase.client.core.deps.io.netty.bootstrap.ServerBootstrap)

Example 70 with ByteBuf

use of com.couchbase.client.core.deps.io.netty.buffer.ByteBuf in project couchbase-jvm-clients by couchbase.

the class MemcacheProtocolDecodeHandlerTest method writeAsRandomChunks.

/**
 * Helper method to randomly chunk up the source until the channel emits a new message.
 *
 * @param channel the channel to write into.
 * @param source  the source buffer.
 */
private static void writeAsRandomChunks(final EmbeddedChannel channel, final ByteBuf source) {
    while (channel.inboundMessages().isEmpty()) {
        int chunkSize = new Random().nextInt(source.readableBytes() + 1);
        ByteBuf toWrite = source.readBytes(chunkSize);
        channel.writeOneInbound(toWrite);
    }
}
Also used : Random(java.util.Random) ByteBuf(com.couchbase.client.core.deps.io.netty.buffer.ByteBuf)

Aggregations

ByteBuf (com.couchbase.client.core.deps.io.netty.buffer.ByteBuf)107 Test (org.junit.jupiter.api.Test)54 InetSocketAddress (java.net.InetSocketAddress)17 EmbeddedChannel (com.couchbase.client.core.deps.io.netty.channel.embedded.EmbeddedChannel)12 ChannelFuture (com.couchbase.client.core.deps.io.netty.channel.ChannelFuture)11 Duration (java.time.Duration)10 CouchbaseException (com.couchbase.client.core.error.CouchbaseException)9 CoreContext (com.couchbase.client.core.CoreContext)8 ParameterizedTest (org.junit.jupiter.params.ParameterizedTest)8 CompressionConfig (com.couchbase.client.core.env.CompressionConfig)6 ResponseStatus (com.couchbase.client.core.msg.ResponseStatus)6 GetRequest (com.couchbase.client.core.msg.kv.GetRequest)6 ChannelHandlerContext (com.couchbase.client.core.deps.io.netty.channel.ChannelHandlerContext)5 AuthenticationFailureException (com.couchbase.client.core.error.AuthenticationFailureException)5 ArrayList (java.util.ArrayList)5 DurabilityTimeoutCoercedEvent (com.couchbase.client.core.cnc.events.io.DurabilityTimeoutCoercedEvent)4 FeaturesNegotiatedEvent (com.couchbase.client.core.cnc.events.io.FeaturesNegotiatedEvent)4 CompositeByteBuf (com.couchbase.client.core.deps.io.netty.buffer.CompositeByteBuf)4 FullHttpRequest (com.couchbase.client.core.deps.io.netty.handler.codec.http.FullHttpRequest)4 BaseEndpoint (com.couchbase.client.core.endpoint.BaseEndpoint)4