Alfresco, instalando OCR en un servidor externo

por / Jueves, 19 Enero 2017 / Publicado enBlog
BeeCon 2017
Descubre todo lo que traerá Alfresco 5.2

Nuestro Alfresco Simple OCR Action se ha convertido en los últimos meses en el addon de referencia para incorporar un servicio de OCR a la versión Community de Alfresco tanto en servidores Linux como en servidores Windows.

A pesar de que en muchos casos la guía de configuración provista en GitHub es suficiente, existen otros escenarios de uso intensivo que requieren un despliegue más complejo. En este artículo os mostramos cómo configurar un servicio de OCR para Alfresco alojado en un servidor externo, lo que permite mantener la calidad de servicio de Alfresco independientemente del nivel de carga OCR que esté experimentando el sistema.

Describiremos una configuración de Alfresco comunicándose por SSH con un servidor de OCR corriendo pdfsandwich en un CentOS 7, pero podéis utilizar otro protocolo de comunicación, sistema operativo Windows o un software de OCR distinto para implementar vuestro servicio.

Configuración del servidor de OCR

Software requerido:

  • CentOS Linux release 7.3.1611 (Core)
  • pdfsandwich 0.1.4

Puertos requeridos:

  • 22 (SSH): servicio de proceso OCR de pdfsandwich

La aplicación pdfsandwich es utilizada para la generación de PDFs buscables a partir de ficheros PDF con imágenes o imágenes TIFF. Este servicio será invocado por línea de comandos desde Alfresco a través del addon Alfresco Simple OCR instalado en el servidor de Alfresco.

Instalando pdfsandwich

Se instalan las dependencias necesarias.

$ yum -y install wget gcc gcc-c++ make autoconf automake libtool libjpeg-devel libpng-devel libtiff-devel zlib-devel ocaml ImageMagick ImageMagick-devel

Se instala el programa leptonica a partir de los fuentes.

$ wget http://www.leptonica.org/source/leptonica-1.72.tar.gz
$ tar xvf leptonica-1.72.tar.gz
$ cd leptonica-1.72
$ ./configure
$ make
$ make install

Se instala el programa tesseract OCR a partir de los fuentes.

$ wget http://github.com/tesseract-ocr/tesseract/archive/3.04.01.tar.gz
$ tar xvf 3.04.01.tar.gz
$ cd tesseract-3.04.01
$ ./autogen.sh
$ ./configure
$ make
$ make install
$ ldconfig

Se instalan todos los paquetes de idioma de tesseract.

