Commit ce1ecf146edfe5ae5c63f082b1e5cdc35c287075

Authored by daniel@ruoso.com
1 parent 252b3fe5
Exists in master

ETL agora faz mais operacoes.

git-svn-id: http://svn.softwarepublico.gov.br/svn/sistemadeatendimento/sistema/trunk@8 63db2ce5-8a6c-0410-abb9-a418dd412890
Fila-ETL/fila_etl.yaml
... ... @@ -16,7 +16,7 @@ Model::DBSERVI:
16 16 schema_class: 'Fila::Servico::DB'
17 17 connect_info:
18 18 - 'dbi:Pg:host=localhost;database=fila'
19   - - ruoso
  19 + - fila
20 20 - teste
21 21 Model::Federado:
22 22 federacao:
... ...
Fila-ETL/lib/Fila/ETL/Controller/Atendimento.pm
... ... @@ -245,153 +245,164 @@ sub estados :Chained('atendimento') :PathPart :Args(0) {
245 245 my $local = $c->model('Federado')->target($c, $id, 'Local')->find
246 246 ({ id_local => $id });
247 247  
248   - my $sql = q#;
  248 + my $sql_times = q{
249 249 SELECT
250   -
251   - date_trunc('minute',times.vt_fac) AS datahora,
252   - COUNT(es_espe_ini.*) AS espe_ini,
253   - COUNT(es_espe_fim.*) AS espe_fim,
254   - COUNT(es_cham_ini.*) AS cham_ini,
255   - COUNT(es_cham_fim.*) AS cham_fim,
256   - COUNT(es_aten_ini.*) AS aten_ini,
257   - COUNT(es_aten_fim.*) AS aten_fim,
258   - COUNT(es_no_show.*) AS no_show,
259   - ct_espe_ini.id_categoria AS ct_espe_ini_id_categoria,
260   - ct_espe_ini.nome AS ct_espe_ini_nome,
261   - ct_espe_ini.codigo AS ct_espe_ini_codigo,
262   - ct_espe_fim.id_categoria AS ct_espe_fim_id_categoria,
263   - ct_espe_fim.nome AS ct_espe_fim_nome,
264   - ct_espe_fim.codigo AS ct_espe_fim_codigo,
265   - ct_cham_ini.id_categoria AS ct_cham_ini_id_categoria,
266   - ct_cham_ini.nome AS ct_cham_ini_nome,
267   - ct_cham_ini.codigo AS ct_cham_ini_codigo,
268   - ct_cham_fim.id_categoria AS ct_cham_fim_id_categoria,
269   - ct_cham_fim.nome AS ct_cham_fim_nome,
270   - ct_cham_fim.codigo AS ct_cham_fim_codigo,
271   - ct_aten_ini.id_categoria AS ct_aten_ini_id_categoria,
272   - ct_aten_ini.nome AS ct_aten_ini_nome,
273   - ct_aten_ini.codigo AS ct_aten_ini_codigo,
274   - ct_aten_fim.id_categoria AS ct_aten_fim_id_categoria,
275   - ct_aten_fim.nome AS ct_aten_fim_nome,
276   - ct_aten_fim.codigo AS ct_aten_fim_codigo,
277   - ct_no_show.id_categoria AS ct_no_show_id_categoria,
278   - ct_no_show.nome AS ct_no_show_nome,
279   - ct_no_show.codigo AS ct_no_show_codigo
280   -
  250 + DISTINCT DATE_TRUNC('minute', estado_atendimento.vt_ini) + '59.9999999 seconds' AS vt_fac
281 251 FROM
  252 + atendimento LEFT JOIN
  253 + estado_atendimento USING (id_atendimento)
  254 +WHERE
  255 + atendimento.id_local = ? AND
  256 + atendimento.vt_ini >= ? AND
  257 + atendimento.vt_ini < ? AND
  258 + estado_atendimento.vt_ini >= ? AND
  259 + estado_atendimento.vt_ini < ?
  260 +};
  261 +
  262 + my $sql_estados_categorias = q{
  263 +SELECT
  264 + COUNT(tipo_estado_atendimento.*) as quantidade,
  265 + categoria.nome, categoria.codigo, categoria.id_categoria,
  266 + tipo_estado_atendimento.nome as nome_estado
282 267  
283   - ( SELECT vt_ini AS vt_fac FROM estado_atendimento estados_ini
284   - WHERE (
285   - ( estados_ini.vt_ini >= ? ) AND
286   - ( estados_ini.vt_ini < ? ) )
287   - UNION
288   - SELECT vt_fim AS vt_fac FROM estado_atendimento estados_fim
289   - WHERE (
290   - ( estados_fim.vt_fim >= ? ) AND
291   - ( estados_fim.vt_fim < ? ) )
292   - ) AS times
293   -
294   - LEFT JOIN estado_atendimento AS es_espe_ini ON (times.vt_fac = es_espe_ini.vt_ini
295   - AND es_espe_ini.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='espera'))
296   -
297   - LEFT JOIN atendimento AS at_espe_ini ON
298   - ( es_espe_ini.id_atendimento = at_espe_ini.id_atendimento AND
299   - at_espe_ini.id_local = ? )
300   -
301   - LEFT JOIN categoria_atendimento AS cs_espe_ini ON
302   - ( at_espe_ini.id_atendimento = cs_espe_ini.id_atendimento)
303   -
304   - LEFT JOIN categoria AS ct_espe_ini ON
305   - ( cs_espe_ini.id_categoria = ct_espe_ini.id_categoria)
306   -
307   - LEFT JOIN estado_atendimento AS es_espe_fim ON (times.vt_fac = es_espe_fim.vt_fim
308   - AND es_espe_fim.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='espera'))
309   -
310   - LEFT JOIN atendimento AS at_espe_fim ON
311   - ( es_espe_fim.id_atendimento = at_espe_fim.id_atendimento AND
312   - at_espe_fim.id_local = ? )
313   -
314   - LEFT JOIN categoria_atendimento AS cs_espe_fim ON
315   - ( at_espe_fim.id_atendimento = cs_espe_fim.id_atendimento)
316   -
317   - LEFT JOIN categoria AS ct_espe_fim ON
318   - ( cs_espe_fim.id_categoria = ct_espe_fim.id_categoria)
319   -
320   - LEFT JOIN estado_atendimento AS es_cham_ini ON (times.vt_fac = es_cham_ini.vt_ini
321   - AND es_cham_ini.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='chamando'))
322   -
323   - LEFT JOIN atendimento AS at_cham_ini ON
324   - ( es_cham_ini.id_atendimento = at_cham_ini.id_atendimento AND
325   - at_cham_ini.id_local = ? )
326   -
327   - LEFT JOIN categoria_atendimento AS cs_cham_ini ON
328   - ( at_cham_ini.id_atendimento = cs_cham_ini.id_atendimento)
  268 +FROM
  269 + categoria LEFT JOIN
  270 + categoria_atendimento
  271 + ON (categoria.id_categoria=categoria_atendimento.id_categoria AND
  272 + categoria_atendimento.vt_ini <= ? AND
  273 + categoria_atendimento.vt_fim > ?) LEFT JOIN
  274 + atendimento
  275 + ON (atendimento.id_atendimento=categoria_atendimento.id_atendimento AND
  276 + atendimento.id_local = ? ) LEFT JOIN
  277 + estado_atendimento
  278 + ON (atendimento.id_atendimento=estado_atendimento.id_atendimento AND
  279 + estado_atendimento.vt_ini <= ? AND
  280 + estado_atendimento.vt_fim > ?) LEFT JOIN
  281 + tipo_estado_atendimento USING (id_estado)
  282 +
  283 +WHERE tipo_estado_atendimento.nome IS NOT NULL
