Java OCR : riconoscimento di una stringa e terminare subito senza processare intero contenuto

82 views
Skip to first unread message

Giuseppe Coniglio

unread,
Sep 8, 2022, 11:50:07 AM9/8/22
to JUG Torino - JVM User Group Torino
Ciao a tutti,
avrei bisogno di una libreria OCR da usare con JAVA che data in input una stringa di testo appena viene trovata termini subito la conversione.

Ho provato Tesseract con un progetto pilota trovato su https://colwil.com/how-to-extract-text-from-a-scanned-pdf-using-ocr-in-java/

    String text = extractTextFromScannedDocument(document);
    System.out.println(text)

Purtroppo sto riscontrando diverse velocità di esecuzione indipendenti dalle dimensioni del file ma dal contenuto del file pdf :
- 10 secondi per elaborare un pdf di 400 KB con una pagina soltanto che è una immagine con poco testo;
- 3 minuti  per elaborare un pdf di 800 KB con 11 pagine tutte immagini con parecchio testo;
-  1 minuto per elaborare un pdf di 70 KB con 9 pagine con parecchio testo;
-  45 secondi per un file di 1 MB con 2 pagine di cui entrambe immagini dentro il pdf (testo come fosse il contratto della Sim telefonica)

Ho cercato qualcosa a pagamento come Aspose (https://products.aspose.com/ocr/java/) ma anche qua nel codice Java viene elaborato tutto il file e stampato il contenuto :

// Recognize image 
  String result = api.RecognizePage("<file name>"); 
// Display the recognition result 
 System.out.println(result);

Conoscete una libreria OCR che converte il file in testo dando un testo in input e che si fermi subito ? 

Ho necessità che l'elaborazione OCR sia sincrona durante un upload da pagina web e per questo non posso far aspettare l'utente.... questo caso d'uso è un requisito essenziale , potrei fare l'laborazione OCR asincrona con un microservizio Spring Boot ma prima vorrei capire se esiste qualcosa che fa al mio caso.

Grazie :-)
Have a nice day

Giuseppe Coniglio

unread,
Sep 9, 2022, 10:11:13 AM9/9/22
to JUG Torino - JVM User Group Torino
Ho provato per curiosità l'Utilizzo di Google Cloud: ho caricato nel mio cloud il pdf di esempio da 69 KB ma con tanto testo (9 pagine), ho eseguito il codice presente su https://cloud.google.com/vision/docs/pdf, mi ha creato i files json nella cartella di output nel mio Bucket, ma il tempo di esecuzione è notevole -> sempre dai 25 secondi in su...
E comunque si tratterebbe di salvare prima i files in cloud perdendo lo scenario real time durante l'upload dell'utente...
Temo non ci sia una libreria e/o servizio che faccia searching e ocr contemporaneamente :-(

Giuseppe Coniglio

unread,
Sep 12, 2022, 8:40:01 AM9/12/22
to JUG Torino - JVM User Group Torino
Non ci sono soluzioni sincrone, per forza di cose l'elaborazione sarà asincrona:
Sarà schedulato ogni tot minuti e validerà i file pdf estraendo il testo e ricercando le parole chiave corrette.
Bye 

Matteo Mortari

unread,
Sep 12, 2022, 9:10:24 AM9/12/22
to Giuseppe Coniglio, JUG Torino - JVM User Group Torino
Ciao Giuseppe,
non sono intervenuto in questo thread prima, perché di OCR che fa short-circuit/early return appena trova un match non ne conosco; noto adesso stai pensando di integrare OCR nella maniera "classica" ovvero lasciare al OCR ritornare tutto il testo trovato.

Volevo segnalarti, se può essere utile, che io ho trovato facilissimo usare questa estensione: https://quarkiverse.github.io/quarkiverse-docs/quarkus-tika/dev/index.html
L'ho usata per questo progettino: https://github.com/tarilabs/quarkus-aytb#readme

Spero possa esserti utile, se non hai requisiti particolari sullo stack (i.e.: Spring Boot).
Ciao,
MM

--
Hai ricevuto questo messaggio perché sei iscritto al gruppo "JUG Torino - JVM User Group Torino" di Google Gruppi.
Per annullare l'iscrizione a questo gruppo e non ricevere più le sue email, invia un'email a jugtorino+...@googlegroups.com.
Per visualizzare questa discussione sul Web, visita https://groups.google.com/d/msgid/jugtorino/50186c1c-cfc3-460f-a449-66badc8fa2c5n%40googlegroups.com.


--

Giuseppe Coniglio

unread,
Sep 12, 2022, 10:29:36 AM9/12/22
to JUG Torino - JVM User Group Torino
  Ciao Matteo,
in teoria considerando che le parole chiave da ricercare starebbero sulla prima pagina (sto vedendo tutti i pdf forniti dal cliente) potrei anche non parsificare tutto il contenuto del file.
Esempio con pseudo codice molto grezzo e da ottimizzare :-)

        PDFRenderer pdfRenderer = new PDFRenderer(document);
        StringBuilder out = new StringBuilder();
        ITesseract _tesseract = new Tesseract();
        _tesseract.setDatapath("tessdata");
        _tesseract.setLanguage("ita");          
        for (int page = 0; page < document.getNumberOfPages(); page++) {
            BufferedImage bufferedImage = pdfRenderer.renderImageWithDPI(page, 300, ImageType.RGB);
            File tempFile = File.createTempFile("tempfile_" + page, ".png");
            ImageIO.write(bufferedImage, "png", tempFile);
            String result = _tesseract.doOCR(tempFile);
            int index = result.toUpperCase().indexOf("STRINGA DA TROVARE");
           if (index >= 0 ) {
                System.out.println("Trovato il testo 'STRINGA DA TROVARE'");
                break;
            }
            out.append(result);
            tempFile.delete();
        }
        return out.toString();

