Análise de desempenho da mula

Um aplicativo Mule é um corpo colaborativo de um conjunto de serviços. O serviço processa mensagens nos três estágios a seguir:
Estágio de recebimento do conector do conector Estágio
de processamento do componente de serviço Estágio de
distribuição do conector do conector O
ajuste de desempenho do Mule é analisar e melhorar os três acima para cada serviço No estágio, você pode usar um método de ajuste unificado para todos os serviços e ainda definir métodos independentes e não otimizados para cada serviço.
Sobre o pool de threads
para cada pedido para ser uma mula são threading exclusivo (servidor da web semelhante), conector receptor usando pool de threads para receber e processar pedidos de entrada. Observe que o mule pode enviar mensagens de forma síncrona ou assíncrona. Por padrão, a mensagem é assíncrona, ou seja, a mensagem que não requer uma resposta é o método "dispare e esqueça - não se preocupe após o lançamento" (semelhante a um míssil guiado automático), se Para responder, você deve configurar o serviço para ser síncrono. Se a configuração for assíncrona, use o receptor e distribuidor do conector; se for síncrono, use apenas o receptor do conector.
Se você usar o método síncrono, o processamento de uma mensagem usará apenas um fio para percorrer o interior da mula.
Se o método assíncrono for usado, o receptor usa um encadeamento para enviar a mensagem para o componente, em seguida, transfere para o encadeamento do componente e, em seguida, o encadeamento do receptor é retornado ao conjunto de encadeamentos do receptor (o receptor reutilizará este encadeamento) após o
componente processar a mensagem assíncrona , A mensagem é enviada para um encadeamento do distribuidor, o receptor, o componente e o distribuidor possuem seus próprios conjuntos de encadeamentos. Se for síncrono, apenas o receptor possui um pool de threads.

About Threading Profiles thread description descrição de
thread define o comportamento de mule no pool de threads. Você pode defini-lo separadamente para cada conjunto de encadeamentos do receptor, conjunto de encadeamentos do componente e conjunto de encadeamentos do distribuidor. A configuração mais importante é maxThreadsActive: o número máximo de threads ativos.

Pooling Profiles on pool descreve
vários single e componentes, cada componente tem um pooling pool pool PooledJavaComponent, recebendo uma pluralidade de instâncias de componentes para lidar com solicitações simultâneas. O perfil de pool do serviço configura este pool de componentes. A configuração mais importante é maxActive: o número máximo ativo, que especifica o número máximo de instâncias do componente usadas para processar solicitações simultâneas, ou seja, o número máximo de solicitações simultâneas suportadas. Observe que essa configuração deve ser consistente com a configuração maxThreadsActive do conjunto de encadeamentos do receptor. Você pode usar o mule HQ para monitorar o pool de componentes e o número máximo de instâncias de componentes em uso para ajudá-lo a ajustar o número de componentes e threads.

