Pergunta sobre symfony, background, php, parsing – Como posso fazer a análise de dados em segundo plano com o Symfony2?

4

Eu escrevo uma aplicação web em PHP com o Symfony2. O usuário pode fazer upload de um arquivo CSV com dados salvos no banco de dados. A análise de cada linha do arquivo CSV dura cerca de 0,2 segundo porque faço algumas solicitações à API do Google Maps.

Então, quando você faz o upload de um arquivo CSV com 5000 linhas, o que é um caso realista no meu aplicativo, pode levar 16 minutos para analisar o arquivo inteiro.

Não quero que o usuário espere 16 minutos até que ele possa continuar usando meu aplicativo. Então, minha pergunta é: como posso analisar o arquivo CSV em segundo plano, para que o usuário possa continuar navegando?

Eu iria com o Gearman - fácil de configurar e funciona muito bem com o PHP. halfer
O Symfony2 não possui nenhum recurso de processo / trabalho em segundo plano pronto para uso, então você precisa rolar o seu próprio. hakre

Sua resposta

3   a resposta
7

kernel.terminate ouvinte de eventos e faça sua análise lá. Este evento é disparado depois que a resposta é enviada ao navegador. A implementação da amostra seria,

Declaração de serviço,

//services.yml
csv_parse_listener:
    class: FQCN\Of\CsvParseListener
    tags:
        - { name: kernel.event_listener, event: kernel.terminate, method: onKernelTerminate }

Classe de escuta,

namespace Your\namespace;
use Symfony\Component\HttpKernel\Event\PostResponseEvent;

class CsvParseListener
{
    public function onKernelTerminate(PostResponseEvent $event)
    {
        $request = $event->getRequest();
        if($request->get('_route') !== "Your_route"){
            return;
        }

        $csvFile = $request->files->get('file_field_name');

        //move file using $csvFile->move()
        //read and parse
    }
}
O erro foi feito por mim;) Mas agora oonKernelTerminate método não é chamado, meu aplicativo não executa o código nesse método. Eu olhei no arquivovendor\symfony\src\Symfony\Component\HttpKernel\KernelEvent mas não houve evento 'terminate'. rotespferd
Deixe-noscontinue esta discussão no chat Mun Mun Das
O evento "kernel.terminate" pode ser chamado no Symfony2? Minha aplicação web lança um erro quando eu quero usá-lo. rotespferd
A guia de eventos não mostra o evento terminate. Eu tenho o Symfony Standard Edition 2.0.15 daqui:symfony.com/download. Qual deles você usa. O mesmo ou algo do Github? rotespferd
1

CSV e exec () esse script do script que gerencia o upload. Em sistemas * IX, você pode fazer o comando iniciado por exec () ser executado em segundo plano, acrescentando um caractere &.

Você provavelmente também incluirá um script que permitirá ao usuário verificar o progresso do processamento.

Executar um trabalho de longa duração a partir de um pedido da web parece arriscado para mim. John Carter
4

s e tenha umComando regularmente executado porcron que manipula qualquer trabalho na tabela da fila de trabalhos.

À medida que o processamento prossegue em um trabalho, você pode atualizar a tabela de trabalhos para que um usuário possa voltar e ver o progresso acontecendo (por exemplo, você pode ter uma barra de progresso do ajax) e saber quando o trabalho está concluído.

Dessa forma, você também desativa o upload do processamento e pode controlar quantos trabalhos são processados ​​de uma só vez. A execução de tarefas de longa duração diretamente a partir da entrada do usuário sem um sistema de limitação / enfileiramento é uma ótima maneira de se abrir para um ataque de negação de serviço ...

Parece uma boa ideia. Vou tentar assim. Obrigado :) rotespferd

Perguntas relacionadas