From d737426332d9cc60239225ff33a197061e6858e4 Mon Sep 17 00:00:00 2001 From: Nei Jobson Date: Thu, 15 Sep 2016 11:21:15 -0300 Subject: [PATCH] Correções, melhoria do INSTALL e inclusão dos arquivos workflow.pdf e workflow.vsd com Workflow de funcionamento da solução. --- INSTALL.txt | 236 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------------------------------------------------------------------------------- usr/local/bin/ocr | 40 ++++++++++++++++++++++++---------------- workflow.pdf | Bin 0 -> 309283 bytes workflow.vsd | Bin 0 -> 169472 bytes 4 files changed, 177 insertions(+), 99 deletions(-) create mode 100644 workflow.pdf create mode 100644 workflow.vsd diff --git a/INSTALL.txt b/INSTALL.txt index 265ecb0..3b6b7fc 100644 --- a/INSTALL.txt +++ b/INSTALL.txt @@ -1,103 +1,173 @@ -# Configure o script, alterando as variáveis no arquivo 'usr/local/bin/ocr': - # @BASE_DIRS: Lista de diretórios base para a busca de arquivos --> cada diretório base irá ter sua própria instância do script - # @SUB_DIRS: Subdiretórios de entrada, saída, backup do arquivos originais, temporário e de arquivos com erro - # $MAX_FILES: Número máximo de arquivos a serem processados simultaneamente por diretório de entrada (default: 2) - # $MAX_PGS: Número máximo de páginas que podem ser processadas simultanemante por arquivo de entrada (default: no. de CPUs) - # Essas variáveis controlam o número máximo de instâncias de processos simultâneas = Num. de diretorios X MAX_FILES X MAX_PGS. - # Recomenda-se que o equipamento tenha em torno de 1,5 GB de RAM para cada core de CPU de forma a evitar swap. Se isso não for possível, pode ser reduzido o número de processos ou arquivos simultâneos. - -# Para operação multi instância, basta instalar quantos servidores forem necessários e eles podem ter acesso aos mesmos diretórios de entrada que podem ser compatilhamentos SAMBA/CIFS/Windows ou NFS. - - -# Configuração e instalação do OCR server: - -# Compilando os pré-requisitos: máquina de COMPILAÇÃO APENAS -- (RedHat) --> os requisitos de runtime estão abaixo e são menores - yum -y install autoconf make gcc-java gcc gcc-c++ subversion pkg-config automake libtool yasm cmake git libgcj - yum -y install libtiff-devel libpng-devel openjpeg-devel libjpeg-turbo-devel giflib-devel libwebp-devel zlib-devel libicu-devel pango-devel cairo-devel fontconfig-devel gettext-devel - -# Ubuntu - apt-get install build-essential cmake libtool yasm pkg-config subversion git libgcj14 - apt-get install libtiff-dev libpng-dev libopenjpeg-dev libjpeg8-dev libjpeg-turbo8-dev libjpeg-dev libgif-dev zlib1g-dev libicu-dev libpango1.0-dev libcairo2-dev libfontconfig1-dev libgettextpo-dev - - cd /usr/local/src - - for i in \ - https://github.com/tesseract-ocr/langdata.git \ - https://github.com/DanBloomberg/leptonica.git \ - https://github.com/libav/libav.git \ - https://github.com/tesseract-ocr/tessdata.git \ - https://github.com/tesseract-ocr/tesseract.git \ - git://git.freedesktop.org/git/poppler/poppler.git \ - git://git.freedesktop.org/git/poppler/test.git \ - https://github.com/Flameeyes/unpaper.git \ - https://github.com/ocaml/ocaml.git \ - https://gitlab.camlcity.org/gerd/lib-findlib.git \ - https://github.com/johnwhitington/camlpdf.git \ - https://github.com/johnwhitington/cpdf-source.git \ - ; do git clone $i; done - - wget http://www.itzgeek.com/msttcore-fonts-2.0-3.noarch.rpm - rpm -Uvh msttcore-fonts-2.0-3.noarch.rpm - rm -f msttcore-fonts-2.0-3.noarch.rpm - - wget https://www.pdflabs.com/tools/pdftk-the-pdf-toolkit/pdftk-2.02-src.zip - unzip pdftk-2.02-src.zip - rm -f pdftk-2.02-src.zip - -# Leptonica - cd leptonica && ./autobuild && ./configure && make -j 8 all install && cd .. +# OCR Server 1.0.1 - (c) Agencia Nacional de Telecomunicacoees +# +# This script monitors a set of input directories for PDF files +# once a new file is detected, it is processes through tesseract OCR +# in order to generate a new file with a hidden searchable text layer +# +# It may be distributed under the conditions of the LGPL v2.1 license. +# +# Author: Guilherme Chehab +# +# Version History: +# 0.1 Initial single server version +# 0.2 Check if page already has the html hidden layer, if so, ignore it +# 0.3 Solved issues about various image enconding types +# 0.4 Added a postnormalization step to ensure all output pdf pages have +# the same size and orientations as the original files +# 0.5 Used input file renaming as a way to sync multiple parallel instances, +# that way, it is minimized the risk of same file being OCRed multiple times. +# 0.6 Added a default handler for unknown image encoding using jpeg encoding +# 0.7 Solved an issue with files with more than 1000 pages +# 1.0 First release version +# 1.0.1 Solving error when file has no images +# +# TODO: - Changes get_imgs and OCR processing to enable pages with more than one image -- it +# would not work on previous versions that assumed #pages = #imgs. Version 1.1 counts them +# diferently but does not treat it adequately +# +# Check software requirements on the comments bellow +# +# To configure input dirs change @BASE_DIRS and @SUB_DIRS variables +# +# +# O servidor OCR depende dos seguintes componentes: +# - Perl 5.10.1, com seguintes módulos: +# - File::Find::Rule +# - File::Basename +# - File::Copy +# - File::Path +# - File::Touch +# - Sys::Syslog +# - Sys::Hostname +# - IPC::Open3 +# - IO::Select +# - POSIX +# - Tesseract-ocr 3.05, com dicionários inglês e português +# - Pdftk 2.02 +# - Poppler-utils 0.42.0 +# - Cpdf 3.3 +# - ImageMagick 6.7.2-7 +# +# Na ausência deles na distribuição do sistema operacional, o uso de versões antigas desses componentes podem comprometer o correto funcionamento do sistema +# Dessa forma, pode ser necessário compilar os componentes faltantes, assim como as bibliotecas necessárias para o seu correto funcionamento. +# Esse arquivo contem informações quanto aos procedimentos para instalar e configurar o sistema pressupondo o pior caso, qual seja, a necessidade de compilação dos componentes. +# +## ATENÇÃO: se algum componente abaixo não estiver disponível no repositório padrão para o Linux utilizado, deve-se proceder com a compilação da versão mais recente do componente disponibilizado em outros repositórios para que seja instalado no Linux a ser utilizado. +# +# Configure o script, alterando as variáveis no arquivo '/usr/local/bin/ocr': +# +# @BASE_DIRS: Lista de diretórios base para a busca de arquivos --> cada diretório base irá ter sua própria instância do script +# @SUB_DIRS: Subdiretórios de entrada, saída, backup do arquivos originais, temporário e de arquivos com erro +# $MAX_FILES: Número máximo de arquivos a serem processados simultaneamente por diretório de entrada (default: 2) +# $MAX_PGS: Número máximo de páginas que podem ser processadas simultanemante por arquivo de entrada (default: no. de CPUs) +# Essas variáveis controlam o número máximo de instâncias de processos simultâneas = Num. de diretorios X MAX_FILES X MAX_PGS. +# Recomenda-se que o equipamento tenha em torno de 1,5 GB de RAM para cada core de CPU de forma a evitar swap. Se isso não for possível, pode ser reduzido o número de processos ou arquivos simultâneos. +# A configuração do servidor pode ser dimensionada com base no tempo desejado para processamento de grandes arquivos (> 100 páginas). Cada página tem sua própria thread de processamento, até o limite de $MAX_PGS, cujo default é o no. de cores de CPU. Em média cada página demora em torno de 18 segundos em uma CPU Xeon E5 4670@2.6GHz. Assim, com 16 CPUs, o desempenho agregado é em torno de 1,2 segundos por página. +# +# Para operação multi instância, basta instalar quantos servidores forem necessários e eles podem ter acesso aos mesmos diretórios de entrada que podem ser compartilhamentos SAMBA/CIFS/Windows ou NFS. +# +# +# ----------------------- COMPILAÇÃO dos pré requisitos (obs.: os comandos de devem ser executados como root) +# +# +# Compilando os pré-requisitos: máquina de COMPILAÇÃO APENAS +# +# RedHat 6.7: +yum -y install autoconf make gcc-java gcc gcc-c++ subversion pkg-config automake libtool yasm cmake git libgcj +yum -y install libtiff-devel libpng-devel openjpeg-devel libjpeg-turbo-devel giflib-devel libwebp-devel zlib-devel libicu-devel pango-devel cairo-devel fontconfig-devel gettext-devel +cd /tmp +wget http://www.itzgeek.com/msttcore-fonts-2.0-3.noarch.rpm +rpm -Uvh msttcore-fonts-2.0-3.noarch.rpm +rm -f msttcore-fonts-2.0-3.noarch.rpm + +# Ubuntu 14.04 Server: +apt-get install build-essential cmake libtool yasm pkg-config subversion git libgcj14 +apt-get install libtiff-dev libpng-dev libopenjpeg-dev libjpeg8-dev libjpeg-turbo8-dev libjpeg-dev libgif-dev zlib1g-dev libicu-dev libpango1.0-dev libcairo2-dev libfontconfig1-dev libgettextpo-dev +apt-get install +apt-get install ttf-mscorefonts-installer + +# Ambas plataformas: +cd /usr/local/src + +for i in \ + https://github.com/tesseract-ocr/langdata.git \ + https://github.com/DanBloomberg/leptonica.git \ + https://github.com/libav/libav.git \ + https://github.com/tesseract-ocr/tessdata.git \ + https://github.com/tesseract-ocr/tesseract.git \ + git://git.freedesktop.org/git/poppler/poppler.git \ + git://git.freedesktop.org/git/poppler/test.git \ + https://github.com/Flameeyes/unpaper.git \ + https://github.com/ocaml/ocaml.git \ + https://gitlab.camlcity.org/gerd/lib-findlib.git \ + https://github.com/johnwhitington/camlpdf.git \ + https://github.com/johnwhitington/cpdf-source.git \ +; do git clone $i; done + +wget https://www.pdflabs.com/tools/pdftk-the-pdf-toolkit/pdftk-2.02-src.zip +unzip pdftk-2.02-src.zip +rm -f pdftk-2.02-src.zip + +# Tesseract, versão 3.05-dev ou superior +# Bibliotecas para o Tesseract: Leptonica e Libav +cd leptonica && ./autobuild && ./configure && make -j 8 all install && cd .. + +cd libav && ./configure --enable-sram && make -j8 all install && cd .. # Tesseract - cd tesseract && ./autogen.sh && ./configure && make -j 8 all install && cd .. - cp -avR tessdata/* /usr/local/share/tessdata/ +cd tesseract && ./autogen.sh && ./configure && make -j 8 all install && cd .. +cp -avR tessdata/* /usr/local/share/tessdata/ -# libav - cd libav && ./configure --enable-sram && make -j8 all install && cd .. +# cpdf, versão 3.3 ou superior +cd ocaml && ./configure && make world.opt && make install && cd .. +mkdir -p /usr/local/man/man5 +cd lib-findlib && ./configure && make all && make install && cd .. +cd camlpdf && sed -i.bak s/\(uint32\)/\(uint32_t\)/g flatestubs.c && make && make install && cd .. +cd cpdf-source && make all && make install && cp cpdf /usr/local/bin && cd .. -# cpdf - cd ocaml && ./configure && make world.opt && make install && cd .. - mkdir -p /usr/local/man/man5 - cd lib-findlib && ./configure && make all && make install && cd .. - cd camlpdf && sed -i.bak s/\(uint32\)/\(uint32_t\)/g flatestubs.c && make && make install && cd .. - cd cpdf-source && make all && make install && cp cpdf /usr/local/bin && cd .. +# pdftk, versão 2.02 ou superior +cd pdftk-2.02-dist/pdftk && make -f Makefile.Redhat all install && cd ../.. -# pdftk - cd pdftk-2.02-dist/pdftk && make -f Makefile.Redhat all install && cd ../.. +# poppler-utils, versão 0.42.0 ou superior +cd poppler && ./autogen.sh && LIBOPENJPEG_LIBS=-l/usr/local/lib/libopenjp2.so LIBOPENJPEG_CFLAGS=-I/usr/local/include ./configure --enable-libopenjpeg=openjpeg2 && make all install && cd .. -# poppler - cd poppler && ./autogen.sh && LIBOPENJPEG_LIBS=-l/usr/local/lib/libopenjp2.so LIBOPENJPEG_CFLAGS=-I/usr/local/include ./configure --enable-libopenjpeg=openjpeg2 && make all install && cd .. +# ----------------------- INSTALAÇÃO (obs.: os comandos de devem ser executados como root) +## Comandos adicionais para configuração do módulo: + # Criação do usuário - adduser ocr +adduser ocr # Copie os arquivos ocr ocr-init* para o /home/ocr e, conforme o sistema operacional - cp /home/ocr/ocr /usr/local/bin - cp /home/ocr/ocr-init-rh /etc/init.d/ocr (OU) - cp /home/ocr/ocr-init-Ubuntu /etc/init/ocr +cp /home/ocr/ocr /usr/local/bin +cp /home/ocr/ocr-init-rh /etc/init.d/ocr (OU) +cp /home/ocr/ocr-init-Ubuntu /etc/init/ocr -# Auto start (RedHat) - chkconfig --add ocr - chkconfig --level 2345 ocr on +# Auto start (RedHat 6.7) +chkconfig --add ocr +chkconfig --level 2345 ocr on -# Auto start (Ubuntu) - update-rd.d ocr defaults +# Auto start (Ubuntu 14.04) +update-rd.d ocr defaults # Create pkg - cd /home/ocr - tar cvozf pkg-ocr.tgz /usr/local/bin /usr/local/lib* /usr/local/man/ /usr/local/sbin/ /usr/local/share/ /usr/local/etc /usr/local/include/ /home/ocr/ocr* /etc/init.d/ocr /etc/rc*.d/*ocr - su +cd /home/ocr +tar cvozf pkg-ocr.tgz /usr/local/bin /usr/local/lib* /usr/local/man/ /usr/local/sbin/ /usr/local/share/ /usr/local/etc /usr/local/include/ /home/ocr/ocr* /etc/init.d/ocr /etc/rc*.d/*ocr +su # Copie o pacote para os outros servidores e extraia com: - cd / - tar xovzf pkg-ocr.tgz +cd / +tar xovzf pkg-ocr.tgz -# Instalando pré-requisitos RUNTIME - yum -y install perl-File-Find-Rule-Perl perl-File-Touch libtiff libpng openjpeg-libs libjpeg-turbo giflib zlib libicu pango cairo fontconfig ImageMagick gettext libwebp - yum -y install libtiff libpng openjpeg libjpeg-turbo giflib libwebp zlib libicu pango cairo fontconfig gettext +# Instalando pré-requisitos RUNTIME em servidores adicionais -# Ubuntu - apt-get install libfile-find-rule-perl libfile-find-rule-perl-perl libtiff5 libpng12-0 libopenjpeg2 libjpeg-turbo8 libgif4 zlib1g libicu52 libpango1.0-0 libcairo2 fontconfig imagemagick gettext libwebp5 # libgcj14 - apt-get install libtiff5 libpng12-0 libopenjpeg2 libjpeg8 libjpeg-turbo8 libjpeg8 zlib1g libpango1.0-0 libcairo2 libfontconfig1 libgettextpo0 +# Redhat 6.7 +yum -y install perl-File-Find-Rule-Perl perl-File-Touch libtiff libpng openjpeg-libs libjpeg-turbo giflib zlib libicu pango cairo fontconfig ImageMagick gettext libwebp +yum -y install libtiff libpng openjpeg libjpeg-turbo giflib libwebp zlib libicu pango cairo fontconfig gettext + +# Ubuntu 14.04 +apt-get install libfile-find-rule-perl libfile-find-rule-perl-perl libtiff5 libpng12-0 libopenjpeg2 libjpeg-turbo8 libgif4 zlib1g libicu52 libpango1.0-0 libcairo2 fontconfig imagemagick gettext libwebp5 # libgcj14 +apt-get install libtiff5 libpng12-0 libopenjpeg2 libjpeg8 libjpeg-turbo8 libjpeg8 zlib1g libpango1.0-0 libcairo2 libfontconfig1 libgettextpo0 # Inicie o serviço com - service ocr start \ No newline at end of file +service ocr start \ No newline at end of file diff --git a/usr/local/bin/ocr b/usr/local/bin/ocr index db3186a..bc9cd3c 100644 --- a/usr/local/bin/ocr +++ b/usr/local/bin/ocr @@ -1,6 +1,6 @@ #! /usr/bin/perl -w # -# OCR Server 1.0 - (c) Agência Nacional de Telecomunicações +# OCR Server 1.0.1 - (c) Agencia Nacional de Telecomunicacoes # # This script monitors a set of input directories for PDF files # once a new file is detected, it is processes through tesseract OCR @@ -21,6 +21,11 @@ # 0.6 Added a default handler for unknown image encoding using jpeg encoding # 0.7 Solved an issue with files with more than 1000 pages # 1.0 First release version +# 1.0.1 Solving error when file has no images +# +# TODO: - Changes get_imgs and OCR processing to enable pages with more than one image -- it +# would not work on previous versions that assumed #pages = #imgs. Version 1.1 counts them +# diferently but does not treat it adequately # # Check software requirements on the comments bellow # @@ -288,10 +293,9 @@ sub ocr { my ($pages, @pg_w, @pg_h, @pg_r); $pages = get_pages ($tmp_file, \@pg_w, \@pg_h, \@pg_r); - - my (@img_w, @img_h, @img_t); - $pages = get_imgs ( $tmp_file, \@img_w, \@img_h, \@img_t); + my ($imgs,@page_img, @img_w, @img_h, @img_t); + $imgs = get_imgs ( $tmp_file, \@page_img, \@img_w, \@img_h, \@img_t); for ( my $i=0; $i< $pages; $i++ ) { my $pg = sprintf ("pg_%06d", $i+1); @@ -308,18 +312,21 @@ sub ocr { $pids{$pid}=$pg; } else { $0 = "ocr $in_name (".($i+1)."/$pages)" if(!$DEBUG); - print "\t\t${in_file}: ".(${i}+1)." / $pages: $pg_w[$i] x $pg_h[$i] - $pg_r[$i] & $img_w[$i] x $img_h[$i], $img_t[$i]\n" if $DEBUG; - if (! defined $img_t[$i] ) { + if (is_ocred ("${tmpdir}/${pg}.pdf")) { move ("${tmpdir}/${pg}.pdf","${tmpdir}/${pg}-cpdf.pdf"); + print "\t\t${in_file}: ".(${i}+1)." / $pages: Page already has text layer, ignoring page\n" if $DEBUG; exit 0; } - if (is_ocred ("${tmpdir}/${pg}.pdf")) { + if (! defined $img_t[$i] ) { move ("${tmpdir}/${pg}.pdf","${tmpdir}/${pg}-cpdf.pdf"); + print "\t\t${in_file}: ".(${i}+1)." / $pages: Undefined image type on page, ignoring page\n" if $DEBUG; exit 0; } + print "\t\t${in_file}: ".(${i}+1)." / $pages: $pg_w[$i] x $pg_h[$i] - $pg_r[$i] & $img_w[$i] x $img_h[$i], $img_t[$i]\n" if $DEBUG; + undef $cmd; if ($img_t[$i] eq "gray") { @@ -462,8 +469,8 @@ sub get_pages { } sub get_imgs { - my ($in_file, $w, $h, $t) = @_; - my ($dumb, $i, $width, $height, $type); + my ($in_file, $page_img, $w, $h, $t) = @_; + my ($dumb, $i, $page, $width, $height, $type); my ($exit, $cmd, @lines, @err) = exec_cmd("${PDFIMAGES} -list \"${in_file}\""); @@ -471,15 +478,16 @@ sub get_imgs { chomp $line; $line =~ s/^ {1,}//; if ( $line =~ /image|mask/ ) { - ($i , $dumb, $dumb, $width, $height, $type) = split / {1,}/,$line; - @$w[$i-1] = $width; - @$h[$i-1] = $height; - @$t[$i-1] = ( $type eq "-" ? "rgb" : $type ); - @$t[$i-1] = ( $type eq "icc" ? "rgb" : $type ); - @$t[$i-1] = ( $type eq "index" ? "rgb" : $type ); + ($page, $i , $dumb, $width, $height, $type) = split / {1,}/,$line; + @$page_img[$page-1]=$i; + @$w[$page-1] = $width; + @$h[$page-1] = $height; + @$t[$page-1] = ( $type eq "-" ? "rgb" : $type ); + @$t[$page-1] = ( $type eq "icc" ? "rgb" : $type ); + @$t[$page-1] = ( $type eq "index" ? "rgb" : $type ); } } - return $i; + return $i+1; } sub get_rotation { diff --git a/workflow.pdf b/workflow.pdf new file mode 100644 index 0000000..3cae9ab Binary files /dev/null and b/workflow.pdf differ diff --git a/workflow.vsd b/workflow.vsd new file mode 100644 index 0000000..43f31a7 Binary files /dev/null and b/workflow.vsd differ -- libgit2 0.21.2