Search in sources :

Example 1 with RetryingRequest

use of org.apache.openejb.client.event.RetryingRequest in project tomee by apache.

the class Client method processRequest.

protected Response processRequest(final Request req, final Response res, final ServerMetaData server) throws RemoteException {
    if (server == null) {
        throw new IllegalArgumentException("Server instance cannot be null");
    }
    final long start = System.nanoTime();
    final ClusterMetaData cluster = getClusterMetaData(server);
    //Determine which protocol to use for request writes
    final ProtocolMetaData protocolRequest = (null != COMPATIBLE_META_DATA ? COMPATIBLE_META_DATA : PROTOCOL_META_DATA);
    /*----------------------------*/
    /* Get a connection to server */
    /*----------------------------*/
    final Connection conn;
    try {
        conn = ConnectionManager.getConnection(cluster, server, req);
    } catch (final IOException e) {
        throw new RemoteException("Unable to connect", e);
    }
    OutputStream out = null;
    InputStream in = null;
    try {
        /*----------------------------------*/
        try {
            out = conn.getOutputStream();
        } catch (final IOException e) {
            throw newIOException("Cannot open output stream to server: ", e);
        }
        /*----------------------------------*/
        try {
            protocolRequest.writeExternal(out);
            out.flush();
        } catch (final IOException e) {
            throw newIOException("Cannot write the protocol metadata to the server: ", e);
        }
        /*----------------------------------*/
        /* Get output streams */
        /*----------------------------------*/
        final ObjectOutput objectOut;
        try {
            objectOut = new ObjectOutputStream(out);
        } catch (final IOException e) {
            throw newIOException("Cannot open object output stream to server: ", e);
        }
        /*----------------------------------*/
        try {
            server.setMetaData(protocolRequest);
            server.writeExternal(objectOut);
        } catch (final IOException e) {
            throw newIOException("Cannot write the ServerMetaData to the server: ", e);
        }
        /*----------------------------------*/
        try {
            final ClusterRequest clusterRequest = new ClusterRequest(cluster);
            clusterRequest.setMetaData(protocolRequest);
            objectOut.write(clusterRequest.getRequestType().getCode());
            clusterRequest.writeExternal(objectOut);
        } catch (final Throwable e) {
            throw newIOException("Cannot write the ClusterMetaData to the server: ", e);
        }
        /*----------------------------------*/
        try {
            objectOut.write(req.getRequestType().getCode());
        } catch (final IOException e) {
            throw newIOException("Cannot write the request type to the server: ", e);
        }
        /*----------------------------------*/
        try {
            req.setMetaData(protocolRequest);
            req.writeExternal(objectOut);
            objectOut.flush();
            out.flush();
        } catch (final java.io.NotSerializableException e) {
            throw new IllegalArgumentException("Object is not serializable: " + e.getMessage());
        } catch (final IOException e) {
            throw newIOException("Cannot write the request to the server: " + e.getMessage(), e);
        }
        try {
            in = conn.getInputStream();
        } catch (final IOException e) {
            if (AuthenticationException.class.isInstance(e.getCause())) {
                throw e.getCause();
            }
            throw newIOException("Cannot open input stream to server: ", e);
        }
        //Determine the server response protocol for reading
        final ProtocolMetaData protocolResponse = new ProtocolMetaData();
        try {
            protocolResponse.readExternal(in);
        } catch (final EOFException e) {
            throw newIOException("Prematurely reached the end of the stream.  " + protocolResponse.getSpec() + " : " + e.getMessage(), e);
        } catch (final IOException e) {
            throw newIOException("Cannot determine server protocol version: Received " + protocolResponse.getSpec() + " : " + e.getMessage(), e);
        }
        final ObjectInput objectIn;
        try {
            objectIn = new EjbObjectInputStream(in);
        } catch (final IOException e) {
            throw newIOException("Cannot open object input stream to server (" + protocolResponse.getSpec() + ") : " + e.getMessage(), e);
        }
        /*----------------------------------*/
        try {
            final ClusterResponse clusterResponse = new ClusterResponse();
            clusterResponse.setMetaData(protocolResponse);
            clusterResponse.readExternal(objectIn);
            switch(clusterResponse.getResponseCode()) {
                case UPDATE:
                    {
                        setClusterMetaData(server, clusterResponse.getUpdatedMetaData());
                    }
                    break;
                case FAILURE:
                    {
                        throw clusterResponse.getFailure();
                    }
            }
        } catch (final ClassNotFoundException e) {
            throw new RemoteException("Cannot read the cluster response from the server.  The class for an object being returned is not located in this system:", e);
        } catch (final IOException e) {
            throw newIOException("Cannot read the cluster response from the server (" + protocolResponse.getSpec() + ") : " + e.getMessage(), e);
        } catch (final Throwable e) {
            throw new RemoteException("Error reading cluster response from server (" + protocolResponse.getSpec() + ") : " + e.getMessage(), e);
        }
        /*----------------------------------*/
        try {
            res.setMetaData(protocolResponse);
            res.readExternal(objectIn);
        } catch (final ClassNotFoundException e) {
            throw new RemoteException("Cannot read the response from the server.  The class for an object being returned is not located in this system:", e);
        } catch (final IOException e) {
            throw newIOException("Cannot read the response from the server (" + protocolResponse.getSpec() + ") : " + e.getMessage(), e);
        } catch (final Throwable e) {
            throw new RemoteException("Error reading response from server (" + protocolResponse.getSpec() + ") : " + e.getMessage(), e);
        }
        if (retryConditions.size() > 0) {
            if (res instanceof EJBResponse) {
                final EJBResponse ejbResponse = (EJBResponse) res;
                if (ejbResponse.getResult() instanceof ThrowableArtifact) {
                    final ThrowableArtifact artifact = (ThrowableArtifact) ejbResponse.getResult();
                    //noinspection ThrowableResultOfMethodCallIgnored
                    if (retryConditions.contains(artifact.getThrowable().getClass())) {
                        throw new RetryException(res);
                    //                            if (? < maxConditionRetry) {
                    //                                throw new RetryException(res);
                    //                            } else {
                    //                                if (FINER) {
                    //                                    logger.log(Level.FINER, "Giving up on " + artifact.getThrowable().getClass().getName().toString());
                    //                                }
                    //                            }
                    }
                }
            }
        }
        if (FINEST) {
            final long time = System.nanoTime() - start;
            final String message = String.format("Invocation %sns - %s - Request(%s) - Response(%s)", time, conn.getURI(), req, res);
            logger.log(Level.FINEST, message);
        }
    } catch (final RemoteException e) {
        throw e;
    } catch (final IOException e) {
        final URI uri = conn.getURI();
        final Set<URI> failed = getFailed();
        Client.fireEvent(new RequestFailed(uri, req, e));
        if (FINER) {
            logger.log(Level.FINER, "Add Failed " + uri.toString());
        }
        failed.add(uri);
        conn.discard();
        if (e instanceof RetryException || getRetry()) {
            try {
                Client.fireEvent(new RetryingRequest(req, server));
                processRequest(req, res, server);
            } catch (final RemoteFailoverException re) {
                throw re;
            } catch (final RemoteException re) {
                if (e instanceof RetryException) {
                    return ((RetryException) e).getResponse();
                }
                throw new RemoteFailoverException("Cannot complete request.  Retry attempted on " + failed.size() + " servers", e);
            }
        } else {
            throw new RemoteException("Cannot read the response from the server (" + protocolRequest.getSpec() + ") : " + e.getMessage(), e);
        }
    } catch (final Throwable error) {
        throw new RemoteException("Error while communicating with server: ", error);
    } finally {
        if (null != out) {
            try {
                out.close();
            } catch (final Throwable e) {
            //Ignore
            }
        }
        if (null != in) {
            try {
                in.close();
            } catch (final Throwable e) {
            //Ignore
            }
        }
        if (null != conn) {
            try {
                conn.close();
            } catch (final Throwable t) {
                logger.log(Level.WARNING, "Error closing connection with server: " + t.getMessage(), t);
            }
        }
    }
    return res;
}
Also used : HashSet(java.util.HashSet) Set(java.util.Set) AuthenticationException(javax.naming.AuthenticationException) ObjectOutputStream(java.io.ObjectOutputStream) OutputStream(java.io.OutputStream) RequestFailed(org.apache.openejb.client.event.RequestFailed) ObjectOutputStream(java.io.ObjectOutputStream) URI(java.net.URI) RetryingRequest(org.apache.openejb.client.event.RetryingRequest) EOFException(java.io.EOFException) ObjectOutput(java.io.ObjectOutput) InputStream(java.io.InputStream) IOException(java.io.IOException) Exceptions.newIOException(org.apache.openejb.client.Exceptions.newIOException) ObjectInput(java.io.ObjectInput) RemoteException(java.rmi.RemoteException)

Aggregations

EOFException (java.io.EOFException)1 IOException (java.io.IOException)1 InputStream (java.io.InputStream)1 ObjectInput (java.io.ObjectInput)1 ObjectOutput (java.io.ObjectOutput)1 ObjectOutputStream (java.io.ObjectOutputStream)1 OutputStream (java.io.OutputStream)1 URI (java.net.URI)1 RemoteException (java.rmi.RemoteException)1 HashSet (java.util.HashSet)1 Set (java.util.Set)1 AuthenticationException (javax.naming.AuthenticationException)1 Exceptions.newIOException (org.apache.openejb.client.Exceptions.newIOException)1 RequestFailed (org.apache.openejb.client.event.RequestFailed)1 RetryingRequest (org.apache.openejb.client.event.RetryingRequest)1