12
votes

Calcul du temps d'exécution de la demande de service Web

J'ai un service Web de savon de travail mis en œuvre avec CXF en Java. Quel serait un bon moyen de calculer l'exécution de la méthode sur un côté serveur?

Qu'est-ce que j'ai fait pour le moment est que j'ai utilisé des intercepteurs. J'ai défini Statique Public Start Long Start dans mon inintercepteur (phase.receive). Et dans mon exterintercepteur (phase.send) je calcule le temps de réponse comme ceci: xxx

est-il une meilleure façon de faire cela? Je lisais sur l'exécution de la méthode du proxy de la méthode, mais je n'ai aucune idée de la façon de faire ça.

Mise à jour de la question:

J'ai googlé un peu plus une trouvaille mon chemin arrondi le Deuxièmement, en utilisant le proxy, c'est-à-dire: xxx

basé sur les commentaires à cette question jusqu'à présent, l'utilisation des intercepteurs est meilleure que d'utiliser le proxy. Je cherche à ralentir le service Web au moins possible (cela le ralentira certainement) et, en même temps, obtenez une mesure de performance précise.


2 commentaires

Je pense que le mécanisme ci-dessus est bon.


Je recommanderais des intercepteurs aussi


4 Réponses :


10
votes

Je ne recommanderais pas votre première approche d'utiliser inintercepteur et Outinterceptor - la raison est qu'il n'ya pas de moyen propre de stocker le temps de démarrage - l'approche que vous avez des jetons pour le stocker dans une variable statique ne fonctionnera pas dans un environnement fileté. .

Votre deuxième approche d'utilisation de l'AOP est très bonne, mais elle ne donnera pas le temps passé dans la pile CXF, il ne fournira que le temps une fois que l'appel vient à votre niveau de service. P>

i Sentez la meilleure approche utilisera un filtre de servlet, vous pouvez le faire: p> xxx pré>

et fournir le mappage sur le même URI où vous avez fourni le mappage pour CXFServillet. p>

Cela devrait être beaucoup plus propre. Si vous voulez quelque chose d'encore plus granulaire, vous pouvez mélanger cette approche avec votre approche AOP pour trouver le temps de réponse global, puis la rompre dans les délais de la méthode de service individuels. P>

<servlet>
    <servlet-name>CXFServlet</servlet-name>
    <servlet-class>org.apache.cxf.transport.servlet.CXFServlet</servlet-class>
</servlet>

<servlet-mapping>
    <servlet-name>CXFServlet</servlet-name>
    <url-pattern>/webservices/*</url-pattern>
</servlet-mapping> 
<filter-mapping>
    <filter-name>ExecTimeFilter</filter-name>
    <url-pattern>/webservices/*</url-pattern>
    <dispatcher>REQUEST</dispatcher>
</filter-mapping>


1 commentaires

+1 pour être très utile en effet. Une note: si vous utilisez la sécurité du ressort, sachez qu'elle est également appliquée via un filtre et que vous devez faire attention à l'ordre des filtres afin de vous assurer que vous avez également choisi la couche de sécurité (ou non. sur ce que vous voulez).



3
votes

Je pense que les intercepteurs peuvent mettre des données arbitraires dans l'objet code> message code>, afin que vous puissiez stocker l'heure de début et la récupérer ultérieurement pour calculer le temps écoulé.

// in your send interceptor
@Override
public void handleMessage(Message message) {
    Long startTime = message.remove("my.timing.start");
    if (startTime != null) {
        long executionTime = System.currentTimeMillis() - startTime;
        System.out.println("execution time was ~" + executionTime + " ms");
    }
}


2 commentaires

J'ai essayé cela, et cela ne fonctionnera pas, des objets stockés à l'aide de messages.UT () dans l'intercepteur de réception ne sont pas disponibles via Message.pan dans Envoyer Interceptor.


Au lieu de stocker des informations sur la demande de démarrage de la demande dans l'objet Message, vous pouvez appuyer sur ThreadLocal, puis la récupérer dans l'intercepteur sortant.



0
votes

Calculer la méthode exécution sur un côté serveur?

Utilisation de Intercepteurs Vous mesurez CXF aussi!
Je veux dire intercepteurs sont utilisés pour PRE / POST Processus un message par rapport à votre logique d'application .
Utilisation de l'intercepteur Vos mesures incluent des parties de la chaîne de débit CXF.
Si c'est ce que vous voulez, alors d'accord.
Mais si vous voulez mesurer votre exécution de méthode, vous devez mettre l'intervalle de synchronisation par rapport à votre méthode.


0 commentaires

5
votes

basé sur Réponse des matts J'ai travaillé après. La clé est que, dans l'intercepteur sortant, vous devez obtenir un message entrant et obtenir un horodatage de départ de celui-ci.

public class IncomingInterceptor extends AbstractPhaseInterceptor<Message> {

    public IncomingInterceptor() {
        super(Phase.RECEIVE);
    }

    @Override
    public void handleMessage(Message msg) throws Fault {
        long startTime = System.currentTimeMillis();
        msg.put("my.timing.start", startTime);
    }
}


public class OutgoingInterceptor extends AbstractPhaseInterceptor<Message> {
    Logger log = LoggerFactory.getLogger(AbstractPhaseInterceptor.class);
    public OutgoingInterceptor() {
        super(Phase.SEND);
    }

    @Override
    public void handleMessage(Message msg) throws Fault {
        Long startTime = (Long)msg.getExchange().getInMessage().remove("my.timing.start");
        if (startTime != null) {
            long executionTime = System.currentTimeMillis() - startTime;
            log.info("execution time was ~" + executionTime + " ms");
        } else {
            log.info("timer not found");
        }
    }       
}


1 commentaires

Je pense que vous devez utiliser msg.getexchange (). Mettez / supprimer?