ひよこになりたい

Programming Server Network Security and so on

Python3でOCR(pytesseract)を使えるようにする

CTFを解いていると時々OCRが欲しい場面が出てくるのですが、Python用のOCRライブラリはPython2系列のものばかりで、Python3でのOCRライブラリは検索してもヒットしません。

私はPython3系列派なので、どうしてもOCRをPython3で使いたい!ということで、Python2用のOCRライブラリであるpytesseractをPython3で使えるように書きなおしてみたのでメモしておきます。

意外に簡単に使えるようになったので、使いたい人は試してみてね。

pytesseractはpipで入れることができます。

# pip install pytesseract

しかし、pip3を使用しても入るのはPython2系列用のコードで、Python3では動きません。。(たまにあるよね)

ということで、pipで入れたpytesseract(ver0.1)に修正を加えます

# pip install pytesseract
$ cd /Path/to/site-packages
$ cd pytesseract
$ vim pytesseract.py

/Path/to/site-packagesの部分はPython3のsite-packageを指定してください。私はMacを使っているので、/Library/Frameworks/Python.framework/Versions/3.3/lib/python3.3/site-packages/にありました。

以下の部分に修正を加えます。先に2to3コマンドで変換しておくと少しだけラクになるかも。

$ 2to3 -w pytesseract

変更箇所はこちら(diff)

47,48c47,48
< import Image
< import StringIO
---
> from PIL import Image
> import io
51a52
> import tempfile
102,103c103,104
< sys.stderr = StringIO.StringIO()
< return os.tempnam(None, 'tess_')
---
> sys.stderr = io.StringIO()
> return tempfile.mkstemp("", 'tess_')
120,122c121,122
<
< input_file_name = '%s.bmp' % tempnam()
< output_file_name_base = tempnam()
---
> input_file_name = '{0}.bmp'.format(tempnam()[1])
> output_file_name_base = tempnam()[1]
124c124
< output_file_name = '%s.txt' % output_file_name_base
---
> output_file_name = '{0}.txt'.format(output_file_name_base)
126c126
< output_file_name = '%s.box' % output_file_name_base
---
> output_file_name = '{0}.box'.format(output_file_name_base)
136c138
< f = file(output_file_name)
---
> f = open(output_file_name)
151c153
< sys.stderr.write('ERROR: Could not open file "%s"\n' % filename)
---
> sys.stderr.write('ERROR: Could not open file "{0}"\n'.format(filename))
153c155
< print image_to_string(image)
---
> print(image_to_string(image))
160c162
< sys.stderr.write('ERROR: Could not open file "%s"\n' % filename)
---
> sys.stderr.write('ERROR: Could not open file "{0}"\n'.format(filename))
162c164
< print image_to_string(image, lang=lang)
---
>  print(image_to_string(image, lang=lang))

< の行を > に置き換えです。

保存して終わり。実行してみると

>>> import pytesseract
>>> from PIL import Image
>>> img = Image.open("/Users/hinanawi/tenshi.png")
>>> message = pytesseract.image_to_string(img)
>>> print(message)
'tenshityanaishiteru'

こんな感じに出力できます:)

% 追記:pyocrはPython3対応らしいです。