O
número de encadeamentos de computação de encadeamentos a serem calculados deve considerar os seguintes fatores:
solicitações de usuário simultâneas: Normalmente, é o número de solicitações de serviço para processamento de entrada de entrada simultaneamente. No nível do conector, as solicitações de usuários simultâneos são a soma do número de solicitações de usuários simultâneos para todos os serviços que usam esse conector. Normalmente, você deve determinar o número de solicitações de usuário simultâneas da perspectiva das necessidades de negócios.
Tempo de processamento: o tempo médio de processamento desde o início da execução do receptor do conector até o final do processamento da mensagem, o distribuidor do conector enviando uma resposta à saída ou a resposta do receptor de volta ao cliente. Geralmente, você deve decidir esse tempo de processamento com base em testes de unidade.
Tempo de resposta: se um serviço é executado no modo síncrono, o tempo de resposta é o tempo real que o cliente espera pela chegada da resposta. Se for assíncrono, é o tempo total desde a solicitação até a mula até que ela saia da saída. No cenário de pool de threads, nem sempre há threads disponíveis. Se for esse o caso, a solicitação será enviada para a fila de trabalho do pool de threads interno e aguardará o próximo thread disponível (semelhante ao BlockingQueue workQueue de ThreadPoolExecutor). Portanto, o tempo de resposta é calculado da seguinte maneira: Tempo de resposta = média do tempo de espera do pool de threads na fila de trabalho + média do tempo de processamento.
Timeout: se sua empresa precisa especificar um tempo máximo de espera, é isso.
Depois de esclarecer os fatores acima, você pode estimar o maxThreadsActive e maxBufferSize do pool de threads de serviço e do pool de threads do receptor e derivar a fórmula:
Solicitações de usuário simultâneas = maxThreadsActive + maxBufferSize
maxThreadsActive é o número de threads ativos e maxBufferSize é o número de solicitações que podem ser processadas na fila.
As
necessidades de negócios do serviço de computação de segmento de cada serviço determinam o número de processamento simultâneo. Por exemplo, um serviço pode precisar lidar com 50 simultaneidade e outro precisa de 40. Este valor geralmente pode ser definido pelo atributo maxThreadsActive da etiqueta de serviço. Se você precisar definir um tempo limite para o processamento de sincronização, deverá fazer alguns cálculos e estimativas para cada serviço:
1. Execute o caso de teste de sincronização para encontrar o tempo de resposta
2. Deduzir o tempo de resposta do tempo limite permitido pelos requisitos de negócios é sua espera máxima Tempo (tempo máximo de espera = tempo limite-tempo de resposta).
3. Divida o tempo máximo de espera pelo tempo de resposta para encontrar os lotes executados em sequência (lotes =
tempo máximo de espera / tempo de resposta). A solicitação está em Espere na fila até que o primeiro lote seja concluído e, em seguida, os threads do primeiro lote podem ser reciclados para o próximo lote.
4. Divida o número de solicitações de usuário simultâneas pelo lote para obter o número de encadeamentos, que é a configuração maxThreadsActive do serviço (onde maxThreadsActive = solicitações de usuário simultâneas / lotes de processamento). Este é o número total de encadeamentos que podem executar um serviço simultaneamente.
5. maxBufferSize é igual ao número de solicitações de usuário simultâneas menos maxThreadsActive (maxBufferSize = solicitações de usuário simultâneas-maxThreadsActive). Este é o número de solicitações permitidas para aguardar threads disponíveis na fila - deve ser o quinto parâmetro na construção da era ThreadPoolExecutor: BlockingQueue fila de bloqueio workQueue, essa fila de bloqueio é na verdade uma fila de encadeamento aguardando para obter direitos / bloqueios de execução de objeto em um monitor de objeto, que pertence à categoria de coleção simultânea do pacote Java.util.concurrent.

Intercalado com a fila de bloqueio da fila Queue BlockingQueue
Teste detalhado da fila comum:
o código de coleta de código Java
package com.test;

import java.util.LinkedList;
import java.util.Queue;

