Amazon Textractが面白かったので、.Net Core環境で使ってみました。
2019/06/12現在まだ日本語の記事が全然ない(.Netにいたっては英語の記事もぱっと見た感じ無さそう)ので、誰かの参考になれば嬉しいな。
参考にしたAmazonのDocumentはこちら。
https://docs.aws.amazon.com/ja_jp/textract/latest/dg/how-it-works-analyzing.html
基本的に前回のDetect textと同じですが、表の結果が格納されている形式が少し難しかったので
別の記事にしました。
表の中身はBlockTypeがCELLのBlockに格納されているので、そこを見れば良いです。
だけどCELLにはTEXTが入ってないので、表の中身は子要素のIDから該当するBlockを引っ張ってくる必要があります。
インデクサでIDを引数にとってダイレクトに要素をとってこれる方法があると思って探したけど、ないんだよなぁ。
public List<List<string>> table = new List<List<string>>();
public IActionResult OnPost(IFormFile Targetfile)
using (var client = new AmazonTextractClient(awsCredentials, this.awsOptions.Region))
{
//Document処理用のバッファ用意
Stream s = Targetfile.OpenReadStream();
byte[] file = new byte[Targetfile.Length];
MemoryStream ms = new MemoryStream(file);
s.CopyTo(ms);
//AWSに解析させるDocumentオブジェクトの準備
Document doc = new Document();
doc.Bytes = ms;
//リクエストの作成
DetectDocumentTextRequest req = new DetectDocumentTextRequest();
req.Document = doc;
req.FeatureTypes.Add("TABLES"); //表を解析するときはこれが必要です。
//解析の実行
var response = client.AnalyzeDocumentAsync(req);
response.Wait();
//結果はメンバ変数として定義したtableに格納されます。
foreach (var b in response.Result.Blocks)
{
if (b.BlockType == BlockType.CELL)
{
foreach (var r in b.Relationships)
{
Block word = response.Result.Blocks.Find(delegate(Block block) {
return block.Id == r.Ids[0];
});
if (table.Count < b.RowIndex) table.Add(new List<string>());
table[b.RowIndex-1].Add(word.Text);
}
}
}
※例によってエラー処理とか書いてません。気をつけてください。あと、表の取得の仕方もサンプル用に簡略化してます。ほんとは表が複数ある場合とかいろいろな場合を考慮する必要があります。
ちなみにハマったポイントとしては、このリンクにあるこの画像をキャプチャしてテストしてたんですけど、私の環境ではTextractでTableとして認識されませんでしたww(2019/6/12現在)
Documentのどこかに書いてあったのですが、それなりに高解像度である必要があるみたいです。