Ovviamente nella realtà avrò diversi testi da cercare ed il codice sarà ben diverso ;-)

Casi pilota:
PDF  (70 KB) creato con testo : 9 pagine : Trovata la stringa nella prima pagina e tempo di elaborazione 7 secondi
PDF (900 KB) creato con 11 immagini , una immagine in ogni pagina : Trovata la stringa nella prima pagina , tempo di elaborazione  dai 15 secondi in su...

Rimane dunqu una elaborazione asincrona in tutti i casi e non fattibile durante l'upload del file nella pagina web.
Sto scrivendo il mio microservizio con schedulazione interna che andrà a elaborare i files pdf presenti nel path utente...

Provo a dare un'occhiata all'estensione fornitami :-)
Grazie
Giuseppe

Giuseppe Coniglio

unread,
Sep 12, 2022, 11:40:48 AM9/12/22
to JUG Torino - JVM User Group Torino
Sto provando Apache Tika, codice sorgente preso da https://github.com/mimaraslan/ocr-apache-tika-demo-project/blob/master/src/com/mimaraslan/_009_PdfParse.java

File di prova allegati 

Stampa il contenuto del file "Example.pdf" in 2 secondi:

Contents of the PDF :
Apache Tika is a framework for content type detection and content extraction which was designed by

Apache software foundation. It detects and extracts metadata and structured text content from

different types of documents such as spreadsheets, text documents, images or PDFs including audio or

video input formats to certain extent. 


Ok il pdf contiente queste righe di testo, ma se provo a salvare come immagine e creare un pdf non rileva alcun testo:

***************************

Contents of the PDF :
 



***************************


         BodyContentHandler handler = new BodyContentHandler();
          Metadata metadata = new Metadata();
          //FileInputStream inputstream = new FileInputStream(new File("Example.pdf"));
          FileInputStream inputstream = new FileInputStream(new File("PDF_creato_con_immagine.pdf"));
          ParseContext pcontext = new ParseContext();
         
          //parsing the document using PDF parser
          PDFParser pdfparser = new PDFParser();
          pdfparser.parse(inputstream, handler, metadata,pcontext);
          System.out.println("***************************\n");
          //getting the content of the document
          System.out.println("Contents of the PDF :" + handler.toString());
          System.out.println("***************************\n");
  
Addirittura qua non viene rilevato neanche il testo del pdf creato tramite immagine, non va bene
Sto sbagliando qualcosa con Apache Tika secondo voi?
Grazie :-)
Example.pdf
PDF_creato_con_immagine.pdf

Giuseppe Coniglio

unread,
Sep 12, 2022, 11:57:51 AM9/12/22
to JUG Torino - JVM User Group Torino
The Apache Tika™ toolkit detects and extracts metadata and text from over a thousand different file types (such as PPT, XLS, and PDF).

Non va bene nel mio caso, io ho dei PDF creati con delle immagini all'interno

God Save the King
 ;-)

Matteo Mortari

unread,
Sep 12, 2022, 12:15:25 PM9/12/22
to Giuseppe Coniglio, JUG Torino - JVM User Group Torino
Weird, IIRC anche le immagini embedded nel PDF erano uno degli use case supportati, altrimenti non servirebbe la integrazione che hanno con Tesseract, non credi?
Se fosse limitato al testo nel PDF basterebbe parsare il PDF, Tesseract serve proprio per lo OCR.

Prova a guardare nel manuale di Tika, perché a me pare di ricordare qualcosa in merito alle "include inline images"?🤔

Mi spiace di non ricordare più precisamente, spero aiuti cmq


Giuseppe Coniglio

unread,
Sep 12, 2022, 12:28:14 PM9/12/22
to JUG Torino - JVM User Group Torino
Anche con le immagini non va ,  TIKA - Extracting Image File : https://www.tutorialspoint.com/tika/tika_extracting_image_file.htm

Contents of the document:

Nessun contenuto rilevato

rilevo il testo di qualsiasi pdf, creato con testo oppure con immagini :-)
ciao
Immagine_con_Test.jpg
boy.jpg

Matteo Mortari

unread,
Sep 24, 2022, 3:07:24 AM9/24/22
to Giuseppe Coniglio, JUG Torino - JVM User Group Torino
Ciao Giuseppe