329 284  
330   - LEFT JOIN categoria AS ct_cham_ini ON
331   - ( cs_cham_ini.id_categoria = ct_cham_ini.id_categoria)
  285 +GROUP BY
  286 + categoria.nome, categoria.codigo, categoria.id_categoria,
  287 + tipo_estado_atendimento.nome
332 288  
333   - LEFT JOIN estado_atendimento AS es_cham_fim ON (times.vt_fac = es_cham_fim.vt_fim
334   - AND es_cham_fim.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='chamando'))
335 289  
336   - LEFT JOIN atendimento AS at_cham_fim ON
337   - ( es_cham_fim.id_atendimento = at_cham_fim.id_atendimento AND
338   - at_cham_fim.id_local = ? )
  290 +};
339 291  
340   - LEFT JOIN categoria_atendimento AS cs_cham_fim ON
341   - ( at_cham_fim.id_atendimento = cs_cham_fim.id_atendimento)
  292 + my $storage = $c->model('Federado')->storage($c, $id);
  293 + $storage->ensure_connected;
  294 + my $dbi = $storage->dbh;
342 295  
343   - LEFT JOIN categoria AS ct_cham_fim ON
344   - ( cs_cham_fim.id_categoria = ct_cham_fim.id_categoria)
  296 + my $sth = $dbi->prepare($sql_times);
  297 + $sth->execute( $id,
  298 + $c->stash->{last_vt_base}, $c->stash->{vt_base},
  299 + $c->stash->{last_vt_base}, $c->stash->{vt_base},
  300 + );
345 301  
346   - LEFT JOIN estado_atendimento AS es_aten_ini ON (times.vt_fac = es_aten_ini.vt_ini
347   - AND es_aten_ini.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='atendimento'))
  302 + my $sth_inner = $dbi->prepare($sql_estados_categorias);
