plagiarism-checker 1.0.0 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rubocop.yml +2 -2
- data/Gemfile +4 -4
- data/LICENSE.txt +21 -21
- data/Rakefile +2 -2
- data/bin/console +7 -7
- data/bin/setup +8 -8
- data/example_async.rb +50 -0
- data/example_syncronized.rb +73 -0
- data/lib/copyleaks_api.rb +2 -1
- data/lib/copyleaks_api/Models/ResultRecord.rb +58 -0
- data/lib/copyleaks_api/api.rb +64 -7
- data/lib/copyleaks_api/config.rb +3 -1
- data/lib/copyleaks_api/copyleaks_cloud.rb +54 -30
- data/lib/copyleaks_api/copyleaks_process.rb +44 -48
- data/lib/copyleaks_api/version.rb +3 -3
- metadata +6 -5
- data/examples/main.rb +0 -60
- data/lib/copyleaks_api/language.rb +0 -61
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a856007784b1580e5c8ca554fc9a22ad847f854e
|
4
|
+
data.tar.gz: 7b3342e7458536584f404273815d4407c01fc31a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9262172bde5a793f4edf4cbe615520c5a23737cfd410fc364aaca2ed3da7cdee1c916b656133e240151e1a090ff7c47992d0654c8260f4b21c2ab80597ae1bbd
|
7
|
+
data.tar.gz: b082d51155d016a2a223f784ccdf80b928eb9c8803a62c9da020f7128d0ec663d68a9a348b1cf298c49bbb23baf692b1afcbc1922ee7a83f7a3f54c9f8650ae2
|
data/.rubocop.yml
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
Metrics/LineLength:
|
2
|
-
Max: 120
|
1
|
+
Metrics/LineLength:
|
2
|
+
Max: 120
|
data/Gemfile
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
source 'https://rubygems.org'
|
2
|
-
|
3
|
-
# Specify your gem's dependencies in copyleaks_api.gemspec
|
4
|
-
gemspec
|
1
|
+
source 'https://rubygems.org'
|
2
|
+
|
3
|
+
# Specify your gem's dependencies in copyleaks_api.gemspec
|
4
|
+
gemspec
|
data/LICENSE.txt
CHANGED
@@ -1,21 +1,21 @@
|
|
1
|
-
The MIT License(MIT)
|
2
|
-
|
3
|
-
Copyright(c) 2016 Copyleaks LTD (https://copyleaks.com)
|
4
|
-
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
-
of this software and associated documentation files (the "Software"), to deal
|
7
|
-
in the Software without restriction, including without limitation the rights
|
8
|
-
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
-
copies of the Software, and to permit persons to whom the Software is
|
10
|
-
furnished to do so, subject to the following conditions:
|
11
|
-
|
12
|
-
The above copyright notice and this permission notice shall be included in all
|
13
|
-
copies or substantial portions of the Software.
|
14
|
-
|
15
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
-
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
-
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
-
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
-
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
-
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
21
|
-
SOFTWARE.
|
1
|
+
The MIT License(MIT)
|
2
|
+
|
3
|
+
Copyright(c) 2016 Copyleaks LTD (https://copyleaks.com)
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
13
|
+
copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
21
|
+
SOFTWARE.
|
data/Rakefile
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
require "bundler/gem_tasks"
|
2
|
-
task :default => :spec
|
1
|
+
require "bundler/gem_tasks"
|
2
|
+
task :default => :spec
|
data/bin/console
CHANGED
@@ -1,7 +1,7 @@
|
|
1
|
-
#!/usr/bin/env ruby
|
2
|
-
|
3
|
-
require 'bundler/setup'
|
4
|
-
require 'copyleaks_api'
|
5
|
-
|
6
|
-
require 'irb'
|
7
|
-
IRB.start
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'bundler/setup'
|
4
|
+
require 'copyleaks_api'
|
5
|
+
|
6
|
+
require 'irb'
|
7
|
+
IRB.start
|
data/bin/setup
CHANGED
@@ -1,8 +1,8 @@
|
|
1
|
-
#!/usr/bin/env bash
|
2
|
-
set -euo pipefail
|
3
|
-
IFS=$'\n\t'
|
4
|
-
set -vx
|
5
|
-
|
6
|
-
bundle install
|
7
|
-
|
8
|
-
# Do any other automated setup that you need to do here
|
1
|
+
#!/usr/bin/env bash
|
2
|
+
set -euo pipefail
|
3
|
+
IFS=$'\n\t'
|
4
|
+
set -vx
|
5
|
+
|
6
|
+
bundle install
|
7
|
+
|
8
|
+
# Do any other automated setup that you need to do here
|
data/example_async.rb
ADDED
@@ -0,0 +1,50 @@
|
|
1
|
+
# Import the module
|
2
|
+
require_relative './lib/copyleaks_api'
|
3
|
+
# If you installed this library using gem install use this import
|
4
|
+
#require 'copyleaks_api'
|
5
|
+
|
6
|
+
# In order to use this API you need to register to Copyleaks at https://copyleaks.com/account/register
|
7
|
+
# Login using your account email and account key provided at api.copyleaks.com dashboards.
|
8
|
+
email = "<--YOUR-EMAIL-->"
|
9
|
+
api_key = "<--API-KEY-->"
|
10
|
+
# There are currently 3 available products - :businesses, :education, :websites
|
11
|
+
cloud = CopyleaksApi::CopyleaksCloud.new(email, api_key, :businesses)
|
12
|
+
|
13
|
+
# Check your account balance
|
14
|
+
puts "You have #{cloud.get_credits_balance} credits"
|
15
|
+
|
16
|
+
# Process Configuration
|
17
|
+
CopyleaksApi::Config.sandbox_mode = true # Sandbox mode will not consume any credits while returning dummy results
|
18
|
+
CopyleaksApi::Config.http_callback = 'http://yoursite.here/callback/completion/{PID}'
|
19
|
+
# For testing purposes you can use http://requestb.in
|
20
|
+
|
21
|
+
#CopyleaksApi::Config
|
22
|
+
# For more information: https://api.copyleaks.com/GeneralDocumentation/RequestHeaders
|
23
|
+
# Available configuration options:
|
24
|
+
#CopyleaksApi::Config do |config|
|
25
|
+
# config.sanbox_mode = true
|
26
|
+
# config.allow_partial_scan = true
|
27
|
+
# config.http_callback = 'http://yoursite.here/callback/{PID}'
|
28
|
+
# config.in_progress_result = 'http://yoursite.here/callback/results/{PID}'
|
29
|
+
# config.email_callback = 'your@email.com'
|
30
|
+
# config.custom_fields = { some_field: 'and its value' }
|
31
|
+
# config.compare_only = true # Only while using create-by-files
|
32
|
+
#end
|
33
|
+
|
34
|
+
|
35
|
+
# Create a process using one of the optional methods
|
36
|
+
# Available methods: create_by_url, create_by_text, create_by_file, create_by_files and create_by_ocr.
|
37
|
+
# For more information see our documentation on http://api.copyleaks.com/
|
38
|
+
begin
|
39
|
+
process = cloud.create_by_url("https://microsoft.com/")
|
40
|
+
#process = cloud.create_by_text("THE TEXT YOU WISH TO SCAN")
|
41
|
+
#process = cloud.create_by_file(path_to_file)
|
42
|
+
#processes = cloud.create_by_files(files_paths)
|
43
|
+
#process = cloud.create_by_ocr(path_to_image, language: 'en') # Requires the language of the text.
|
44
|
+
# Use cloud.get_ocr_languages to get the supported langauges.
|
45
|
+
# or take a look at this page: https://api.copyleaks.com/GeneralDocumentation/OcrLanguagesList
|
46
|
+
|
47
|
+
puts "Your scan(#{process.process_id}) was created successfully. We will trigger the callback soon."
|
48
|
+
rescue Exception => ex
|
49
|
+
puts "Failed to create new process with exception: #{ex}"
|
50
|
+
end
|
@@ -0,0 +1,73 @@
|
|
1
|
+
# Import the module
|
2
|
+
require_relative './lib/copyleaks_api'
|
3
|
+
# If you installed this library using gem install use this import
|
4
|
+
#require 'copyleaks_api'
|
5
|
+
|
6
|
+
# In order to use this API you need to register to Copyleaks at https://copyleaks.com/account/register
|
7
|
+
# Login using your account email and account key provided at api.copyleaks.com dashboards.
|
8
|
+
email = "<--YOUR-EMAIL-->"
|
9
|
+
api_key = "<--API-KEY-->"
|
10
|
+
# There are currently 3 available products - :businesses, :education, :websites
|
11
|
+
cloud = CopyleaksApi::CopyleaksCloud.new(email, api_key, :businesses)
|
12
|
+
|
13
|
+
# Check your account balance
|
14
|
+
puts "You have #{cloud.get_credits_balance} credits"
|
15
|
+
|
16
|
+
# Process Configuration
|
17
|
+
CopyleaksApi::Config.sandbox_mode = true # Sandbox mode will not consume any credits while returning fake results
|
18
|
+
#CopyleaksApi::Config
|
19
|
+
# For more information: https://api.copyleaks.com/GeneralDocumentation/RequestHeaders
|
20
|
+
# Available configuration options:
|
21
|
+
#CopyleaksApi::Config do |config|
|
22
|
+
# config.sanbox_mode = true
|
23
|
+
# config.allow_partial_scan = true
|
24
|
+
# config.http_callback = 'http://yoursite.here'
|
25
|
+
# config.in_progress_result = 'http://yoursite.here'
|
26
|
+
# config.email_callback = 'your@email.com'
|
27
|
+
# config.custom_fields = { some_field: 'and its value' }
|
28
|
+
# config.compare_only = true # Only while using create-by-files
|
29
|
+
#end
|
30
|
+
|
31
|
+
|
32
|
+
# Create a process using one of the optional methods
|
33
|
+
# Available methods: create_by_url, create_by_text, create_by_file, create_by_files and create_by_ocr.
|
34
|
+
# For more information see our documentation on http://api.copyleaks.com/
|
35
|
+
process = cloud.create_by_url("https://copyleaks.com/")
|
36
|
+
#process = cloud.create_by_text("THE TEXT YOU WISH TO SCAN")
|
37
|
+
#process = cloud.create_by_file(path_to_file)
|
38
|
+
#processes = cloud.create_by_files(files_paths)
|
39
|
+
#process = cloud.create_by_ocr(path_to_image, language: 'en') # Requires the language of the text.
|
40
|
+
# Use cloud.get_ocr_languages to get the supported langauges.
|
41
|
+
# or take a look at this page: https://api.copyleaks.com/GeneralDocumentation/OcrLanguagesList
|
42
|
+
|
43
|
+
puts "Processing Started"
|
44
|
+
|
45
|
+
# Now we will check the status of the process until its done
|
46
|
+
# **We highly recommend to use the http_callback option at the config in order to get a callback once the process is finished**
|
47
|
+
# For more info visit: https://api.copyleaks.com/GeneralDocumentation/RequestHeaders
|
48
|
+
while process.processing?
|
49
|
+
sleep(1)
|
50
|
+
process.update_status
|
51
|
+
puts "#"*(process.progress/2) + "-"*(50 - process.progress/2) + "#{process.progress}%"
|
52
|
+
end
|
53
|
+
|
54
|
+
puts "Processing Ended"
|
55
|
+
# to get our results from processing we can just call correspond method
|
56
|
+
results = process.get_results
|
57
|
+
|
58
|
+
puts "#{results.size} Results: "
|
59
|
+
results.each do |res|
|
60
|
+
#puts cloud.get_comparison_report(res)
|
61
|
+
#puts cloud.get_raw_text(res)
|
62
|
+
puts res.to_s
|
63
|
+
end
|
64
|
+
|
65
|
+
# Delete the created process
|
66
|
+
#puts process.delete
|
67
|
+
|
68
|
+
# In order to get all your past processes
|
69
|
+
#processes = cloud.get_processes
|
70
|
+
#puts "Overall you have #{processes.size} processes"
|
71
|
+
#processes.each do |res|
|
72
|
+
# puts res.to_s
|
73
|
+
#end
|
data/lib/copyleaks_api.rb
CHANGED
@@ -3,9 +3,10 @@ unless $LOAD_PATH.include?(File.expand_path(File.dirname(__FILE__)))
|
|
3
3
|
end
|
4
4
|
require 'copyleaks_api/version'
|
5
5
|
|
6
|
-
require 'copyleaks_api/language'
|
7
6
|
require 'copyleaks_api/errors'
|
8
7
|
|
8
|
+
require 'copyleaks_api/Models/ResultRecord'
|
9
|
+
|
9
10
|
require 'copyleaks_api/validators/custom_fields_validator'
|
10
11
|
require 'copyleaks_api/validators/email_validator'
|
11
12
|
require 'copyleaks_api/validators/file_validator'
|
@@ -0,0 +1,58 @@
|
|
1
|
+
module CopyleaksApi
|
2
|
+
class ResultRecord
|
3
|
+
def initialize(response)
|
4
|
+
@URL = response['URL']
|
5
|
+
@Percents = response['Percents']
|
6
|
+
@NumberOfCopiedWords = response['NumberOfCopiedWords']
|
7
|
+
@CachedVersion = response['CachedVersion']
|
8
|
+
@Title = response['Title']
|
9
|
+
@Introduction = response['Introduction']
|
10
|
+
@ComparisonReport = response['ComparisonReport']
|
11
|
+
@EmbededComparison = response['EmbededComparison']
|
12
|
+
end
|
13
|
+
|
14
|
+
def get_url
|
15
|
+
@URL
|
16
|
+
end
|
17
|
+
|
18
|
+
def get_percents
|
19
|
+
@Percents
|
20
|
+
end
|
21
|
+
|
22
|
+
def get_number_of_copied_words
|
23
|
+
@NumberOfCopiedWords
|
24
|
+
end
|
25
|
+
|
26
|
+
def get_cached_version
|
27
|
+
@CachedVersion
|
28
|
+
end
|
29
|
+
|
30
|
+
def get_title
|
31
|
+
@Title
|
32
|
+
end
|
33
|
+
|
34
|
+
def get_introduction
|
35
|
+
@Introduction
|
36
|
+
end
|
37
|
+
|
38
|
+
def get_comparison_report
|
39
|
+
@ComparisonReport
|
40
|
+
end
|
41
|
+
|
42
|
+
def get_embeded_comparison
|
43
|
+
@EmbededComparison
|
44
|
+
end
|
45
|
+
|
46
|
+
def to_s
|
47
|
+
puts "----------------------------------------------------------------"
|
48
|
+
puts "Title: #{@Title}"
|
49
|
+
puts "Introduction: #{@Introduction}"
|
50
|
+
puts "Url: #{@URL}"
|
51
|
+
puts "Percents: #{@Percents}%"
|
52
|
+
puts "NumberOfCopiedWords: #{@NumberOfCopiedWords}"
|
53
|
+
puts "CachedVersion: #{@CachedVersion}"
|
54
|
+
puts "ComparisonReport: #{@ComparisonReport}"
|
55
|
+
puts "EmbededComparison: #{@EmbededComparison}"
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
data/lib/copyleaks_api/api.rb
CHANGED
@@ -3,12 +3,15 @@ require 'net/http'
|
|
3
3
|
require 'mimemagic'
|
4
4
|
require 'mimemagic/overlay'
|
5
5
|
require 'openssl'
|
6
|
+
require 'securerandom'
|
7
|
+
|
6
8
|
|
7
9
|
module CopyleaksApi
|
8
10
|
class Api
|
9
11
|
BASE_URL = 'https://api.copyleaks.com'.freeze
|
10
|
-
|
11
|
-
|
12
|
+
API_VERSION_V1 = 'v1'.freeze
|
13
|
+
API_VERSION_V2 = 'v2'.freeze
|
14
|
+
|
12
15
|
# constructor
|
13
16
|
def initialize
|
14
17
|
uri = URI(BASE_URL)
|
@@ -23,6 +26,12 @@ module CopyleaksApi
|
|
23
26
|
make_request(request, options.merge(no_callbacks: true))
|
24
27
|
end
|
25
28
|
|
29
|
+
# make get request without any callback header
|
30
|
+
def get_with_final_path(path, options = {})
|
31
|
+
request = Net::HTTP::Get.new(path)
|
32
|
+
make_request(request, options.merge(no_callbacks: true))
|
33
|
+
end
|
34
|
+
|
26
35
|
# make post request with given options
|
27
36
|
def post(path, body = nil, options = {})
|
28
37
|
request = Net::HTTP::Post.new(request_uri(path))
|
@@ -45,6 +54,15 @@ module CopyleaksApi
|
|
45
54
|
make_request(request, options.merge(boundary: boundary))
|
46
55
|
end
|
47
56
|
|
57
|
+
# makes post request with file inside
|
58
|
+
def post_files(path, files_paths, options = {})
|
59
|
+
request = Net::HTTP::Post.new(request_uri(path, api_version: API_VERSION_V2))
|
60
|
+
options[:partial_scan] ||= CopyleaksApi::Config.allow_partial_scan
|
61
|
+
options[:compare_only] ||= CopyleaksApi::Config.compare_only
|
62
|
+
boundary = "copyleaks_sdk_#{SecureRandom.hex(4)}"
|
63
|
+
request.body = files_body(files_paths, boundary)
|
64
|
+
make_request(request, options.merge(boundary: boundary))
|
65
|
+
end
|
48
66
|
private
|
49
67
|
|
50
68
|
# extracts mime type of given file
|
@@ -66,10 +84,28 @@ module CopyleaksApi
|
|
66
84
|
"\r\n--#{boundary}--\r\n"
|
67
85
|
].join('')
|
68
86
|
end
|
87
|
+
|
88
|
+
# prepares post body with file inside
|
89
|
+
def files_body(paths, boundary)
|
90
|
+
body = "\r\n--#{boundary}\r\n"
|
91
|
+
counter = 1
|
92
|
+
paths.each do |path|
|
93
|
+
body += "content-disposition: form-data; name=\"file_#{counter}\"" +
|
94
|
+
"; filename=\"#{File.basename(path)}\"\r\n" +
|
95
|
+
"Content-Type: #{extract_mime_type(path)}\r\n" +
|
96
|
+
"Content-Transfer-Encoding: binary\r\n" +
|
97
|
+
"\r\n" +
|
98
|
+
File.open(path, 'rb') { |io| io.read } +
|
99
|
+
"\r\n--#{boundary}\r\n"
|
100
|
+
counter += 1
|
101
|
+
end
|
102
|
+
body += "\r\n--#{boundary}--\r\n"
|
103
|
+
body
|
104
|
+
end
|
69
105
|
|
70
106
|
# gather all API path
|
71
|
-
def request_uri(path)
|
72
|
-
"/#{
|
107
|
+
def request_uri(path, api_version: API_VERSION_V1)
|
108
|
+
"/#{api_version}/#{path}"
|
73
109
|
end
|
74
110
|
|
75
111
|
# gather headers, makes request and do validation
|
@@ -77,7 +113,11 @@ module CopyleaksApi
|
|
77
113
|
gather_headers(request, options)
|
78
114
|
response = @http.request(request)
|
79
115
|
Validators::ResponseValidator.validate!(response)
|
80
|
-
|
116
|
+
if not options.key?(:parse_json) or options[:parse_json]
|
117
|
+
JSON.parse(response.body)
|
118
|
+
else
|
119
|
+
response.body
|
120
|
+
end
|
81
121
|
end
|
82
122
|
|
83
123
|
# gather all headers
|
@@ -87,6 +127,8 @@ module CopyleaksApi
|
|
87
127
|
email_callback_header(options),
|
88
128
|
authentication_header(options),
|
89
129
|
sandbox_header,
|
130
|
+
compare_only_header,
|
131
|
+
in_progress_result(options),
|
90
132
|
content_type_header(options),
|
91
133
|
partial_scan_header(options),
|
92
134
|
'User-Agent' => "RUBYSDK/#{CopyleaksApi::VERSION}"
|
@@ -100,7 +142,21 @@ module CopyleaksApi
|
|
100
142
|
return {} unless Config.sandbox_mode
|
101
143
|
{ 'copyleaks-sandbox-mode' => '' }
|
102
144
|
end
|
103
|
-
|
145
|
+
|
146
|
+
# Compare your files against each other only
|
147
|
+
def compare_only_header
|
148
|
+
return {} unless Config.compare_only
|
149
|
+
{ 'copyleaks-compare-documents-for-similarity' => '' }
|
150
|
+
end
|
151
|
+
|
152
|
+
# Receive callback every time we find a new result without waiting for completion
|
153
|
+
def in_progress_result(options)
|
154
|
+
return {} if options[:no_http_callback] || options[:no_callbacks]
|
155
|
+
value = options[:in_progress_result] || CopyleaksApi::Config.in_progress_result
|
156
|
+
return {} unless value
|
157
|
+
Validators::UrlValidator.validate!(value)
|
158
|
+
{ 'copyleaks-in-progress-new-result' => value }
|
159
|
+
end
|
104
160
|
# prepares header for content type
|
105
161
|
def content_type_header(options)
|
106
162
|
{ 'Content-Type' => options[:boundary] ? "multipart/form-data; boundary=\"#{options[:boundary]}\"" :
|
@@ -125,7 +181,7 @@ module CopyleaksApi
|
|
125
181
|
value = options[:http_callback] || CopyleaksApi::Config.http_callback
|
126
182
|
return {} unless value
|
127
183
|
Validators::UrlValidator.validate!(value)
|
128
|
-
{ 'copyleaks-http-callback' => value }
|
184
|
+
{ 'copyleaks-http-completion-callback' => value }
|
129
185
|
end
|
130
186
|
|
131
187
|
# prepares header for email callback
|
@@ -137,6 +193,7 @@ module CopyleaksApi
|
|
137
193
|
{ 'copyleaks-email-callback' => value }
|
138
194
|
end
|
139
195
|
|
196
|
+
|
140
197
|
# prepares headers with custom fields
|
141
198
|
def custom_field_headers(options)
|
142
199
|
return {} if options[:no_custom_fields]
|
data/lib/copyleaks_api/config.rb
CHANGED
@@ -6,10 +6,12 @@ module CopyleaksApi
|
|
6
6
|
http_callback: nil,
|
7
7
|
email_callback: nil,
|
8
8
|
custom_fields: {},
|
9
|
+
compare_only: false,
|
10
|
+
in_progress_result: nil,
|
9
11
|
}.freeze
|
10
12
|
|
11
13
|
class << self
|
12
|
-
attr_writer :sandbox_mode, :http_callback, :email_callback, :custom_fields, :allow_partial_scan
|
14
|
+
attr_writer :sandbox_mode, :compare_only, :http_callback, :email_callback, :custom_fields, :allow_partial_scan, :in_progress_result
|
13
15
|
|
14
16
|
DEFAULTS.each do |attr, value|
|
15
17
|
# getters for all options
|
@@ -1,12 +1,13 @@
|
|
1
1
|
require 'copyleaks_api/errors'
|
2
2
|
require 'copyleaks_api/api'
|
3
3
|
|
4
|
+
|
4
5
|
module CopyleaksApi
|
5
6
|
class CopyleaksCloud
|
6
|
-
ALLOWED_ENDPOINTS = [:
|
7
|
+
ALLOWED_ENDPOINTS = [:businesses, :education, :websites]
|
7
8
|
attr_accessor :access_token
|
8
9
|
attr_reader :endpoint_type
|
9
|
-
|
10
|
+
|
10
11
|
# constructor
|
11
12
|
def initialize(email, api_key, type)
|
12
13
|
raise ArgumentError, "Endpoint type '#{type}' is invalid" unless ALLOWED_ENDPOINTS.include?(type.to_sym)
|
@@ -19,63 +20,76 @@ module CopyleaksApi
|
|
19
20
|
end
|
20
21
|
|
21
22
|
# returns account balance from endpoint
|
22
|
-
def
|
23
|
+
def get_credits_balance
|
23
24
|
api.get(url('count-credits'), token: @access_token.token)['Amount'].to_i
|
24
25
|
end
|
25
26
|
|
26
27
|
# uses create-by-url endpoint to create process
|
27
28
|
def create_by_url(url, options = {})
|
28
29
|
response = api.post(url('create-by-url'), { 'Url' => url }.to_json, options.merge(token: @access_token.token))
|
29
|
-
CopyleaksProcess.create(self, response)
|
30
|
+
CopyleaksProcess.create(self, api, response)
|
30
31
|
end
|
31
32
|
|
32
33
|
# uses create-by-file endpoint to create process
|
33
34
|
def create_by_file(file_path, options = {})
|
34
35
|
response = api.post_file(url('create-by-file'), file_path, options.merge(token: @access_token.token))
|
35
|
-
CopyleaksProcess.create(self, response)
|
36
|
+
CopyleaksProcess.create(self, api, response)
|
37
|
+
end
|
38
|
+
|
39
|
+
# uses create-by-file endpoint to create process
|
40
|
+
def create_by_files(files_paths, options = {})
|
41
|
+
response = api.post_files(url('create-by-file'), files_paths, options.merge(token: @access_token.token))
|
42
|
+
success_uploads = response['Success']
|
43
|
+
processes = []
|
44
|
+
success_uploads.each do |upload|
|
45
|
+
processes.push(CopyleaksProcess.create(self, api, upload))
|
46
|
+
end
|
47
|
+
processes
|
36
48
|
end
|
37
49
|
|
38
50
|
# uses create-by-file-ocr endpoint to create process
|
39
51
|
def create_by_ocr(ocr_file_path, options = {})
|
40
52
|
response = api.post_file(url_with_language('create-by-file-ocr', options), ocr_file_path,
|
41
53
|
options.merge(token: @access_token.token))
|
42
|
-
CopyleaksProcess.create(self, response)
|
54
|
+
CopyleaksProcess.create(self, api, response)
|
43
55
|
end
|
44
56
|
|
45
57
|
# uses create-by-text endpoint to create process
|
46
58
|
def create_by_text(text, options = {})
|
47
59
|
response = api.post(url('create-by-text'), text, options.merge(token: @access_token.token))
|
48
|
-
CopyleaksProcess.create(self, response)
|
49
|
-
end
|
50
|
-
|
51
|
-
# deletes process by given id
|
52
|
-
def delete(id)
|
53
|
-
api.delete(url(:delete, id), token: @access_token.token)
|
54
|
-
true
|
60
|
+
CopyleaksProcess.create(self, api, response)
|
55
61
|
end
|
56
62
|
|
57
|
-
#
|
58
|
-
def
|
63
|
+
# Returns a list of your past processes
|
64
|
+
def get_processes
|
59
65
|
response = api.get(url(:list), token: @access_token.token)
|
60
|
-
response.map { |hash| CopyleaksProcess.create_from_list(self, hash) }
|
66
|
+
response.map { |hash| CopyleaksProcess.create_from_list(self, @api, hash) }
|
61
67
|
end
|
62
|
-
|
63
|
-
#
|
64
|
-
def
|
65
|
-
response = api.
|
66
|
-
|
67
|
-
CopyleaksApi::CopyleaksProcess.create_from_status(self, id, response)
|
68
|
+
|
69
|
+
# Returns the raw text of a given result
|
70
|
+
def get_raw_text(result)
|
71
|
+
response = api.get_with_final_path(result.get_cached_version, parse_json: false, token: @access_token.token)
|
72
|
+
response
|
68
73
|
end
|
69
74
|
|
70
|
-
#
|
71
|
-
def result
|
72
|
-
response = api.
|
73
|
-
|
74
|
-
CopyleaksApi::CopyleaksProcess.create_from_result(self, id, response)
|
75
|
+
# Returns the raw text of a given result
|
76
|
+
def get_comparison_report(result)
|
77
|
+
response = api.get_with_final_path(result.get_comparison_report, token: @access_token.token)
|
78
|
+
response
|
75
79
|
end
|
76
|
-
|
77
|
-
|
78
|
-
|
80
|
+
|
81
|
+
# Returns a list of currently supported languages for ocr
|
82
|
+
def get_ocr_languages
|
83
|
+
response = api.get(url_misc('ocr-languages-list'))
|
84
|
+
response
|
85
|
+
end
|
86
|
+
|
87
|
+
# Returns a list of currently supported file types
|
88
|
+
def get_supported_file_types
|
89
|
+
response = api.get(url_misc('supported-file-types'))
|
90
|
+
response
|
91
|
+
end
|
92
|
+
|
79
93
|
# gather url for endpoints which need language in get parameters
|
80
94
|
def url_with_language(action, options)
|
81
95
|
language = options[:language] || Language.english
|
@@ -88,5 +102,15 @@ module CopyleaksApi
|
|
88
102
|
return "#{@endpoint_type}/#{action}" if id.nil?
|
89
103
|
"#{@endpoint_type}/#{id}/#{action}"
|
90
104
|
end
|
105
|
+
|
106
|
+
# gather path for download endpoint
|
107
|
+
def url_downloads(action, id = nil)
|
108
|
+
return "downloads/#{action}"
|
109
|
+
end
|
110
|
+
|
111
|
+
# gather path for download endpoint
|
112
|
+
def url_misc(action, id = nil)
|
113
|
+
return "miscellaneous/#{action}"
|
114
|
+
end
|
91
115
|
end
|
92
116
|
end
|
@@ -1,81 +1,77 @@
|
|
1
1
|
require 'time'
|
2
|
+
require 'copyleaks_api/Models/ResultRecord'
|
3
|
+
|
2
4
|
|
3
5
|
module CopyleaksApi
|
4
6
|
class CopyleaksProcess
|
5
|
-
|
6
|
-
|
7
|
-
attr_accessor :status, :process_id, :status, :progress, :custom_fields, :created_at
|
7
|
+
attr_accessor :process_id, :progress, :custom_fields, :created_at
|
8
8
|
|
9
9
|
# constructor
|
10
10
|
def initialize(options)
|
11
11
|
@cloud = options[:cloud]
|
12
|
-
[:cloud, :process_id, :custom_fields, :result, :
|
12
|
+
[:cloud, :api, :process_id, :custom_fields, :result, :progress].each do |attr|
|
13
13
|
instance_variable_set("@#{attr}", options[attr]) if options[attr]
|
14
14
|
end
|
15
|
-
|
16
15
|
@created_at = DateTime.parse(options[:created_at]) if options[:created_at]
|
17
|
-
@status = STATUSES[options[:status_code].to_i + 1] if options[:status_code]
|
18
16
|
end
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
define_method("#{status}?") do
|
23
|
-
reload if @status.nil?
|
24
|
-
@status == status
|
25
|
-
end
|
17
|
+
|
18
|
+
def to_s
|
19
|
+
return "Created at: #{@created_at}"
|
26
20
|
end
|
27
21
|
|
28
|
-
# returns true if
|
22
|
+
# returns true if still processing data on server side
|
29
23
|
def processing?
|
30
|
-
|
24
|
+
if @progress == 100
|
25
|
+
false
|
26
|
+
else
|
27
|
+
true
|
28
|
+
end
|
31
29
|
end
|
32
30
|
|
33
31
|
# return result data or retrieves from result endpoint if nothing specified
|
34
|
-
|
35
|
-
|
32
|
+
# retries result information of process with given id
|
33
|
+
def get_results
|
34
|
+
response = @api.get(@cloud.url(:result, @process_id), no_callbacks: true, token: @cloud.access_token.token)
|
35
|
+
@results = []
|
36
|
+
response.each do |res|
|
37
|
+
@results.push(CopyleaksApi::ResultRecord.new(res))
|
38
|
+
end
|
39
|
+
@results
|
40
|
+
end
|
41
|
+
|
42
|
+
# retries status information of process with given id
|
43
|
+
def update_status
|
44
|
+
response = @api.get(@cloud.url(:status, @process_id), no_callbacks: true, token: @cloud.access_token.token)
|
45
|
+
@progress = response['ProgressPercents'].to_i
|
46
|
+
@progress
|
36
47
|
end
|
37
48
|
|
38
|
-
#
|
39
|
-
def
|
40
|
-
|
41
|
-
|
49
|
+
# Returns the source text of this process
|
50
|
+
def get_source_text
|
51
|
+
response = @api.get(@cloud.url_downloads("source-text?pid=#{@process_id}"), parse_json: false, no_callbacks: true, token: @cloud.access_token.token)
|
52
|
+
response
|
42
53
|
end
|
43
54
|
|
44
55
|
# deletes process from API
|
45
56
|
def delete
|
46
|
-
@cloud.delete
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
response = @cloud.status(process_id, raw: true)
|
53
|
-
@status = response['Status'].downcase
|
54
|
-
@progress = response['ProgressPercents'].to_i
|
55
|
-
@result = nil
|
56
|
-
self
|
57
|
+
response = @api.delete(@cloud.url(:delete, @process_id), token: @cloud.access_token.token)
|
58
|
+
if response['StatusCode'] == 200
|
59
|
+
true
|
60
|
+
else
|
61
|
+
false
|
62
|
+
end
|
57
63
|
end
|
58
64
|
|
59
65
|
class << self
|
60
66
|
# create CopyleaksProcess based on data got from any create endpoint
|
61
|
-
def create(cloud, hash)
|
62
|
-
new(cloud: cloud, process_id: hash['ProcessId'], created_at: hash['CreationTimeUTC'])
|
67
|
+
def create(cloud, api, hash)
|
68
|
+
new(cloud: cloud, api: api, process_id: hash['ProcessId'], created_at: hash['CreationTimeUTC'])
|
63
69
|
end
|
64
|
-
|
65
|
-
# create CopyleaksProcess based on data got from status endpoint
|
66
|
-
def create_from_status(cloud, id, hash)
|
67
|
-
new(cloud: cloud, process_id: id, status: hash['Status'].downcase, progress: hash['ProgressPercents'])
|
68
|
-
end
|
69
|
-
|
70
|
-
# creates CopyleaksProcess based on data got from result endpoint
|
71
|
-
def create_from_result(cloud, id, result)
|
72
|
-
new(cloud: cloud, process_id: id, result: result)
|
73
|
-
end
|
74
|
-
|
70
|
+
|
75
71
|
# creates CopyleaksProcess based on data got from list endpoint
|
76
|
-
def create_from_list(cloud, hash)
|
77
|
-
new(cloud: cloud, process_id: hash['ProcessId'], created_at: hash['CreationTimeUTC'],
|
78
|
-
|
72
|
+
def create_from_list(cloud, api, hash)
|
73
|
+
new(cloud: cloud, api: api, process_id: hash['ProcessId'], created_at: hash['CreationTimeUTC'],
|
74
|
+
status_code: hash['Status'].downcase, custom_fields: hash['CustomFields'])
|
79
75
|
end
|
80
76
|
end
|
81
77
|
end
|
@@ -1,3 +1,3 @@
|
|
1
|
-
module CopyleaksApi
|
2
|
-
VERSION = '
|
3
|
-
end
|
1
|
+
module CopyleaksApi
|
2
|
+
VERSION = '2.0.0'.freeze
|
3
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: plagiarism-checker
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Copyleaks ltd
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2017-10-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: webmock
|
@@ -113,15 +113,16 @@ files:
|
|
113
113
|
- bin/console
|
114
114
|
- bin/setup
|
115
115
|
- copyleaks_api.gemspec
|
116
|
-
-
|
116
|
+
- example_async.rb
|
117
|
+
- example_syncronized.rb
|
117
118
|
- lib/copyleaks_api.rb
|
119
|
+
- lib/copyleaks_api/Models/ResultRecord.rb
|
118
120
|
- lib/copyleaks_api/access_token.rb
|
119
121
|
- lib/copyleaks_api/api.rb
|
120
122
|
- lib/copyleaks_api/config.rb
|
121
123
|
- lib/copyleaks_api/copyleaks_cloud.rb
|
122
124
|
- lib/copyleaks_api/copyleaks_process.rb
|
123
125
|
- lib/copyleaks_api/errors.rb
|
124
|
-
- lib/copyleaks_api/language.rb
|
125
126
|
- lib/copyleaks_api/validators/custom_fields_validator.rb
|
126
127
|
- lib/copyleaks_api/validators/email_validator.rb
|
127
128
|
- lib/copyleaks_api/validators/file_validator.rb
|
@@ -149,7 +150,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
149
150
|
version: '0'
|
150
151
|
requirements: []
|
151
152
|
rubyforge_project:
|
152
|
-
rubygems_version: 2.6.
|
153
|
+
rubygems_version: 2.6.13
|
153
154
|
signing_key:
|
154
155
|
specification_version: 4
|
155
156
|
summary: Detects plagiarism and checks content distribution online.
|
data/examples/main.rb
DELETED
@@ -1,60 +0,0 @@
|
|
1
|
-
require 'bundler/setup'
|
2
|
-
require 'copyleaks_api'
|
3
|
-
|
4
|
-
# firstly we need to create new Cloud entity
|
5
|
-
email = '<YOUR-EMAIL>'
|
6
|
-
api_key = '<YOUR-API-KEY>'
|
7
|
-
cloud = CopyleaksApi::CopyleaksCloud.new(email, api_key, :publisher)
|
8
|
-
|
9
|
-
# to check your balance just call balance
|
10
|
-
|
11
|
-
puts "Your balance is #{cloud.balance} credits"
|
12
|
-
|
13
|
-
# firstly we need to change work mode to sandbox
|
14
|
-
|
15
|
-
CopyleaksApi::Config.sandbox_mode = true
|
16
|
-
|
17
|
-
# now we can create new process by some url and custom callback
|
18
|
-
process = cloud.create_by_url('http://exmaple.com', http_callback: 'http://requestb.in/')
|
19
|
-
|
20
|
-
# Other scanning options
|
21
|
-
# Text scan:
|
22
|
-
#process = cloud.create_by_text("-Your text here-")
|
23
|
-
|
24
|
-
# Textual file scan:
|
25
|
-
#path = File.join(File.dirname(__FILE__), '..', 'spec', 'fixtures', 'files', 'lorem.txt')
|
26
|
-
#process = cloud.create_by_file(path)
|
27
|
-
|
28
|
-
# Ocr scan:
|
29
|
-
#path = File.join(File.dirname(__FILE__), '..', 'spec', 'fixtures', 'files', 'lorem.jpg')
|
30
|
-
#process = cloud.create_by_ocr(path, language: CopyleaksApi::Language.latin)
|
31
|
-
|
32
|
-
puts "Now process has state '#{process.status}'"
|
33
|
-
|
34
|
-
# to update process information we can just do this
|
35
|
-
|
36
|
-
# process.reload
|
37
|
-
|
38
|
-
# and it automatically call cloud.status with his id
|
39
|
-
# it need some time to process your request so we need to wait
|
40
|
-
|
41
|
-
while process.processing?
|
42
|
-
sleep(1)
|
43
|
-
process.reload
|
44
|
-
end
|
45
|
-
|
46
|
-
puts "And after sleep - #{process.status}"
|
47
|
-
# to get our results from processing we can just call correspond method
|
48
|
-
|
49
|
-
puts 'And its results are:'
|
50
|
-
puts process.result.inspect
|
51
|
-
|
52
|
-
# all results will be in array ow hashes with keys like Copyleaks API provides
|
53
|
-
# to get list of all existing processes we can call list method
|
54
|
-
|
55
|
-
processes = cloud.list
|
56
|
-
puts "Overall you have #{processes.size} processes"
|
57
|
-
|
58
|
-
# Delete finished process by PID:
|
59
|
-
#PID = '00000000-0000-0000-0000-000000000000'
|
60
|
-
#cloud.delete(PID)
|
@@ -1,61 +0,0 @@
|
|
1
|
-
module CopyleaksApi
|
2
|
-
module Language
|
3
|
-
ALLOWED = ['Afrikaans',
|
4
|
-
'Albanian',
|
5
|
-
'Basque',
|
6
|
-
'Brazilian',
|
7
|
-
'Bulgarian',
|
8
|
-
'Byelorussian',
|
9
|
-
'Catalan',
|
10
|
-
'Chinese_Simplified',
|
11
|
-
'Chinese_Traditional',
|
12
|
-
'Croatian',
|
13
|
-
'Czech',
|
14
|
-
'Danish',
|
15
|
-
'Dutch',
|
16
|
-
'English',
|
17
|
-
'Esperanto',
|
18
|
-
'Estonian',
|
19
|
-
'Finnish',
|
20
|
-
'French',
|
21
|
-
'Galician',
|
22
|
-
'German',
|
23
|
-
'Greek',
|
24
|
-
'Hungarian',
|
25
|
-
'Icelandic',
|
26
|
-
'Indonesian',
|
27
|
-
'Italian',
|
28
|
-
'Japanese',
|
29
|
-
'Korean',
|
30
|
-
'Latin',
|
31
|
-
'Latvian',
|
32
|
-
'Lithuanian',
|
33
|
-
'Macedonian',
|
34
|
-
'Malay',
|
35
|
-
'Moldavian',
|
36
|
-
'Norwegian',
|
37
|
-
'Polish',
|
38
|
-
'Portuguese',
|
39
|
-
'Romanian',
|
40
|
-
'Russian',
|
41
|
-
'Serbian',
|
42
|
-
'Slovak',
|
43
|
-
'Slovenian',
|
44
|
-
'Spanish',
|
45
|
-
'Swedish',
|
46
|
-
'Tagalog',
|
47
|
-
'Turkish',
|
48
|
-
'Ukrainian'].freeze
|
49
|
-
|
50
|
-
ALLOWED.each_with_index do |lang, index|
|
51
|
-
method = lang.downcase
|
52
|
-
|
53
|
-
# returns appropriate language name based on method name
|
54
|
-
define_method(method) do
|
55
|
-
ALLOWED[index]
|
56
|
-
end
|
57
|
-
|
58
|
-
module_function method
|
59
|
-
end
|
60
|
-
end
|
61
|
-
end
|