> Non va bene nel mio caso, io ho dei PDF creati con delle immagini all'interno
> ...
> Anche con le immagini non va

A me Tika va eccome :) estraggo il testo dal PDF allegato anche dalle immagini che estrae con Tesseract via OCR.

L'unica cosa che ho sempre notato nella mia breve esperienza con Tika, è che di solito la configurazione di default funziona bene in moltissimi casi, ma non necessariamente "il tuo" ed in tal caso basta assicurarsi della pipeline di parsing di Tika sia quella migliore per il tuo use-case.

Ho fatto una breve demo al volo qui: link
Allego anche screenshot.

Spero utile,
MM

Screenshot 2022-09-24 at 08.51.57.png.jpg

Giuseppe Coniglio

unread,
Sep 26, 2022, 5:53:44 AM9/26/22
to Matteo Mortari, JUG Torino - JVM User Group Torino
Ciao Matteo,
Ovviamente senza installare alcunchè nel mio Windows 
Impostando la property "setExtractInlineImages" di Tika il testo ora viene estratto correttamente da un pdf contenente immagini

Parser parser      = new AutoDetectParser();
 BodyContentHandler handler      = new BodyContentHandler(Integer.MAX_VALUE);
 TesseractOCRConfig config       = new TesseractOCRConfig();
     PDFParser pdfparser          = new PDFParser(); // parsing the document using PDF parser
     PDFParserConfig pdfParserConfig = new PDFParserConfig();
 
     ParseContext parseContext    = new ParseContext();

     Metadata metadata      = new Metadata();

     pdfParserConfig.setExtractInlineImages(true);
     pdfParserConfig.setExtractUniqueInlineImagesOnly(false); // set to false if pdf contains multiple images.
     
     parseContext.set(TesseractOCRConfig.class, config);
     parseContext.set(PDFParserConfig.class, pdfParserConfig);
     parseContext.set(Parser.class, parser); //need to add this to make sure recursive parsing happens!
     
     pdfparser.parse(inputstream, handler, metadata, parseContext);

     System.out.println("Content:" + handler.toString());

Grazie ancora :-)
Buona giornata

Giuseppe Coniglio

unread,
Sep 26, 2022, 9:33:18 AM9/26/22
to Matteo Mortari, JUG Torino - JVM User Group Torino
Errata corrige, usando il pdf 

il testo rilevato è:

This is a PDF containing text and images; this was part of some text.

Below you can find an image

Manca il testo dell'immagine che è presente nel pdf.

pdfParserConfig.setExtractInlineImages(true);
 pdfParserConfig.setExtractUniqueInlineImagesOnly(true); // set to false if pdf contains multiple images.


Credo di abbandonare Apache Tika perchè sono legato ad un'altra architettura ed il codice Java presente in rete per questa architettura non risolve il testo dei miei casi esclusivi anche smanettando le varie properties di PDFParserConfig..

Utilizzo quindi Apache PDFBox e Tesseract (https://colwil.com/how-to-extract-text-from-a-scanned-pdf-using-ocr-in-java/) che funziona con Java 8 ed estrae il testo correttamente da "untitled.pdf" :

This is a lot of 12 point text to test the
ocr code and see |If it works on all types
of file format.

The quick brown dog jumped over the
lazy fox. The quick brown dog jumped
over the lazy fox. The quick brown dog
jJumped over the lazy fox. The quick
brown dog jumped over the lazy fox.


Have a nice day



untitled.pdf
Immagine_nel_PDF.jpg

Matteo Mortari

unread,
Sep 26, 2022, 9:43:07 AM9/26/22
to Giuseppe Coniglio, JUG Torino - JVM User Group Torino
Ciao Giuseppe,
evidentemente c'è qualche problema di configurazione nel tuo ambiente, in quanto se noti il mio screenshot, sia manualmente che dei test, il testo viene riconosciuto integralmente (specie OCR nelle embedded images).

Se hai risolto in altro modo, sono contento per te.

Tenevo solo a dimostrare che la soluzione con Tika funziona, come da demo e screenshot precedentemente allegati.
Spero utile,
MM

Giuseppe Coniglio

unread,
Sep 26, 2022, 9:45:53 AM9/26/22
to Matteo Mortari, JUG Torino - JVM User Group Torino
Ciao Matteo,
Io ho Java 8 e quel codice su Github non gira
come faccio a farlo funzionare?
Ho visto il codice e non ho visto particolari settaggi , quindi ho cercato nell'api di Tika come riprodurre quel caso con del codice Java 8 compliant (senza usare Java 17 e Quarkus e api rest etc..) ma non ho trovato nulla
Se c'è un esempio in rete con un main semplice e le impostazioni di TIka da usare con Java 8 ben venga :-)
grazie ancora

Matteo Mortari

unread,
Sep 26, 2022, 9:48:19 AM9/26/22
to Giuseppe Coniglio, JUG Torino - JVM User Group Torino
Penso il demo funzioni anche con Java 11 facendo il cambio della property nel maven file, ma non sotto, semplicemente perché Quarkus IIRC parte da JDK11

Spero utile,
MM
Reply all
Reply to author
Forward
0 new messages