348 303  
349   - LEFT JOIN atendimento AS at_aten_ini ON
350   - ( es_aten_ini.id_atendimento = at_aten_ini.id_atendimento AND
351   - at_aten_ini.id_local = ? )
  304 + my $dlocal = $c->model('DB::DLocal')->get_dimension($local);
  305 + my $cat_cache = {};
  306 +
  307 + while (my ($datahora) = $sth->fetchrow_array) {
  308 + my $datahora_dt = DateTime::Format::Pg->parse_datetime($datahora);
  309 + my $data = $c->model('DB::DData')->get_dimension($datahora_dt);
  310 + my $horario = $c->model('DB::DHorario')->get_dimension($datahora_dt);
  311 + my $counters_cat = {};
  312 +
  313 + $sth_inner->execute($datahora,$datahora,$id,$datahora,$datahora);
  314 + while (my $item = $sth_inner->fetchrow_hashref) {
  315 + my $id_categoria = $item->{id_categoria};
  316 + $counters_cat->{$id_categoria}{$item->{nome_estado}} = $item->{quantidade};
  317 + $counters_cat->{$id_categoria}{categoria}{codigo} = $item->{codigo};
  318 + $counters_cat->{$id_categoria}{categoria}{codigo} = $item->{nome};
  319 + }
  320 +
  321 + foreach my $id_categoria (keys %{$counters_cat}) {
  322 + unless (exists $cat_cache->{$id_categoria}) {
  323 + $cat_cache->{$id_categoria} = $c->model('DB::DCategoria')->get_dimension
  324 + (Fila::Servico::DB::Categoria->new
  325 + ({ map { $_ => $counters_cat->{$id_categoria}{categoria}{$_}
  326 + } qw(id_categoria nome codigo) }));
  327 + }
  328 + my $categoria = $cat_cache->{$id_categoria};
  329 +
  330 + $c->model('DB::FQuantidadeEstados')->create
  331 + ({ id_local => $dlocal,
  332 + id_categoria => $categoria,
  333 + data => $data,
  334 + horario => $horario,
  335 +
  336 + ( map { 'quantidade_'.$_ => ($counters_cat->{$id_categoria}{$_} || 0) }
  337 + 'espera',
  338 + 'chamando',
  339 + 'atendimento',
  340 + 'avaliacao'
  341 + )
  342 + });
  343 + }
352 344  
353   - LEFT JOIN categoria_atendimento AS cs_aten_ini ON
354   - ( at_aten_ini.id_atendimento = cs_aten_ini.id_atendimento)
  345 + }
355 346  
356   - LEFT JOIN categoria AS ct_aten_ini ON
357   - ( cs_aten_ini.id_categoria = ct_aten_ini.id_categoria)
  347 + $c->model('DB::ActivityLog')->create
  348 + ({ activity_type => '/atendimento/estados',
  349 + id_local => $id,
  350 + vt_base => $c->stash->{vt_base},
  351 + vt_ini => $c->stash->{now} });
358 352  
359   - LEFT JOIN estado_atendimento AS es_aten_fim ON (times.vt_fac = es_aten_fim.vt_fim
360   - AND es_aten_fim.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='atendimento'))
  353 + });
361 354  
362   - LEFT JOIN atendimento AS at_aten_fim ON
363   - ( es_aten_fim.id_atendimento = at_aten_fim.id_atendimento AND
364   - at_aten_fim.id_local = ? )
  355 +}