$ wget https://github.com/tesseract-ocr/tessdata/archive/3.04.00.tar.gz
$ tar xvf 3.04.00.tar.gz
$ mv tessdata-3.04.00/* /usr/local/share/tessdata/

Se instala el programa unpaper a través de su RPM.

$ wget http://dl.fedoraproject.org/pub/epel/6/x86_64/unpaper-0.3-4.el6.x86_64.rpm
$ rpm -ivh unpaper-0.3-4.el6.x86_64.rpm

Se instala el programa pdfsandwich a partir de los fuentes.

$ wget http://downloads.sourceforge.net/project/pdfsandwich/pdfsandwich%200.1.4/pdfsandwich-0.1.4.tar.bz2
$ tar xvf pdfsandwich-0.1.4.tar.bz2
$ cd pdfsandwich-0.1.4
$ ./configure
$ make
$ make install

Se verifica que el programa ha sido correctamente instalado.

$ pdfsandwich -version
pdfsandwich version 0.1.4

Configuración del servidor de Alfresco

Una vez instalado un Alfresco en el addon Alfresco Simple OCR, creamos un script para la invocación al servidor remoto de OCR.


#!/bin/bash

# pdfsandwich hostname
PDFSANDWICH_SERVER="alfresco-ocr.keensoft.es"

# extract filenames
INPUT=$(basename "$3")
OUTPUT=$(basename "$5")

# SSH parameters
SCP=scp
SSH=ssh

# copy original pdf to pdfsandwich server
$SCP $3 root@$PDFSANDWICH_SERVER:/tmp/$INPUT

# execute pdfsandwich program (requires administrator privileges)
$SSH root@$PDFSANDWICH_SERVER "pdfsandwich $1 $2 /tmp/$INPUT $4 /tmp/$OUTPUT $6"

# copy transformed pdf back to alfresco server
$SCP root@$PDFSANDWICH_SERVER:/tmp/$OUTPUT $5

# remove temporal files
$SSH root@$PDFSANDWICH_SERVER "rm -f /tmp/$INPUT; rm -f /tmp/$OUTPUT"

Se genera la clave RSA en el servidor de Alfresco y se envía la parte pública al servidor de OCR para permitir comandos ssh sin interacción.


$ ssh-keygen -t rsa
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa):
Enter passphrase (empty for no passphrase):
Enter same passphrase again:
Your identification has been saved in /root/.ssh/id_rsa.
Your public key has been saved in /root/.ssh/id_rsa.pub.
$ ssh-copy-id -i ~/.ssh/id_rsa.pub alfresco-ocr.keensoft.es

Se actualiza la propiedad de alfresco-global.properties para que utilice el script que hemos creado arriba.


ocr.command=/opt/alfresco/scripts/ocr.sh

Se reinicia el servicio de Alfresco.

$ systemctl restart alfresco

Conclusiones

Una vez realizada esta configuración, los trabajos de OCR serán enviados por Alfresco al servidor externo alfresco-ocr.keensoft.es, permitiendo mantener la calidad de servicio en el propio servidor de Alfresco. También es posible aumentar la capacidad de este servicio, configurando el pool de hilos asíncronos de Alfresco.


# Default Async Action Thread Pool
default.async.action.threadPriority=1
default.async.action.corePoolSize=8
default.async.action.maximumPoolSize=20

En ocasiones, para mejorar la calidad de servicio de Alfresco no es necesario disponer de nuevo software, sino de instalar el disponible de la manera adecuada.

Responsable tecnológico para soluciones de gestión documental en keensoft. Especialista en Alfresco y en implantaciones de Administración Electrónica.

Etiquetado bajo: ,

2 Responses to “Alfresco, instalando OCR en un servidor externo”

  1. Hola Angel,
    Muchas gracias por tus contribuciones. Me preguntaba si podrias ayudarme.
    He intentado en más de cinco ocasiones configurar el servidor de pdfsandwich remoto (en local funciona sin problemas).
    Para poder instalar simple-ocr y que alfresco inicie, no he encontrado otra manera que instalar también pdfsandwich en el servidor “local”.

    servidor debian 8.7.1 (local)
    alfresco 5.2

    servidor ubuntu 16.1 (también intentado 13.1 con idéntico resultado) (remoto)
    pdfsandwich 0.1.6
    tesseract 3.03
    leptonica 1.71
    unpaper 0.4.2

    Modificando el archivo “alfresco-global.properties”, según indica la web de simple-ocr, pero usando el script que llama al procedimiento remoto, en lugar de la primera línea:

    #ocr.command=/usr/local/bin/pdfsandwich
    ocr.command=/opt/alfresco-community/scripts/ocr.sh
    ocr.output.verbose=true
    ocr.output.file.prefix.command=-o

    ocr.extra.commands=-verbose -lang spa+eng+fra
    ocr.server.os=linux

    En mi caso, debo cambiar las variables del script “ocr.sh” que propones, puesto que la salida es:
    /opt/alfresco-community/scripts/ocr.sh -verbose -lang cat+spa /opt/alfresco-community/tomcat/temp/Alfresco/OCRTransformWorker_source_5849973338233067610.pdf -o /opt/alfresco-community/tomcat/temp/Alfresco/OCRTransformWorker_source_5849973338233067610_ocr.pdf

    así que…

    $1: -verbose
    $2: -lang
    $3: spa
    $4: source_path
    $5: -o
    $6: destination_path

    pdfsandwich INPUT -lang spa -verbose -o OUTPUT
    $SSH root@$PDFSANDWICH_SERVER “pdfsandwich /tmp/$INPUT $2 $3 $1 $5 /tmp/$OUTPUT”
    para cumplir:
    pdfsandwich INPUT -lang spa -verbose -o OUTPUT

    y el error que aparece, en “catalina.out” es:

    2017-04-22 09:37:50,217 WARN [alfresco.ocr.OCRExtractAction] [http-apr-8080-exec-5] workspace://SpacesStore/32e14ff1-a103-405a-8510-5187b01d989b: Node does not exist: workspace://SpacesStore/32e1$
    2017-04-22 09:37:50,254 INFO [alfresco.ocr.OCRTransformWorker] [http-apr-8080-exec-5] EXIT VALUE: 127
    2017-04-22 09:37:50,254 INFO [alfresco.ocr.OCRTransformWorker] [http-apr-8080-exec-5] STDOUT:
    2017-04-22 09:37:50,254 INFO [alfresco.ocr.OCRTransformWorker] [http-apr-8080-exec-5] STDERR: /usr/bin/ssh: relocation error: /usr/bin/ssh: symbol EVP_des_cbc, version OPENSSL_1.0.0 not defined $
    lost connection
    /usr/bin/ssh: relocation error: /usr/bin/ssh: symbol EVP_des_cbc, version OPENSSL_1.0.0 not defined in file libcrypto.so.1.0.0 with link time reference
    ssh: relocation error: ssh: symbol EVP_des_cbc, version OPENSSL_1.0.0 not defined in file libcrypto.so.1.0.0 with link time reference

    2017-04-22 09:37:50,267 ERROR [web.scripts.RepositoryContainer] [http-apr-8080-exec-5] Server error (03220024)
    java.lang.RuntimeException: java.lang.RuntimeException: org.alfresco.service.cmr.repository.ContentIOException: 03220023 Failed to perform OCR transformation:
    Execution result:
    os: Linux
    command: /opt/alfresco-community/scripts/ocr.sh -verbose -lang cat+spa /opt/alfresco-community/tomcat/temp/Alfresco/OCRTransformWorker_source_6184988632786898645.pdf -o /opt/alfresco-communit$
    succeeded: true
    exit code: 127
    out:
    err: /usr/bin/ssh: relocation error: /usr/bin/ssh: symbol EVP_des_cbc, version OPENSSL_1.0.0 not defined in file libcrypto.so.1.0.0 with link time reference
    lost connection
    /usr/bin/ssh: relocation error: /usr/bin/ssh: symbol EVP_des_cbc, version OPENSSL_
    at es.keensoft.alfresco.ocr.OCRExtractAction.executeImplInternal(OCRExtractAction.java:143)
    at es.keensoft.alfresco.ocr.OCRExtractAction.executeImpl(OCRExtractAction.java:88)
    at org.alfresco.repo.action.executer.ActionExecuterAbstractBase.execute(ActionExecuterAbstractBase.java:274)
    at org.alfresco.repo.action.ActionServiceImpl.directActionExecution(ActionServiceImpl.java:846)
    at org.alfresco.repo.action.executer.CompositeActionExecuter.executeImpl(CompositeActionExecuter.java:73)
    at org.alfresco.repo.action.executer.ActionExecuterAbstractBase.execute(ActionExecuterAbstractBase.java:274)
    at org.alfresco.repo.action.ActionServiceImpl.directActionExecution(ActionServiceImpl.java:846)
    at org.alfresco.repo.action.ActionServiceImpl.executeActionImpl(ActionServiceImpl.java:747)
    at org.alfresco.repo.action.ActionServiceImpl.executeAction(ActionServiceImpl.java:581)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:183)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:150)
    at org.alfresco.repo.security.permissions.impl.AlwaysProceedMethodInterceptor.invoke(AlwaysProceedMethodInterceptor.java:41)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
    at org.alfresco.repo.security.permissions.impl.ExceptionTranslatorMethodInterceptor.invoke(ExceptionTranslatorMethodInterceptor.java:53)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
    at org.alfresco.repo.audit.AuditMethodInterceptor.invoke(AuditMethodInterceptor.java:166)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
    at org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:96)
    at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:260)
    at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:94)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:204)

  2. Creo que si usas el ejemplo tal cual está funcionará. ¿Has probado a realizarlo así? No entiendo demasiado bien el cambio que haces…

Deja un comentario

SUBIR