mindee 2.2.0 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +2 -0
- data/.rubocop.yml +2 -0
- data/.yardopts +1 -0
- data/CHANGELOG.md +36 -0
- data/README.md +29 -16
- data/bin/mindee.rb +23 -26
- data/docs/code_samples/bank_account_details_v1.txt +10 -5
- data/docs/code_samples/bank_account_details_v2.txt +19 -0
- data/docs/code_samples/bank_check_v1.txt +10 -5
- data/docs/code_samples/carte_vitale_v1.txt +10 -5
- data/docs/code_samples/custom_v1.txt +19 -10
- data/docs/code_samples/default.txt +10 -2
- data/docs/code_samples/expense_receipts_v4.txt +10 -5
- data/docs/code_samples/expense_receipts_v5.txt +11 -6
- data/docs/code_samples/financial_document_v1.txt +10 -5
- data/docs/code_samples/idcard_fr_v1.txt +10 -5
- data/docs/code_samples/invoice_splitter_v1_async.txt +66 -0
- data/docs/code_samples/invoices_v4.txt +10 -5
- data/docs/code_samples/license_plates_v1.txt +10 -5
- data/docs/code_samples/passport_v1.txt +10 -5
- data/docs/code_samples/proof_of_address_v1.txt +10 -5
- data/docs/ruby-api-builder.md +30 -31
- data/docs/ruby-getting-started.md +64 -23
- data/docs/ruby-invoice-ocr.md +70 -59
- data/docs/ruby-passport-ocr.md +49 -40
- data/docs/ruby-receipt-ocr.md +45 -32
- data/lib/mindee/client.rb +150 -148
- data/lib/mindee/geometry/min_max.rb +23 -0
- data/lib/mindee/geometry/point.rb +35 -0
- data/lib/mindee/geometry/polygon.rb +23 -0
- data/lib/mindee/geometry/quadrilateral.rb +45 -0
- data/lib/mindee/geometry/utils.rb +81 -0
- data/lib/mindee/geometry.rb +5 -116
- data/lib/mindee/http/endpoint.rb +123 -16
- data/lib/mindee/http.rb +3 -0
- data/lib/mindee/input/sources.rb +87 -73
- data/lib/mindee/parsing/common/api_response.rb +109 -0
- data/lib/mindee/parsing/common/document.rb +48 -0
- data/lib/mindee/parsing/common/error.rb +24 -0
- data/lib/mindee/parsing/common/inference.rb +43 -0
- data/lib/mindee/parsing/common/ocr/mvision_v1.rb +34 -0
- data/lib/mindee/parsing/common/ocr/ocr.rb +169 -0
- data/lib/mindee/parsing/common/ocr.rb +3 -0
- data/lib/mindee/parsing/common/orientation.rb +26 -0
- data/lib/mindee/parsing/common/page.rb +40 -0
- data/lib/mindee/parsing/common/prediction.rb +15 -0
- data/lib/mindee/parsing/common/product.rb +19 -0
- data/lib/mindee/parsing/common.rb +10 -0
- data/lib/mindee/parsing/custom/classification_field.rb +28 -0
- data/lib/mindee/parsing/custom/list_field.rb +76 -0
- data/lib/mindee/parsing/custom.rb +4 -0
- data/lib/mindee/parsing/standard/amount_field.rb +26 -0
- data/lib/mindee/parsing/standard/base_field.rb +104 -0
- data/lib/mindee/parsing/standard/classification_field.rb +16 -0
- data/lib/mindee/parsing/standard/company_registration_field.rb +21 -0
- data/lib/mindee/parsing/standard/date_field.rb +34 -0
- data/lib/mindee/parsing/standard/locale_field.rb +50 -0
- data/lib/mindee/parsing/standard/payment_details_field.rb +42 -0
- data/lib/mindee/parsing/standard/position_field.rb +44 -0
- data/lib/mindee/parsing/standard/tax_field.rb +108 -0
- data/lib/mindee/parsing/standard/text_field.rb +16 -0
- data/lib/mindee/parsing/standard.rb +12 -0
- data/lib/mindee/parsing.rb +3 -2
- data/lib/mindee/{input → pdf}/pdf_processing.rb +4 -32
- data/lib/mindee/pdf/pdf_tools.rb +34 -0
- data/lib/mindee/pdf.rb +3 -0
- data/lib/mindee/product/.rubocop.yml +5 -0
- data/lib/mindee/product/custom/custom_v1.rb +35 -0
- data/lib/mindee/product/custom/custom_v1_document.rb +60 -0
- data/lib/mindee/product/custom/custom_v1_page.rb +32 -0
- data/lib/mindee/product/eu/license_plate/license_plate_v1.rb +38 -0
- data/lib/mindee/product/eu/license_plate/license_plate_v1_document.rb +37 -0
- data/lib/mindee/product/eu/license_plate/license_plate_v1_page.rb +34 -0
- data/lib/mindee/product/financial_document/financial_document_v1.rb +36 -0
- data/lib/mindee/product/financial_document/financial_document_v1_document.rb +188 -0
- data/lib/mindee/product/financial_document/financial_document_v1_line_item.rb +90 -0
- data/lib/mindee/product/financial_document/financial_document_v1_page.rb +32 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v1.rb +38 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v1_document.rb +43 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v1_page.rb +34 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v2.rb +38 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v2_bban.rb +71 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v2_document.rb +58 -0
- data/lib/mindee/product/fr/bank_account_details/bank_account_details_v2_page.rb +34 -0
- data/lib/mindee/product/fr/carte_vitale/carte_vitale_v1.rb +38 -0
- data/lib/mindee/product/fr/carte_vitale/carte_vitale_v1_document.rb +52 -0
- data/lib/mindee/product/fr/carte_vitale/carte_vitale_v1_page.rb +34 -0
- data/lib/mindee/product/fr/id_card/id_card_v1.rb +38 -0
- data/lib/mindee/product/fr/id_card/id_card_v1_document.rb +82 -0
- data/lib/mindee/product/fr/id_card/id_card_v1_page.rb +48 -0
- data/lib/mindee/product/invoice/invoice_v4.rb +37 -0
- data/lib/mindee/product/invoice/invoice_v4_document.rb +212 -0
- data/lib/mindee/product/invoice/invoice_v4_line_item.rb +66 -0
- data/lib/mindee/product/invoice/invoice_v4_page.rb +32 -0
- data/lib/mindee/product/invoice_splitter/invoice_splitter_v1.rb +36 -0
- data/lib/mindee/product/invoice_splitter/invoice_splitter_v1_document.rb +65 -0
- data/lib/mindee/product/invoice_splitter/invoice_splitter_v1_page.rb +32 -0
- data/lib/mindee/product/passport/passport_v1.rb +36 -0
- data/lib/mindee/{parsing/prediction/fr/id_card/id_card_v1.rb → product/passport/passport_v1_document.rb} +45 -45
- data/lib/mindee/product/passport/passport_v1_page.rb +32 -0
- data/lib/mindee/product/proof_of_address/proof_of_address_v1.rb +36 -0
- data/lib/mindee/product/proof_of_address/proof_of_address_v1_document.rb +83 -0
- data/lib/mindee/product/proof_of_address/proof_of_address_v1_page.rb +32 -0
- data/lib/mindee/product/receipt/receipt_v4.rb +36 -0
- data/lib/mindee/product/receipt/receipt_v4_document.rb +86 -0
- data/lib/mindee/product/receipt/receipt_v4_page.rb +32 -0
- data/lib/mindee/product/receipt/receipt_v5.rb +36 -0
- data/lib/mindee/product/receipt/receipt_v5_document.rb +138 -0
- data/lib/mindee/product/receipt/receipt_v5_line_item.rb +69 -0
- data/lib/mindee/product/receipt/receipt_v5_page.rb +32 -0
- data/lib/mindee/product/us/bank_check/bank_check_v1.rb +38 -0
- data/lib/mindee/product/us/bank_check/bank_check_v1_document.rb +73 -0
- data/lib/mindee/product/us/bank_check/bank_check_v1_page.rb +34 -0
- data/lib/mindee/product.rb +16 -0
- data/lib/mindee/version.rb +2 -1
- data/lib/mindee.rb +3 -1
- metadata +87 -38
- data/docs/code_samples/shipping_containers_v1.txt +0 -14
- data/lib/mindee/document_config.rb +0 -60
- data/lib/mindee/parsing/document.rb +0 -31
- data/lib/mindee/parsing/error.rb +0 -22
- data/lib/mindee/parsing/inference.rb +0 -53
- data/lib/mindee/parsing/page.rb +0 -46
- data/lib/mindee/parsing/prediction/base.rb +0 -30
- data/lib/mindee/parsing/prediction/common_fields/amount.rb +0 -21
- data/lib/mindee/parsing/prediction/common_fields/base.rb +0 -72
- data/lib/mindee/parsing/prediction/common_fields/company_registration.rb +0 -17
- data/lib/mindee/parsing/prediction/common_fields/date.rb +0 -30
- data/lib/mindee/parsing/prediction/common_fields/locale.rb +0 -45
- data/lib/mindee/parsing/prediction/common_fields/payment_details.rb +0 -33
- data/lib/mindee/parsing/prediction/common_fields/position.rb +0 -39
- data/lib/mindee/parsing/prediction/common_fields/tax.rb +0 -40
- data/lib/mindee/parsing/prediction/common_fields/text.rb +0 -12
- data/lib/mindee/parsing/prediction/common_fields.rb +0 -11
- data/lib/mindee/parsing/prediction/custom/custom_v1.rb +0 -58
- data/lib/mindee/parsing/prediction/custom/fields.rb +0 -91
- data/lib/mindee/parsing/prediction/eu/license_plate/license_plate_v1.rb +0 -34
- data/lib/mindee/parsing/prediction/financial_document/financial_document_v1.rb +0 -237
- data/lib/mindee/parsing/prediction/financial_document/financial_document_v1_line_item.rb +0 -58
- data/lib/mindee/parsing/prediction/fr/bank_account_details/bank_account_details_v1.rb +0 -40
- data/lib/mindee/parsing/prediction/fr/carte_vitale/carte_vitale_v1.rb +0 -49
- data/lib/mindee/parsing/prediction/invoice/invoice_v4.rb +0 -212
- data/lib/mindee/parsing/prediction/invoice/invoice_v4_line_item.rb +0 -58
- data/lib/mindee/parsing/prediction/passport/passport_v1.rb +0 -121
- data/lib/mindee/parsing/prediction/proof_of_address/proof_of_address_v1.rb +0 -80
- data/lib/mindee/parsing/prediction/receipt/receipt_v4.rb +0 -87
- data/lib/mindee/parsing/prediction/receipt/receipt_v5.rb +0 -136
- data/lib/mindee/parsing/prediction/receipt/receipt_v5_line_item.rb +0 -37
- data/lib/mindee/parsing/prediction/shipping_container/shipping_container_v1.rb +0 -38
- data/lib/mindee/parsing/prediction/us/bank_check/bank_check_v1.rb +0 -70
- data/lib/mindee/parsing/prediction.rb +0 -15
data/lib/mindee/client.rb
CHANGED
|
@@ -1,33 +1,27 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
require_relative 'input'
|
|
4
|
-
require_relative '
|
|
5
|
-
require_relative '
|
|
6
|
-
require_relative 'parsing/
|
|
4
|
+
require_relative 'http'
|
|
5
|
+
require_relative 'product'
|
|
6
|
+
require_relative 'parsing/common/api_response'
|
|
7
7
|
|
|
8
8
|
module Mindee
|
|
9
|
-
#
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
# @param
|
|
13
|
-
def initialize(
|
|
14
|
-
@
|
|
15
|
-
@doc_configs = doc_configs
|
|
9
|
+
# Mindee API Client.
|
|
10
|
+
# See: https://developers.mindee.com/docs
|
|
11
|
+
class Client
|
|
12
|
+
# @param api_key [String]
|
|
13
|
+
def initialize(api_key: '')
|
|
14
|
+
@api_key = api_key
|
|
16
15
|
end
|
|
17
16
|
|
|
18
|
-
# Call prediction API on
|
|
17
|
+
# Call prediction API on a document and parse the results.
|
|
19
18
|
#
|
|
20
|
-
# @param
|
|
19
|
+
# @param input_source [Mindee::Input::Source::LocalInputSource, Mindee::Input::Source::UrlInputSource]
|
|
21
20
|
#
|
|
22
|
-
# @param
|
|
23
|
-
#
|
|
24
|
-
#
|
|
25
|
-
# @param account_name [String] For custom endpoints, your account or organization username on the API Builder.
|
|
26
|
-
# This is normally not required unless you have a custom endpoint which has the same name as a
|
|
27
|
-
# standard (off the shelf) endpoint.
|
|
28
|
-
# Do not set for standard (off the shelf) endpoints.
|
|
21
|
+
# @param endpoint [HTTP::Endpoint] Endpoint of the API
|
|
22
|
+
# Doesn't need to be set in the case of OTS APIs.
|
|
29
23
|
#
|
|
30
|
-
# @param
|
|
24
|
+
# @param all_words [Boolean] Whether to include the full text for each page.
|
|
31
25
|
# This performs a full OCR operation on the server and will increase response time.
|
|
32
26
|
#
|
|
33
27
|
# @param close_file [Boolean] Whether to `close()` the file after parsing it.
|
|
@@ -44,170 +38,178 @@ module Mindee
|
|
|
44
38
|
# @param cropper [Boolean] Whether to include cropper results for each page.
|
|
45
39
|
# This performs a cropping operation on the server and will increase response time.
|
|
46
40
|
#
|
|
47
|
-
# @return [Mindee::
|
|
41
|
+
# @return [Mindee::Parsing::Common::ApiResponse]
|
|
48
42
|
def parse(
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
43
|
+
input_source,
|
|
44
|
+
product_class,
|
|
45
|
+
endpoint: nil,
|
|
46
|
+
all_words: false,
|
|
53
47
|
close_file: true,
|
|
54
48
|
page_options: nil,
|
|
55
49
|
cropper: false
|
|
56
50
|
)
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
doc_config.predict(@input_doc, include_words, close_file, cropper)
|
|
60
|
-
end
|
|
61
|
-
|
|
62
|
-
private
|
|
63
|
-
|
|
64
|
-
# @param document_class [Mindee::Prediction::Prediction]
|
|
65
|
-
# @param endpoint_name [String]
|
|
66
|
-
def determine_endpoint_name(document_class, endpoint_name)
|
|
67
|
-
return document_class.name if document_class.name != Prediction::CustomV1.name
|
|
68
|
-
|
|
69
|
-
raise "endpoint_name is required when using #{document_class.name} class" if endpoint_name.empty?
|
|
70
|
-
|
|
71
|
-
endpoint_name
|
|
72
|
-
end
|
|
73
|
-
|
|
74
|
-
# @param document_class [Mindee::Prediction::Prediction]
|
|
75
|
-
# @param endpoint_name [String]
|
|
76
|
-
# @param account_name [String]
|
|
77
|
-
def find_doc_config(document_class, endpoint_name, account_name)
|
|
78
|
-
endpoint_name = determine_endpoint_name(document_class, endpoint_name)
|
|
79
|
-
|
|
80
|
-
found = []
|
|
81
|
-
@doc_configs.each_key do |conf|
|
|
82
|
-
found.push(conf) if conf[1] == endpoint_name
|
|
51
|
+
if input_source.is_a?(Mindee::Input::Source::LocalInputSource) && !page_options.nil? && input_source.pdf?
|
|
52
|
+
input_source.process_pdf(page_options)
|
|
83
53
|
end
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
config_key = [account_name, endpoint_name]
|
|
88
|
-
elsif found.length == 1
|
|
89
|
-
config_key = found[0]
|
|
90
|
-
else
|
|
91
|
-
usernames = found.map { |conf| conf[0] }
|
|
92
|
-
raise "Duplicate configuration detected.\n" \
|
|
93
|
-
"You specified the document '#{endpoint_name}' in your custom config.\n" \
|
|
94
|
-
"To avoid confusion, please add the 'account_name' attribute to " \
|
|
95
|
-
"the parse method, one of #{usernames}."
|
|
96
|
-
end
|
|
97
|
-
|
|
98
|
-
@doc_configs[config_key]
|
|
54
|
+
endpoint = initialize_endpoint(product_class) if endpoint.nil?
|
|
55
|
+
prediction = endpoint.predict(input_source, all_words, close_file, cropper)
|
|
56
|
+
Mindee::Parsing::Common::ApiResponse.new(product_class, prediction)
|
|
99
57
|
end
|
|
100
|
-
end
|
|
101
58
|
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
#
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
59
|
+
# Enqueue a document for async parsing
|
|
60
|
+
#
|
|
61
|
+
# @param input_source [Mindee::Input::Source::LocalInputSource, Mindee::Input::Source::UrlInputSource]
|
|
62
|
+
#
|
|
63
|
+
# @param endpoint [HTTP::Endpoint, nil] Endpoint of the API.
|
|
64
|
+
# Doesn't need to be set in the case of OTS APIs.
|
|
65
|
+
#
|
|
66
|
+
# @param all_words [Boolean] Whether to extract all the words on each page.
|
|
67
|
+
# This performs a full OCR operation on the server and will increase response time.
|
|
68
|
+
#
|
|
69
|
+
# @param close_file [Boolean] Whether to `close()` the file after parsing it.
|
|
70
|
+
# Set to false if you need to access the file after this operation.
|
|
71
|
+
#
|
|
72
|
+
# @param page_options [Hash, nil] Page cutting/merge options:
|
|
73
|
+
#
|
|
74
|
+
# * `:page_indexes` Zero-based list of page indexes.
|
|
75
|
+
# * `:operation` Operation to apply on the document, given the `page_indexes specified:
|
|
76
|
+
# * `:KEEP_ONLY` - keep only the specified pages, and remove all others.
|
|
77
|
+
# * `:REMOVE` - remove the specified pages, and keep all others.
|
|
78
|
+
# * `:on_min_pages` Apply the operation only if document has at least this many pages.
|
|
79
|
+
#
|
|
80
|
+
# @param cropper [Boolean] Whether to include cropper results for each page.
|
|
81
|
+
# This performs a cropping operation on the server and will increase response time.
|
|
82
|
+
#
|
|
83
|
+
# @return [Mindee::Parsing::Common::ApiResponse]
|
|
84
|
+
def enqueue(
|
|
85
|
+
input_source,
|
|
86
|
+
product_class,
|
|
87
|
+
endpoint: nil,
|
|
88
|
+
all_words: false,
|
|
89
|
+
close_file: true,
|
|
90
|
+
page_options: nil,
|
|
91
|
+
cropper: false
|
|
92
|
+
)
|
|
93
|
+
if input_source.is_a?(Mindee::Input::Source::LocalInputSource) && !page_options.nil? && input_source.pdf?
|
|
94
|
+
input_source.process_pdf(page_options)
|
|
95
|
+
end
|
|
96
|
+
endpoint = initialize_endpoint(product_class) if endpoint.nil?
|
|
97
|
+
Mindee::Parsing::Common::ApiResponse.new(product_class,
|
|
98
|
+
endpoint.predict_async(input_source, all_words, close_file, cropper))
|
|
110
99
|
end
|
|
111
100
|
|
|
112
|
-
#
|
|
113
|
-
#
|
|
114
|
-
# @param
|
|
115
|
-
#
|
|
116
|
-
#
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
101
|
+
# Parses a queued document
|
|
102
|
+
#
|
|
103
|
+
# @param endpoint [HTTP::Endpoint, nil] Endpoint of the API
|
|
104
|
+
# Doesn't need to be set in the case of OTS APIs.
|
|
105
|
+
#
|
|
106
|
+
# @param job_id [String] Id of the job (queue) to poll from
|
|
107
|
+
#
|
|
108
|
+
# @return [Mindee::Parsing::Common::ApiResponse]
|
|
109
|
+
def parse_queued(
|
|
110
|
+
job_id,
|
|
111
|
+
product_class,
|
|
112
|
+
endpoint: nil
|
|
121
113
|
)
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
HTTP::CustomEndpoint.new(account_name, endpoint_name, version, @api_key)
|
|
125
|
-
)
|
|
126
|
-
self
|
|
114
|
+
endpoint = initialize_endpoint(product_class) if endpoint.nil?
|
|
115
|
+
Mindee::Parsing::Common::ApiResponse.new(product_class, endpoint.parse_async(job_id))
|
|
127
116
|
end
|
|
128
117
|
|
|
129
118
|
# Load a document from an absolute path, as a string.
|
|
130
119
|
# @param input_path [String] Path of file to open
|
|
131
|
-
# @return [Mindee::
|
|
132
|
-
def
|
|
133
|
-
|
|
134
|
-
DocumentClient.new(doc, @doc_configs)
|
|
120
|
+
# @return [Mindee::Input::Source::PathInputSource]
|
|
121
|
+
def source_from_path(input_path)
|
|
122
|
+
Input::Source::PathInputSource.new(input_path)
|
|
135
123
|
end
|
|
136
124
|
|
|
137
125
|
# Load a document from raw bytes.
|
|
138
126
|
# @param input_bytes [String] Encoding::BINARY byte input
|
|
139
127
|
# @param filename [String] The name of the file (without the path)
|
|
140
|
-
# @return [Mindee::
|
|
141
|
-
def
|
|
142
|
-
|
|
143
|
-
DocumentClient.new(doc, @doc_configs)
|
|
128
|
+
# @return [Mindee::Input::Source::BytesInputSource]
|
|
129
|
+
def source_from_bytes(input_bytes, filename)
|
|
130
|
+
Input::Source::BytesInputSource.new(input_bytes, filename)
|
|
144
131
|
end
|
|
145
132
|
|
|
146
133
|
# Load a document from a base64 encoded string.
|
|
147
134
|
# @param base64_string [String] Input to parse as base64 string
|
|
148
135
|
# @param filename [String] The name of the file (without the path)
|
|
149
|
-
# @return [Mindee::
|
|
150
|
-
def
|
|
151
|
-
|
|
152
|
-
DocumentClient.new(doc, @doc_configs)
|
|
136
|
+
# @return [Mindee::Input::Source::Base64InputSource]
|
|
137
|
+
def source_from_b64string(base64_string, filename)
|
|
138
|
+
Input::Source::Base64InputSource.new(base64_string, filename)
|
|
153
139
|
end
|
|
154
140
|
|
|
155
141
|
# Load a document from a normal Ruby `File`.
|
|
156
142
|
# @param input_file [File] Input file handle
|
|
157
143
|
# @param filename [String] The name of the file (without the path)
|
|
158
|
-
# @return [Mindee::
|
|
159
|
-
def
|
|
160
|
-
|
|
161
|
-
|
|
144
|
+
# @return [Mindee::Input::Source::FileInputSource]
|
|
145
|
+
def source_from_file(input_file, filename)
|
|
146
|
+
Input::Source::FileInputSource.new(input_file, filename)
|
|
147
|
+
end
|
|
148
|
+
|
|
149
|
+
# Load a document from a secure remote source (HTTPS).
|
|
150
|
+
# @param url [String] Url of the file
|
|
151
|
+
# @return [Mindee::Input::Source::UrlInputSource]
|
|
152
|
+
def source_from_url(url)
|
|
153
|
+
Input::Source::UrlInputSource.new(url)
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
# Creates a custom endpoint with the given values.
|
|
157
|
+
# Do not set for standard (off the shelf) endpoints.
|
|
158
|
+
#
|
|
159
|
+
# @param endpoint_name [String] For custom endpoints, the "API name" field in the "Settings" page of the
|
|
160
|
+
# API Builder. Do not set for standard (off the shelf) endpoints.
|
|
161
|
+
#
|
|
162
|
+
# @param account_name [String] For custom endpoints, your account or organization username on the API Builder.
|
|
163
|
+
# This is normally not required unless you have a custom endpoint which has the same name as a
|
|
164
|
+
# standard (off the shelf) endpoint.
|
|
165
|
+
# @param version [String] For custom endpoints, version of the product
|
|
166
|
+
# @return [Mindee::HTTP::Endpoint]
|
|
167
|
+
def create_endpoint(endpoint_name: '', account_name: '', version: '')
|
|
168
|
+
initialize_endpoint(Mindee::Product::Custom::CustomV1, endpoint_name: endpoint_name, account_name: account_name,
|
|
169
|
+
version: version)
|
|
162
170
|
end
|
|
163
171
|
|
|
164
172
|
private
|
|
165
173
|
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
174
|
+
# Creates an endpoint with the given values. Raises an error if the endpoint is invalid.
|
|
175
|
+
# @param product_class [Mindee::Product] class of the product
|
|
176
|
+
#
|
|
177
|
+
# @param endpoint_name [String] For custom endpoints, the "API name" field in the "Settings" page of the
|
|
178
|
+
# API Builder. Do not set for standard (off the shelf) endpoints.
|
|
179
|
+
#
|
|
180
|
+
# @param account_name [String] For custom endpoints, your account or organization username on the API Builder.
|
|
181
|
+
# This is normally not required unless you have a custom endpoint which has the same name as a
|
|
182
|
+
# standard (off the shelf) endpoint.
|
|
183
|
+
# @param version [String] For custom endpoints, version of the product.
|
|
184
|
+
# @return [Mindee::HTTP::Endpoint]
|
|
185
|
+
def initialize_endpoint(product_class, endpoint_name: '', account_name: '', version: '')
|
|
186
|
+
if (endpoint_name.nil? || endpoint_name.empty?) && product_class == Mindee::Product::Custom::CustomV1
|
|
187
|
+
raise 'Missing argument endpoint_name when using custom class'
|
|
188
|
+
end
|
|
189
|
+
|
|
190
|
+
endpoint_name = fix_endpoint_name(product_class, endpoint_name)
|
|
191
|
+
account_name = fix_account_name(account_name)
|
|
192
|
+
version = fix_version(product_class, version)
|
|
193
|
+
HTTP::Endpoint.new(account_name, endpoint_name, version, api_key: @api_key)
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
def fix_endpoint_name(product_class, endpoint_name)
|
|
197
|
+
return product_class.endpoint_name if endpoint_name.nil? || endpoint_name.empty?
|
|
198
|
+
|
|
199
|
+
endpoint_name
|
|
171
200
|
end
|
|
172
201
|
|
|
173
|
-
def
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
Prediction::ReceiptV4, 'expense_receipts', '4'
|
|
185
|
-
)
|
|
186
|
-
@doc_configs[['mindee', Prediction::ReceiptV5.name]] = standard_document_config(
|
|
187
|
-
Prediction::ReceiptV5, 'expense_receipts', '5'
|
|
188
|
-
)
|
|
189
|
-
@doc_configs[['mindee', Prediction::PassportV1.name]] = standard_document_config(
|
|
190
|
-
Prediction::PassportV1, 'passport', '1'
|
|
191
|
-
)
|
|
192
|
-
@doc_configs[['mindee', Prediction::EU::LicensePlateV1.name]] = standard_document_config(
|
|
193
|
-
Prediction::EU::LicensePlateV1, 'license_plates', '1'
|
|
194
|
-
)
|
|
195
|
-
@doc_configs[['mindee', Prediction::ShippingContainerV1.name]] = standard_document_config(
|
|
196
|
-
Prediction::ShippingContainerV1, 'shipping_containers', '1'
|
|
197
|
-
)
|
|
198
|
-
@doc_configs[['mindee', Prediction::US::BankCheckV1.name]] = standard_document_config(
|
|
199
|
-
Prediction::US::BankCheckV1, 'bank_check', '1'
|
|
200
|
-
)
|
|
201
|
-
@doc_configs[['mindee', Prediction::FR::BankAccountDetailsV1.name]] = standard_document_config(
|
|
202
|
-
Prediction::FR::BankAccountDetailsV1, 'bank_account_details', '1'
|
|
203
|
-
)
|
|
204
|
-
@doc_configs[['mindee', Prediction::FR::CarteVitaleV1.name]] = standard_document_config(
|
|
205
|
-
Prediction::FR::CarteVitaleV1, 'carte_vitale', '1'
|
|
206
|
-
)
|
|
207
|
-
@doc_configs[['mindee', Prediction::FR::IdCardV1.name]] = standard_document_config(
|
|
208
|
-
Prediction::FR::IdCardV1, 'idcard_fr', '1'
|
|
209
|
-
)
|
|
210
|
-
self
|
|
202
|
+
def fix_account_name(account_name)
|
|
203
|
+
return 'mindee' if account_name.nil? || account_name.empty?
|
|
204
|
+
|
|
205
|
+
account_name
|
|
206
|
+
end
|
|
207
|
+
|
|
208
|
+
def fix_version(product_class, version)
|
|
209
|
+
return version unless version.nil? || version.empty?
|
|
210
|
+
return '1' if product_class.endpoint_version.nil? || product_class.endpoint_version.empty?
|
|
211
|
+
|
|
212
|
+
product_class.endpoint_version
|
|
211
213
|
end
|
|
212
214
|
end
|
|
213
215
|
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Mindee
|
|
4
|
+
# Various helper functions & classes for geometry.
|
|
5
|
+
module Geometry
|
|
6
|
+
# A set of minimum and maximum values.
|
|
7
|
+
class MinMax
|
|
8
|
+
# Minimum
|
|
9
|
+
# @return [Float]
|
|
10
|
+
attr_reader :min
|
|
11
|
+
# Maximum
|
|
12
|
+
# @return [Float]
|
|
13
|
+
attr_reader :max
|
|
14
|
+
|
|
15
|
+
# @param min [Float]
|
|
16
|
+
# @param max [Float]
|
|
17
|
+
def initialize(min, max)
|
|
18
|
+
@min = min
|
|
19
|
+
@max = max
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Mindee
|
|
4
|
+
# Various helper functions for geometry.
|
|
5
|
+
module Geometry
|
|
6
|
+
# A relative set of coordinates (X, Y) on the document.
|
|
7
|
+
class Point
|
|
8
|
+
# @return [Float]
|
|
9
|
+
attr_accessor :x
|
|
10
|
+
# @return [Float]
|
|
11
|
+
attr_accessor :y
|
|
12
|
+
|
|
13
|
+
# @param x [Float]
|
|
14
|
+
# @param y [Float]
|
|
15
|
+
# rubocop:disable Naming/MethodParameterName
|
|
16
|
+
def initialize(x, y)
|
|
17
|
+
@x = x
|
|
18
|
+
@y = y
|
|
19
|
+
end
|
|
20
|
+
# rubocop:enable Naming/MethodParameterName
|
|
21
|
+
|
|
22
|
+
# @return [Float]
|
|
23
|
+
def [](key)
|
|
24
|
+
case key
|
|
25
|
+
when 0
|
|
26
|
+
@x
|
|
27
|
+
when 1
|
|
28
|
+
@y
|
|
29
|
+
else
|
|
30
|
+
throw '0 or 1 only'
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Mindee
|
|
4
|
+
# Various helper functions & classes for geometry.
|
|
5
|
+
module Geometry
|
|
6
|
+
# Contains any number of vertex coordinates (Points).
|
|
7
|
+
class Polygon < Array
|
|
8
|
+
# Get the central point (centroid) of the polygon.
|
|
9
|
+
# @return [Mindee::Geometry::Point]
|
|
10
|
+
def centroid
|
|
11
|
+
Geometry.get_centroid(self)
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
# Determine if the Point is in the Polygon's Y-axis.
|
|
15
|
+
# @param point [Mindee::Geometry::Point]
|
|
16
|
+
# @return [Boolean]
|
|
17
|
+
def point_in_y?(point)
|
|
18
|
+
min_max = Geometry.get_min_max_y(self)
|
|
19
|
+
min_max.min <= point.y && point.y <= min_max.max
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Mindee
|
|
4
|
+
# Various helper functions & classes for geometry.
|
|
5
|
+
module Geometry
|
|
6
|
+
# Contains exactly 4 relative vertices coordinates (Points).
|
|
7
|
+
class Quadrilateral
|
|
8
|
+
# @return [Mindee::Geometry::Point]
|
|
9
|
+
attr_accessor :top_left
|
|
10
|
+
# @return [Mindee::Geometry::Point]
|
|
11
|
+
attr_accessor :top_right
|
|
12
|
+
# @return [Mindee::Geometry::Point]
|
|
13
|
+
attr_accessor :bottom_right
|
|
14
|
+
# @return [Mindee::Geometry::Point]
|
|
15
|
+
attr_accessor :bottom_left
|
|
16
|
+
|
|
17
|
+
# @param top_left [Mindee::Geometry::Point]
|
|
18
|
+
# @param top_right [Mindee::Geometry::Point]
|
|
19
|
+
# @param bottom_right [Mindee::Geometry::Point]
|
|
20
|
+
# @param bottom_left [Mindee::Geometry::Point]
|
|
21
|
+
def initialize(top_left, top_right, bottom_right, bottom_left)
|
|
22
|
+
@top_left = top_left
|
|
23
|
+
@top_right = top_right
|
|
24
|
+
@bottom_right = bottom_right
|
|
25
|
+
@bottom_left = bottom_left
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
# @return [Mindee::Geometry::Point]
|
|
29
|
+
def [](key)
|
|
30
|
+
case key
|
|
31
|
+
when 0
|
|
32
|
+
@top_left
|
|
33
|
+
when 1
|
|
34
|
+
@top_right
|
|
35
|
+
when 2
|
|
36
|
+
@bottom_right
|
|
37
|
+
when 3
|
|
38
|
+
@bottom_left
|
|
39
|
+
else
|
|
40
|
+
throw '0, 1, 2, 3 only'
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
end
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Mindee
|
|
4
|
+
# Various helper functions for geometry.
|
|
5
|
+
module Geometry
|
|
6
|
+
# Transform a prediction into a Quadrilateral.
|
|
7
|
+
# @param prediction [Hash]
|
|
8
|
+
# @return [Mindee::Geometry::Quadrilateral]
|
|
9
|
+
def self.quadrilateral_from_prediction(prediction)
|
|
10
|
+
throw "Prediction must have exactly 4 points, found #{prediction.size}" if prediction.size != 4
|
|
11
|
+
|
|
12
|
+
Quadrilateral.new(
|
|
13
|
+
Point.new(prediction[0][0], prediction[0][1]),
|
|
14
|
+
Point.new(prediction[1][0], prediction[1][1]),
|
|
15
|
+
Point.new(prediction[2][0], prediction[2][1]),
|
|
16
|
+
Point.new(prediction[3][0], prediction[3][1])
|
|
17
|
+
)
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
# Transform a prediction into a Polygon.
|
|
21
|
+
# @param prediction [Hash]
|
|
22
|
+
# @return [Mindee::Geometry::Polygon]
|
|
23
|
+
def self.polygon_from_prediction(prediction)
|
|
24
|
+
polygon = Polygon.new
|
|
25
|
+
return polygon if prediction.nil?
|
|
26
|
+
|
|
27
|
+
prediction.each do |point|
|
|
28
|
+
polygon << Point.new(point[0], point[1])
|
|
29
|
+
end
|
|
30
|
+
polygon
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
# Gets the points of a bounding box for a given set of points
|
|
34
|
+
# @param vertices [Array<Mindee::Geometry::Point>]
|
|
35
|
+
# @return [Array<Float>]
|
|
36
|
+
def self.get_bbox(vertices)
|
|
37
|
+
x_coords = vertices.map(&:x)
|
|
38
|
+
y_coords = vertices.map(&:y)
|
|
39
|
+
[x_coords.min, y_coords.min, x_coords.max, y_coords.max]
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
# Creates the bounding bounding box for a given set of points
|
|
43
|
+
# @param vertices [Array<Mindee::Geometry::Point>]
|
|
44
|
+
# @return [Mindee::Geometry::Quadrilateral]
|
|
45
|
+
def self.get_bounding_box(vertices)
|
|
46
|
+
x_min, y_min, x_max, y_max = get_bbox(vertices)
|
|
47
|
+
Quadrilateral.new(
|
|
48
|
+
Point.new(x_min, y_min),
|
|
49
|
+
Point.new(x_max, y_min),
|
|
50
|
+
Point.new(x_max, y_max),
|
|
51
|
+
Point.new(x_min, y_max)
|
|
52
|
+
)
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# Get the central point (centroid) given a sequence of points.
|
|
56
|
+
# @param points [Array<Mindee::Geometry::Point>]
|
|
57
|
+
# @return [Mindee::Geometry::Point]
|
|
58
|
+
def self.get_centroid(points)
|
|
59
|
+
vertices_count = points.size
|
|
60
|
+
x_sum = points.map(&:x).sum
|
|
61
|
+
y_sum = points.map(&:y).sum
|
|
62
|
+
Point.new(x_sum / vertices_count, y_sum / vertices_count)
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
# Get the maximum and minimum Y value given a sequence of points.
|
|
66
|
+
# @param points [Array<Mindee::Geometry::Point>]
|
|
67
|
+
# @return [Mindee::Geometry::MinMax]
|
|
68
|
+
def self.get_min_max_y(points)
|
|
69
|
+
coords = points.map(&:y)
|
|
70
|
+
MinMax.new(coords.min, coords.max)
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
# Get the maximum and minimum X value given a sequence of points.
|
|
74
|
+
# @param points [Array<Mindee::Geometry::Point>]
|
|
75
|
+
# @return [Mindee::Geometry::MinMax]
|
|
76
|
+
def self.get_min_max_x(points)
|
|
77
|
+
coords = points.map(&:x)
|
|
78
|
+
MinMax.new(coords.min, coords.max)
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|