365 356  
366   - LEFT JOIN categoria_atendimento AS cs_aten_fim ON
367   - ( at_aten_fim.id_atendimento = cs_aten_fim.id_atendimento)
  357 +sub no_show :Chained('atendimento') :PathPart :Args(0) {
  358 + my ($self, $c) = @_;
368 359  
369   - LEFT JOIN categoria AS ct_aten_fim ON
370   - ( cs_aten_fim.id_categoria = ct_aten_fim.id_categoria)
  360 + $c->model('Federado')->doeach
  361 + ($c, sub {
  362 + my $id = shift;
371 363  
372   - LEFT JOIN estado_atendimento AS es_no_show ON (times.vt_fac = es_no_show.vt_ini
373   - AND es_no_show.id_estado=(SELECT id_estado FROM tipo_estado_atendimento WHERE nome='no_show'))
  364 + my $result = $c->model('DB::ActivityLog')->search
  365 + ({ activity_type => '/atendimento/no_show',
  366 + id_local => $id },
  367 + { order_by => 'vt_base DESC' });
374 368  
375   - LEFT JOIN atendimento AS at_no_show ON
376   - ( es_no_show.id_atendimento = at_no_show.id_atendimento AND
377   - at_no_show.id_local = ? )
  369 + if (my $last = $result->first) {
  370 + $c->stash->{last_vt_base} = $last->vt_base;
  371 + } else {
  372 + $c->stash->{last_vt_base} = '-Infinity';
  373 + }
378 374  
379   - LEFT JOIN categoria_atendimento AS cs_no_show ON
380   - ( at_no_show.id_atendimento = cs_no_show.id_atendimento)
  375 + my $local = $c->model('Federado')->target($c, $id, 'Local')->find
  376 + ({ id_local => $id });
381 377  
382   - LEFT JOIN categoria AS ct_no_show ON
383   - ( cs_no_show.id_categoria = ct_no_show.id_categoria)
  378 + my $sql = q#
  379 +SELECT
  380 + DATE_TRUNC('minute', estado_atendimento.vt_ini) AS datahora,
  381 + COUNT(estado_atendimento.*) AS quantidade,
  382 + categoria.nome, categoria.codigo, categoria.id_categoria
384 383  
385   -GROUP BY date_trunc('minute',times.vt_fac),
386   - ct_espe_ini.id_categoria, ct_espe_ini.nome, ct_espe_ini.codigo,
387   - ct_espe_fim.id_categoria, ct_espe_fim.nome, ct_espe_fim.codigo,
388   - ct_cham_ini.id_categoria, ct_cham_ini.nome, ct_cham_ini.codigo,
389   - ct_cham_fim.id_categoria, ct_cham_fim.nome, ct_cham_fim.codigo,
390   - ct_aten_ini.id_categoria, ct_aten_ini.nome, ct_aten_ini.codigo,
391   - ct_aten_fim.id_categoria, ct_aten_fim.nome, ct_aten_fim.codigo,
392   - ct_no_show.id_categoria, ct_no_show.nome, ct_no_show.codigo
  384 +FROM
  385 + tipo_estado_atendimento INNER JOIN
  386 + estado_atendimento
  387 + ON (tipo_estado_atendimento.id_estado=estado_atendimento.id_estado AND
  388 + estado_atendimento.vt_ini > ? AND
  389 + estado_atendimento.vt_ini <= ?) INNER JOIN
  390 + atendimento
  391 + ON (estado_atendimento.id_atendimento=atendimento.id_atendimento AND
  392 + atendimento.id_local = ? AND
  393 + atendimento.vt_ini > ? AND
  394 + atendimento.vt_ini <= ?) INNER JOIN
  395 + categoria_atendimento
  396 + ON (categoria_atendimento.id_atendimento=atendimento.id_atendimento AND
  397 + categoria_atendimento.vt_ini <= estado_atendimento.vt_ini AND
  398 + categoria_atendimento.vt_fim > estado_atendimento.vt_ini) INNER JOIN
  399 + categoria USING (id_categoria)
  400 +
  401 +WHERE tipo_estado_atendimento.nome='no_show'
393 402  
394   -ORDER BY datahora
  403 +GROUP BY
  404 + DATE_TRUNC('minute', estado_atendimento.vt_ini),
  405 + categoria.nome, categoria.codigo, categoria.id_categoria
395 406  
396 407 #;
397 408  
... ... @@ -401,157 +412,47 @@ ORDER BY datahora
401 412  
402 413 my $sth = $dbi->prepare($sql);
403 414 $sth->execute( $c->stash->{last_vt_base}, $c->stash->{vt_base},
404   - $c->stash->{last_vt_base}, $c->stash->{vt_base},
405   - map { $id } 1..7 );
  415 + $id,
  416 + $c->stash->{last_vt_base}, $c->stash->{vt_base},
  417 + );
406 418  
407 419 my $dlocal = $c->model('DB::DLocal')->get_dimension($local);
408   - my $last_datahora;
409   - my $counters_cat = {};
410   - my $last_data;
  420 + my $cat_cache = {};
411 421  
412 422 while (my $item = $sth->fetchrow_hashref) {
413   -
414   - if ($last_datahora && $item->{datahora} ne $last_datahora) {
415   -
416   - # inserir registros para cada categoria
417   - my $data = $c->model('DB::DData')->get_dimension
418   - ( DateTime::Format::Pg->parse_datetime($last_datahora) );
419   - my $horario = $c->model('DB::DHorario')->get_dimension
420   - ( DateTime::Format::Pg->parse_datetime($last_datahora) );
421   -
422   - foreach my $id_categoria (keys %{$counters_cat}) {
423   -
424   - my $categoria = $c->model('DB::DCategoria')->get_dimension
425   - (Fila::Servico::DB::Categoria->new
426   - ({ map { $_ => $counters_cat->{$id_categoria}{categoria}{$_}
427   - } qw(id_categoria nome codigo) }));
428   -
429   -
430   - $c->model('DB::FQuantidadeEstados')->create
431   - ({ id_local => $dlocal,
432   - id_categoria => $categoria,
433   - data => $data,
434   - horario => $horario,
435   -
436   - ( map { 'quantidade_'.$_ => ($counters_cat->{$id_categoria}{$_} || 0) }
437   - 'espera',
438   - 'chamando',
439   - 'atendimento',
440   - 'no_show'
441   - )
442   - });
443   -
444   - $counters_cat->{$id_categoria}{no_show} = 0;
445   - }
446   -
447   - $last_datahora = $item->{datahora};
448   - if ($last_data ne $data) {
449   - $last_datahora = undef;
450   - $last_data = undef;
451   - }
452   -
453   - }
454   - if (not $last_datahora ) {
455   - # vamos obter os contadores iniciais para aquela datahora
456   -
457   - my $sql_quant = q#
458   -
459   -SELECT
460   - cat_est.estado,
461   - cat_est.id_categoria,
462   - cat_est.codigo,
463   - cat_est.nome,
464   - COUNT(categoria_atendimento.*) as total
465   -FROM
466   - ( SELECT tipo_estado_atendimento.id_estado,
467   - tipo_estado_atendimento.nome AS estado, categoria.id_categoria,
468   - categoria.codigo, categoria.nome FROM tipo_estado_atendimento,
469   - categoria
470   - WHERE
471   - tipo_estado_atendimento.nome IN ('espera','chamando','atendimento')
472   - ) AS cat_est
473   - INNER JOIN estado_atendimento
474   - ON (estado_atendimento.id_estado = cat_est.id_estado AND
475   - ? BETWEEN estado_atendimento.vt_ini AND estado_atendimento.vt_fim)
476   - INNER JOIN atendimento
477   - ON (estado_atendimento.id_atendimento = atendimento.id_atendimento AND
478   - ? BETWEEN atendimento.vt_ini AND atendimento.vt_fim)
479   - INNER JOIN categoria_atendimento
480   - ON (atendimento.id_atendimento = categoria_atendimento.id_atendimento AND
481   - categoria_atendimento.id_categoria = cat_est.id_categoria)
482   -GROUP BY
483   - cat_est.estado,
484   - cat_est.id_categoria,
485   - cat_est.codigo,
486   - cat_est.nome
487   -
488   -#;
489   -
490   - my $sth = $dbi->prepare($sql_quant);
491   - $sth->execute($item->{datahora}, $item->{datahora});
492   -
493   - $counters_cat = {};
494   -
495   - while (my $cat_est = $sth->fetchrow_hashref) {
496   - $counters_cat->{$cat_est->{id_categoria}}{categoria} = $cat_est;
497   - $counters_cat->{$cat_est->{id_categoria}}{$cat_est->{estado}} = $cat_est->{total};
498   - $counters_cat->{$cat_est->{id_categoria}}{no_show} = 0;
499   - }
500   -
501   - $last_datahora = $item->{datahora};
502   - $last_data = $last_datahora;
503   - $last_data =~ s/\s.+$//;
504   - }
505   -
506   - # vamos calcular os contadores
507   - if ($item->{espe_ini}) {
508   - $counters_cat->{$item->{ct_espe_ini_id_categoria}}{espera} += $item->{espe_ini};
509   - $counters_cat->{$item->{ct_espe_ini_id_categoria}}{categoria}{codigo} = $item->{ct_espe_ini_codigo};
510   - $counters_cat->{$item->{ct_espe_ini_id_categoria}}{categoria}{nome} = $item->{ct_espe_ini_nome};
511   - }
512   - if ($item->{espe_fim}) {
513   - $counters_cat->{$item->{ct_espe_fim_id_categoria}}{espera} -= $item->{espe_fim};
514   - $counters_cat->{$item->{ct_espe_fim_id_categoria}}{categoria}{codigo} = $item->{ct_espe_fim_codigo};
515   - $counters_cat->{$item->{ct_espe_fim_id_categoria}}{categoria}{nome} = $item->{ct_espe_fim_nome};
516   - }
517   - if ($item->{cham_ini}) {
518   - $counters_cat->{$item->{ct_cham_ini_id_categoria}}{chamando} += $item->{cham_ini};
519   - $counters_cat->{$item->{ct_cham_ini_id_categoria}}{categoria}{codigo} = $item->{ct_cham_ini_codigo};
520   - $counters_cat->{$item->{ct_cham_ini_id_categoria}}{categoria}{nome} = $item->{ct_cham_ini_nome};
521   - }
522   - if ($item->{cham_fim}) {
523   - $counters_cat->{$item->{ct_cham_fim_id_categoria}}{chamando} -= $item->{cham_fim};
524   - $counters_cat->{$item->{ct_cham_fim_id_categoria}}{categoria}{codigo} = $item->{ct_cham_fim_codigo};
525   - $counters_cat->{$item->{ct_cham_fim_id_categoria}}{categoria}{nome} = $item->{ct_cham_fim_nome};
526   - }
527   - if ($item->{aten_ini}) {
528   - $counters_cat->{$item->{ct_aten_ini_id_categoria}}{atendimento} += $item->{aten_ini};
529   - $counters_cat->{$item->{ct_aten_ini_id_categoria}}{categoria}{codigo} = $item->{ct_aten_ini_codigo};
530   - $counters_cat->{$item->{ct_aten_ini_id_categoria}}{categoria}{nome} = $item->{ct_aten_ini_nome};
531   - }
532   - if ($item->{aten_fim}) {
533   - $counters_cat->{$item->{ct_aten_fim_id_categoria}}{atendimento} -= $item->{aten_fim};
534   - $counters_cat->{$item->{ct_aten_fim_id_categoria}}{categoria}{codigo} = $item->{ct_aten_fim_codigo};
535   - $counters_cat->{$item->{ct_aten_fim_id_categoria}}{categoria}{nome} = $item->{ct_aten_fim_nome};
536   - }
537   - if ($item->{no_show}) {
538   - $counters_cat->{$item->{ct_no_show_id_categoria}}{no_show} += $item->{no_show};
539   - $counters_cat->{$item->{ct_no_show_id_categoria}}{categoria}{codigo} = $item->{ct_no_show_codigo};
540   - $counters_cat->{$item->{ct_no_show_id_categoria}}{categoria}{nome} = $item->{ct_no_show_nome};
541   - }
542   -
  423 + my $datahora = $item->{datahora};
  424 + my $datahora_dt = DateTime::Format::Pg->parse_datetime($datahora);
  425 + my $data = $c->model('DB::DData')->get_dimension($datahora_dt);
  426 + my $horario = $c->model('DB::DHorario')->get_dimension($datahora_dt);
  427 + my $id_categoria = $item->{id_categoria};
  428 +
  429 + unless (exists $cat_cache->{$id_categoria}) {
  430 + $cat_cache->{$id_categoria} = $c->model('DB::DCategoria')->get_dimension
  431 + (Fila::Servico::DB::Categoria->new
  432 + ({ map { $_ => $item->{$_}
  433 + } qw(id_categoria nome codigo) }));
  434 + }
  435 + my $categoria = $cat_cache->{$id_categoria};
  436 +
  437 + $c->model('DB::FQuantidadeEstados')->create
  438 + ({ id_local => $dlocal,
  439 + id_categoria => $categoria,
  440 + data => $data,
  441 + horario => $horario,
  442 + quantidade => $item->{quantidade}
  443 + });
543 444 }
544 445  
  446 +
545 447 $c->model('DB::ActivityLog')->create
546   - ({ activity_type => '/atendimento/estados',
  448 + ({ activity_type => '/atendimento/no_show',
547 449 id_local => $id,
548 450 vt_base => $c->stash->{vt_base},
549 451 vt_ini => $c->stash->{now} });
550 452  
551 453 });
552 454  
553   -
554   -
555 455 }
556 456  
  457 +
557 458 1;
... ...
Fila-ETL/lib/Fila/ETL/Controller/Guiches.pm 0 → 100644
... ... @@ -0,0 +1,147 @@
  1 +package Fila::ETL::Controller::Guiches;
  2 +# Copyright 2008, 2009 - Oktiva Comércio e Serviços de Informática Ltda.
  3 +#
  4 +# Este arquivo é parte do programa FILA - Sistema de Atendimento
  5 +#
  6 +# O FILA é um software livre; você pode redistribui-lo e/ou modifica-lo
  7 +# dentro dos termos da Licença Pública Geral GNU como publicada pela
  8 +# Fundação do Software Livre (FSF); na versão 2 da Licença.
  9 +#
  10 +# Este programa é distribuido na esperança que possa ser util, mas SEM
  11 +# NENHUMA GARANTIA; sem uma garantia implicita de ADEQUAÇÂO a qualquer
  12 +# MERCADO ou APLICAÇÃO EM PARTICULAR. Veja a Licença Pública Geral GNU
  13 +# para maiores detalhes.
  14 +#
  15 +# Você deve ter recebido uma cópia da Licença Pública Geral GNU, sob o
  16 +# título "LICENCA.txt", junto com este programa, se não, escreva para a
  17 +# Fundação do Software Livre(FSF) Inc., 51 Franklin St, Fifth Floor,
  18 +
  19 +use strict;
  20 +use warnings;
  21 +use List::Util qw(sum);
  22 +use base qw(Catalyst::Controller);
  23 +
  24 +sub guiches :Chained('/base') :PathPart :CaptureArgs(0) {
  25 + my ($self, $c) = @_;
  26 + $c->stash->{vt_base} = $c->stash->{now};
  27 +}
  28 +
  29 +sub estados :Chained('guiches') :PathPart :Args(0) {
  30 + my ($self, $c) = @_;
  31 +
  32 + $c->model('Federado')->doeach
  33 + ($c, sub {
  34 + my $id = shift;
  35 +
  36 + my $result = $c->model('DB::ActivityLog')->search
  37 + ({ activity_type => '/guiches/estados',
  38 + id_local => $id },
  39 + { order_by => 'vt_base DESC' });
  40 +
  41 + if (my $last = $result->first) {
  42 + $c->stash->{last_vt_base} = $last->vt_base;
  43 + } else {
  44 + $c->stash->{last_vt_base} = '-Infinity';
  45 + }
  46 +
  47 + my $local = $c->model('Federado')->target($c, $id, 'Local')->find
  48 + ({ id_local => $id });
  49 +
  50 + my $sql_times = q{
  51 +SELECT
  52 + DISTINCT DATE_TRUNC('minute', estado_guiche.vt_ini) + '59.9999999 seconds' AS vt_fac
  53 +FROM
  54 + guiche LEFT JOIN
  55 + estado_guiche USING (id_guiche)
  56 +WHERE
  57 + guiche.id_local = ? AND
  58 + guiche.vt_ini >= ? AND
  59 + guiche.vt_ini < ? AND
  60 + estado_guiche.vt_ini >= ? AND
  61 + estado_guiche.vt_ini < ?
  62 +};
  63 +
  64 + my $sql_estados = q{
  65 +SELECT
  66 + COUNT(tipo_estado_guiche.*) as quantidade,
  67 + tipo_estado_guiche.nome as nome_estado
  68 +
  69 +FROM
  70 + guiche LEFT JOIN
  71 + estado_guiche
  72 + ON (guiche.id_guiche=estado_guiche.id_guiche AND
  73 + estado_guiche.vt_ini <= ? AND
  74 + estado_guiche.vt_fim > ?) LEFT JOIN
  75 + tipo_estado_guiche USING (id_estado)
  76 +
  77 +WHERE tipo_estado_guiche.nome IS NOT NULL
  78 + AND guiche.id_local=?
  79 +
  80 +GROUP BY
  81 + tipo_estado_guiche.nome
  82 +
  83 +
  84 +};
  85 +
  86 + my $storage = $c->model('Federado')->storage($c, $id);
  87 + $storage->ensure_connected;
  88 + my $dbi = $storage->dbh;
  89 +
  90 + my $sth = $dbi->prepare($sql_times);
  91 + $sth->execute( $id,
  92 + $c->stash->{last_vt_base}, $c->stash->{vt_base},
  93 + $c->stash->{last_vt_base}, $c->stash->{vt_base},
  94 + );
  95 +
  96 + my $sth_inner = $dbi->prepare($sql_estados);
  97 +
  98 + my $dlocal = $c->model('DB::DLocal')->get_dimension($local);
  99 + my $func_cache = {};
  100 + my $guic_cache = {};
  101 +
  102 + while (my ($datahora) = $sth->fetchrow_array) {
  103 + my $datahora_dt = DateTime::Format::Pg->parse_datetime($datahora);
  104 + my $data = $c->model('DB::DData')->get_dimension($datahora_dt);
  105 + my $horario = $c->model('DB::DHorario')->get_dimension($datahora_dt);
  106 + my $counters = {};
  107 +
  108 + $sth_inner->execute($datahora,$datahora,$id);
  109 + while (my $item = $sth_inner->fetchrow_hashref) {
  110 + $counters->{$item->{nome_estado}} = $item->{quantidade};
  111 + }
  112 +
  113 + $c->model('DB::FEstadosGuiches')->create
  114 + ({ id_local => $dlocal,
  115 + data => $data,
  116 + horario => $horario,
  117 + quantidade_publico =>
  118 + sum( map { $counters->{$_} || 0 }
  119 + 'disponivel',
  120 + 'chamando',
  121 + 'atendimento',
  122 + 'avaliacao',
  123 + 'concluido'
  124 + ),
  125 + ( map { 'quantidade_'.$_ => ($counters->{$_} || 0) }
  126 + 'fechado',
  127 + 'pausa',
  128 + 'interno',
  129 + 'disponivel',
  130 + 'chamando',
  131 + 'atendimento',
  132 + 'avaliacao',
  133 + 'concluido'
  134 + )
  135 + });
  136 + }
  137 +
  138 + $c->model('DB::ActivityLog')->create
  139 + ({ activity_type => '/guiches/estados',
  140 + id_local => $id,
  141 + vt_base => $c->stash->{vt_base},
  142 + vt_ini => $c->stash->{now} });
  143 +
  144 + });
  145 +
  146 +}
  147 +1;
... ...
Fila-ETL/lib/Fila/ETL/DB/FEstadosGuiches.pm 0 → 100644
... ... @@ -0,0 +1,91 @@
  1 +package Fila::ETL::DB::FEstadosGuiches;
  2 +# Copyright 2008, 2009 - Oktiva Comércio e Serviços de Informática Ltda.
  3 +#
  4 +# Este arquivo é parte do programa FILA - Sistema de Atendimento
  5 +#
  6 +# O FILA é um software livre; você pode redistribui-lo e/ou modifica-lo
  7 +# dentro dos termos da Licença Pública Geral GNU como publicada pela
  8 +# Fundação do Software Livre (FSF); na versão 2 da Licença.
  9 +#
  10 +# Este programa é distribuido na esperança que possa ser util, mas SEM
  11 +# NENHUMA GARANTIA; sem uma garantia implicita de ADEQUAÇÂO a qualquer
  12 +# MERCADO ou APLICAÇÃO EM PARTICULAR. Veja a Licença Pública Geral GNU
  13 +# para maiores detalhes.
  14 +#
  15 +# Você deve ter recebido uma cópia da Licença Pública Geral GNU, sob o
  16 +# título "LICENCA.txt", junto com este programa, se não, escreva para a
  17 +# Fundação do Software Livre(FSF) Inc., 51 Franklin St, Fifth Floor,
  18 +
  19 +use strict;
  20 +use warnings;
  21 +use base qw(DBIx::Class);
  22 +
  23 +__PACKAGE__->load_components(qw(Core));
  24 +__PACKAGE__->table('f_estados_guiches');
  25 +__PACKAGE__->add_columns
  26 + (
  27 + id_local =>
  28 + {
  29 + data_type => 'integer',
  30 + },
  31 + data =>
  32 + {
  33 + data_type => 'char(10)',
  34 + },
  35 + horario =>
  36 + {
  37 + data_type => 'char(5)',
  38 + },
  39 + quantidade_fechado =>
  40 + {
  41 + data_type => 'integer',
  42 + },
  43 + quantidade_publico =>
  44 + {
  45 + data_type => 'integer',
  46 + },
  47 + quantidade_pausa =>
  48 + {
  49 + data_type => 'integer',
  50 + },
  51 + quantidade_interno =>
  52 + {
  53 + data_type => 'integer',
  54 + },
  55 + quantidade_disponivel =>
  56 + {
  57 + data_type => 'integer',
  58 + },
  59 + quantidade_chamando =>
  60 + {
  61 + data_type => 'integer',
  62 + },
  63 + quantidade_atendimento =>
  64 + {
  65 + data_type => 'integer',
  66 + },
  67 + quantidade_avaliacao =>
  68 + {
  69 + data_type => 'integer',
  70 + },
  71 + quantidade_concluido =>
  72 + {
  73 + data_type => 'integer',
  74 + },
  75 + );
  76 +
  77 +
  78 +1;
  79 +
  80 +__END__
  81 +
  82 +=head1 NAME
  83 +
  84 +FQuantidadeEstados - Tabela de quantidades por estado de atendimento
  85 +
  86 +=head1 DESCRIPTION
  87 +
  88 +Esta tabela contem o total de atendimentos em um determinado estado
  89 +por local, categoria, data, hora e minuto.
  90 +
  91 +=cut
... ...
Fila-ETL/lib/Fila/ETL/DB/FNoShow.pm 0 → 100644
... ... @@ -0,0 +1,63 @@
  1 +package Fila::ETL::DB::FNoShow;
  2 +# Copyright 2008, 2009 - Oktiva Comércio e Serviços de Informática Ltda.
  3 +#
  4 +# Este arquivo é parte do programa FILA - Sistema de Atendimento
  5 +#
  6 +# O FILA é um software livre; você pode redistribui-lo e/ou modifica-lo
  7 +# dentro dos termos da Licença Pública Geral GNU como publicada pela
  8 +# Fundação do Software Livre (FSF); na versão 2 da Licença.
  9 +#
  10 +# Este programa é distribuido na esperança que possa ser util, mas SEM
  11 +# NENHUMA GARANTIA; sem uma garantia implicita de ADEQUAÇÂO a qualquer
  12 +# MERCADO ou APLICAÇÃO EM PARTICULAR. Veja a Licença Pública Geral GNU
  13 +# para maiores detalhes.
  14 +#
  15 +# Você deve ter recebido uma cópia da Licença Pública Geral GNU, sob o
  16 +# título "LICENCA.txt", junto com este programa, se não, escreva para a
  17 +# Fundação do Software Livre(FSF) Inc., 51 Franklin St, Fifth Floor,
  18 +
  19 +use strict;
  20 +use warnings;
  21 +use base qw(DBIx::Class);
  22 +
  23 +__PACKAGE__->load_components(qw(Core));
  24 +__PACKAGE__->table('f_no_show');
  25 +__PACKAGE__->add_columns
  26 + (
  27 + id_local =>
  28 + {
  29 + data_type => 'integer',
  30 + },
  31 + id_categoria =>
  32 + {
  33 + data_type => 'integer',
  34 + },
  35 + data =>
  36 + {
  37 + data_type => 'char(10)',
  38 + },
  39 + horario =>
  40 + {
  41 + data_type => 'char(5)',
  42 + },
  43 + quantidade =>
  44 + {
  45 + data_type => 'integer',
  46 + }
  47 + );
  48 +
  49 +
  50 +1;
  51 +
  52 +__END__
  53 +
  54 +=head1 NAME
  55 +
  56 +FQuantidadeEstados - Tabela de quantidades por estado de atendimento
  57 +
  58 +=head1 DESCRIPTION
  59 +
  60 +Esta tabela contem o total de atendimentos em um determinado estado
  61 +por local, categoria, data, hora e minuto.
  62 +
  63 +=cut
... ...
Fila-ETL/lib/Fila/ETL/DB/FQuantidadeEstados.pm
... ... @@ -52,7 +52,7 @@ __PACKAGE__-&gt;add_columns
52 52 {
53 53 data_type => 'integer',
54 54 },
55   - quantidade_no_show =>
  55 + quantidade_avaliacao =>
56 56 {
57 57 data_type => 'integer',
58 58 },
... ...