public class QueueTest {
public static void main (String s []) {
Queue queue = new LinkedList (); / * Substitua por PriorityQueue () e a ordem de saída dos subordinados torna-se:
Quatro, Um, Três, Três —— por caractere A ordem natural de classificação da string (por meio de sua implementação java.util.Comparable ou de acordo com java.util.Comparator passado para o construtor * /
queue.offer ("One");
queue.offer ("Two");
queue.offer ( "Três");
queue.offer ("Quatro");
System.out.println ("O chefe da fila é:" + queue.poll ()); // O chefe da fila é: Um
System.out.println (" O chefe da fila é: ”+ queue.poll ()); // O chefe da fila é: Dois
System.out.println (“ O chefe da fila é: ”+ queue.peek ()); // O chefe da fila é: Três
System.out.println (“O chefe da fila é:” + queue.peek ()); // O chefe da fila é: Três
}
}

java.util.concurrent.ConcurrentLinkedQueue é uma fila thread-safe baseada em nós vinculados. O acesso simultâneo não requer sincronização. Como ele adiciona elementos ao final da fila e os exclui do início, desde que você não precise saber o tamanho da fila, o acesso compartilhado de ConcurrentLinkedQueue à coleção pública pode funcionar bem. A coleta de informações sobre o tamanho da fila pode ser lenta e requer o atravessamento da fila.
O novo pacote java.util.concurrent adiciona a interface BlockingQueue e 5 classes de fila de bloqueio. A fila de bloqueio é essencialmente uma estrutura de dados FIFO com um pouco de distorção. Em vez de adicionar ou remover elementos da fila imediatamente, a execução do thread é bloqueada até que haja espaço ou elementos estejam disponíveis. O Javadoc da interface BlockingQueue fornece o uso básico de filas de bloqueio. A operação put () no produtor será bloqueada quando não houver espaço disponível e a operação take () do consumidor será bloqueada quando não houver nada na fila - parecido com isto Na verdade, a função de BlockingQueue é completar o semáforo de sincronização criado por você no modelo tradicional de produtor-consumidor para você.
As cinco filas são diferentes:
ArrayBlockingQueue: uma fila limitada suportada por uma matriz LinkedBlockingQueue: uma
fila limitada opcional suportada pelo nó de link
PriorityBlockingQueue: uma fila de prioridade ilimitada suportada por um heap de prioridade, que usa Contém a ordem de classificação comparável dos elementos para manter os elementos em uma ordem lógica. Pense nisso como uma possível alternativa ao TreeSet
DelayQueue: Uma fila de agendamento baseada em tempo apoiada por um heap de prioridade. A nova implementação de DelayQueue pode ser a mais interessante (e mais complicada). Os elementos adicionados à fila devem ter uma nova interface Delayed antecipadamente (há apenas um método: long getDelay (java.util.concurrent.TimeUnit unit)). Como não há limite para o tamanho da fila, a adição pode ser retornada imediatamente, mas o elemento não pode ser removido da fila antes que o tempo de atraso tenha passado. Se vários elementos completarem o atraso, o elemento com a falha mais antiga / tempo de falha mais longo será retirado primeiro.
SynchronousQueue: um mecanismo simples de rendezvous que usa a interface BlockingQueue. O mais simples. Não tem capacidade interna. É como um sistema de manipulação manual entre threads. Um produtor que adiciona um elemento à fila espera que outro thread seja consumido. Ou, quando o consumidor aparece, o elemento é passado diretamente entre o consumidor e o produtor, e nunca será adicionado à fila de bloqueio.
Exemplo de BlockingQueue:
código de coleção de código Java
package com.test;

import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;

public class BlockingQueueDemo {
public static void main (String [] args) {
BlockingQueue queue = new ArrayBlockingQueue (5);
Produtor p = novo produtor (fila);
Consumidor c1 = novo consumidor (fila);
Consumidor c2 = novo consumidor (fila);
novo Tópico (p) .start ();
novo Thread (c1, “c1”). start ();
novo Thread (c2, “c2”). start ();
}
}

class Producer implementa Runnable {
private final BlockingQueue queue;
Produtor (BlockingQueue q) {
queue = q;
}

public void run() {  
    try {  
        for (int i = 0; i < 100; i++) {  
            queue.put(produce());  
        }  
    } catch (InterruptedException ex) {  
        ex.printStackTrace();  
    }  
}  

String produce() {  
    String temp = "" + (char) ('A' + (int) (Math.random() * 26));  
    System.out.println("produce " + temp);  
    return temp;  
}  

}

a classe Consumer implementa Runnable {
private final BlockingQueue queue;
Consumidor (BlockingQueue q) {
queue = q;
}

public void run() {  
    try {  
        for (int i = 0; i < 100; i++) {  
            consume(queue.take());  
        }  
    } catch (InterruptedException ex) {  
        ex.printStackTrace();  
    }  
}  

void consume(String x) {  
    System.out.println(Thread.currentThread().getName() + " consume: " + x);  
}  

}

Voltando ao assunto de ajuste de desempenho,
suponha que um serviço deve ser capaz de lidar com 200 solicitações de usuários simultâneos, seu tempo limite é de 10 segundos, o tempo de resposta é de 2 segundos para tornar o tempo máximo de espera de 8 segundos (10--2 = 8), o maior O tempo de espera dividido pelo tempo de resposta resulta em um lote de 4 (8/2 = 4). Finalmente, a solicitação do usuário simultâneo dividida pelo lote para obter o maxThreadsActive do serviço é definido como 50 (200/4 = 50) e, em seguida, a solicitação do usuário simultâneo é subtraída de maxThreadsActive para obter o maxBufferSize definido como 150. Resuma a fórmula para obter os parâmetros de sincronização do tempo limite limitado acima:

• Tempo máximo de espera = tempo limite - tempo de resposta
• Lotes = tempo máximo de espera / tempo de resposta
• maxThreadsActive = solicitações / lotes de
usuários simultâneos • maxBufferSize = solicitações de usuários simultâneas - maxThreadsActive

Acho que você gosta

Origin blog.csdn.net/ke_weiquan/article/details/71644017
Recomendado
Clasificación