eyes_core 3.0.4
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 +7 -0
- data/ext/eyes_core/extconf.rb +3 -0
- data/ext/eyes_core/eyes_core.c +80 -0
- data/ext/eyes_core/eyes_core.h +24 -0
- data/lib/applitools/capybara.rb +8 -0
- data/lib/applitools/chunky_png/resampling.rb +148 -0
- data/lib/applitools/chunky_png_patch.rb +8 -0
- data/lib/applitools/connectivity/proxy.rb +3 -0
- data/lib/applitools/connectivity/server_connector.rb +118 -0
- data/lib/applitools/core/app_environment.rb +29 -0
- data/lib/applitools/core/app_output.rb +17 -0
- data/lib/applitools/core/app_output_with_screenshot.rb +22 -0
- data/lib/applitools/core/argument_guard.rb +35 -0
- data/lib/applitools/core/batch_info.rb +18 -0
- data/lib/applitools/core/eyes_base.rb +463 -0
- data/lib/applitools/core/eyes_screenshot.rb +35 -0
- data/lib/applitools/core/fixed_cut_provider.rb +61 -0
- data/lib/applitools/core/fixed_scale_provider.rb +14 -0
- data/lib/applitools/core/helpers.rb +18 -0
- data/lib/applitools/core/location.rb +84 -0
- data/lib/applitools/core/match_result.rb +16 -0
- data/lib/applitools/core/match_results.rb +9 -0
- data/lib/applitools/core/match_window_data.rb +34 -0
- data/lib/applitools/core/match_window_task.rb +86 -0
- data/lib/applitools/core/mouse_trigger.rb +39 -0
- data/lib/applitools/core/rectangle_size.rb +46 -0
- data/lib/applitools/core/region.rb +180 -0
- data/lib/applitools/core/screenshot.rb +49 -0
- data/lib/applitools/core/session.rb +15 -0
- data/lib/applitools/core/session_start_info.rb +33 -0
- data/lib/applitools/core/test_results.rb +55 -0
- data/lib/applitools/core/text_trigger.rb +24 -0
- data/lib/applitools/core/trigger.rb +8 -0
- data/lib/applitools/extensions.rb +18 -0
- data/lib/applitools/eyes_logger.rb +45 -0
- data/lib/applitools/images/eyes.rb +204 -0
- data/lib/applitools/images/eyes_images_screenshot.rb +102 -0
- data/lib/applitools/method_tracer.rb +23 -0
- data/lib/applitools/sauce.rb +2 -0
- data/lib/applitools/utils/eyes_selenium_utils.rb +348 -0
- data/lib/applitools/utils/image_delta_compressor.rb +146 -0
- data/lib/applitools/utils/image_utils.rb +146 -0
- data/lib/applitools/utils/utils.rb +68 -0
- data/lib/applitools/version.rb +3 -0
- data/lib/eyes_core.rb +70 -0
- metadata +273 -0
@@ -0,0 +1,146 @@
|
|
1
|
+
module Applitools::Utils
|
2
|
+
module ImageDeltaCompressor
|
3
|
+
extend self
|
4
|
+
|
5
|
+
BLOCK_SIZE = 10
|
6
|
+
|
7
|
+
# Compresses the target image based on the source image.
|
8
|
+
#
|
9
|
+
# +target+:: +ChunkyPNG::Canvas+ The image to compress based on the source image.
|
10
|
+
# +target_encoded+:: +Array+ The uncompressed image as binary string.
|
11
|
+
# +source+:: +ChunkyPNG::Canvas+ The source image used as a base for compressing the target image.
|
12
|
+
# +block_size+:: +Integer+ The width/height of each block.
|
13
|
+
#
|
14
|
+
# Returns +String+ The binary result (either the compressed image, or the uncompressed image if the compression
|
15
|
+
# is greater in length).
|
16
|
+
def compress_by_raw_blocks(target, target_encoded, source, block_size = BLOCK_SIZE)
|
17
|
+
# If we can't compress for any reason, return the target image as is.
|
18
|
+
if source.nil? || (source.height != target.height) || (source.width != target.width)
|
19
|
+
# Returning a COPY of the target binary string.
|
20
|
+
return String.new(target_encoded)
|
21
|
+
end
|
22
|
+
|
23
|
+
# Preparing the variables we need.
|
24
|
+
target_pixels = target.to_rgb_stream.unpack('C*')
|
25
|
+
source_pixels = source.to_rgb_stream.unpack('C*')
|
26
|
+
image_size = Dimension.new(target.width, target.height)
|
27
|
+
block_columns_count = (target.width / block_size) + ((target.width % block_size).zero? ? 0 : 1)
|
28
|
+
block_rows_count = (target.height / block_size) + ((target.height % block_size).zero? ? 0 : 1)
|
29
|
+
|
30
|
+
# IMPORTANT: The "-Zlib::MAX_WBITS" tells ZLib to create raw deflate compression, without the
|
31
|
+
# "Zlib headers" (this isn't documented in the Zlib page, I found this in some internet forum).
|
32
|
+
compressor = Zlib::Deflate.new(Zlib::BEST_COMPRESSION, -Zlib::MAX_WBITS)
|
33
|
+
|
34
|
+
compression_result = ''
|
35
|
+
|
36
|
+
# Writing the data header.
|
37
|
+
compression_result += PREAMBLE.encode('UTF-8')
|
38
|
+
compression_result += [FORMAT_RAW_BLOCKS].pack('C')
|
39
|
+
compression_result += [0].pack('S>') # Source id, Big Endian
|
40
|
+
compression_result += [block_size].pack('S>') # Big Endian
|
41
|
+
|
42
|
+
# We perform the compression for each channel.
|
43
|
+
3.times do |channel|
|
44
|
+
block_number = 0
|
45
|
+
block_rows_count.times do |block_row|
|
46
|
+
block_columns_count.times do |block_column|
|
47
|
+
actual_channel_index = 2 - channel # Since the image bytes are BGR and the server expects RGB...
|
48
|
+
compare_result = compare_and_copy_block_channel_data(source_pixels, target_pixels, image_size, 3,
|
49
|
+
block_size, block_column, block_row, actual_channel_index)
|
50
|
+
|
51
|
+
unless compare_result.identical
|
52
|
+
channel_bytes = compare_result.channel_bytes
|
53
|
+
string_to_compress = [channel].pack('C')
|
54
|
+
string_to_compress += [block_number].pack('L>')
|
55
|
+
string_to_compress += channel_bytes.pack('C*')
|
56
|
+
|
57
|
+
compression_result += compressor.deflate(string_to_compress)
|
58
|
+
|
59
|
+
# If the compressed data so far is greater than the uncompressed representation of the target, just return
|
60
|
+
# the target.
|
61
|
+
if compression_result.length > target_encoded.length
|
62
|
+
compressor.finish
|
63
|
+
compressor.close
|
64
|
+
# Returning a copy of the target bytes.
|
65
|
+
return String.new(target_encoded)
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
block_number += 1
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
# Compress and flush any remaining uncompressed data in the input buffer.
|
75
|
+
compression_result += compressor.finish
|
76
|
+
compressor.close
|
77
|
+
|
78
|
+
# Returning the compressed result as a byte array.
|
79
|
+
compression_result
|
80
|
+
end
|
81
|
+
|
82
|
+
private
|
83
|
+
|
84
|
+
PREAMBLE = 'applitools'.freeze
|
85
|
+
FORMAT_RAW_BLOCKS = 3
|
86
|
+
|
87
|
+
Dimension = Struct.new(:width, :height)
|
88
|
+
CompareAndCopyBlockChannelDataResult = Struct.new(:identical, :channel_bytes)
|
89
|
+
|
90
|
+
# Computes the width and height of the image data contained in the block at the input column and row.
|
91
|
+
# +image_size+:: +Dimension+ The image size in pixels.
|
92
|
+
# +block_size+:: The block size for which we would like to compute the image data width and height.
|
93
|
+
# +block_column+:: The block column index.
|
94
|
+
# +block_row+:: The block row index.
|
95
|
+
# ++
|
96
|
+
# Returns the width and height of the image data contained in the block are returned as a +Dimension+.
|
97
|
+
def get_actual_block_size(image_size, block_size, block_column, block_row)
|
98
|
+
actual_width = [image_size.width - (block_column * block_size), block_size].min
|
99
|
+
actual_height = [image_size.height - (block_row * block_size), block_size].min
|
100
|
+
Dimension.new(actual_width, actual_height)
|
101
|
+
end
|
102
|
+
|
103
|
+
# Compares a block of pixels between the source and target and copies the target's block bytes to the result.
|
104
|
+
# +source_pixels+:: +Array+ of bytes, representing the pixels of the source image.
|
105
|
+
# +target_pixels+:: +Array+ of bytes, representing the pixels of the target image.
|
106
|
+
# +image_size+:: +Dimension+ The size of the source/target image (remember they must be the same size).
|
107
|
+
# +pixel_length+:: +Integer+ The number of bytes composing a pixel
|
108
|
+
# +block_size+:: +Integer+ The width/height of the block (block is a square, theoretically).
|
109
|
+
# +block_column+:: +Integer+ The block column index (when looking at the images as a grid of blocks).
|
110
|
+
# +block_row+:: +Integer+ The block row index (when looking at the images as a grid of blocks).
|
111
|
+
# +channel+:: +Integer+ The index of the channel we're comparing.
|
112
|
+
# ++
|
113
|
+
# Returns +CompareAndCopyBlockChannelDataResult+ object containing a flag saying whether the blocks are identical
|
114
|
+
# and a copy of the target block's bytes.
|
115
|
+
def compare_and_copy_block_channel_data(source_pixels, target_pixels, image_size, pixel_length, block_size,
|
116
|
+
block_column, block_row, channel)
|
117
|
+
identical = true
|
118
|
+
|
119
|
+
actual_block_size = get_actual_block_size(image_size, block_size, block_column, block_row)
|
120
|
+
|
121
|
+
# Getting the actual amount of data in the block we wish to copy.
|
122
|
+
actual_block_height = actual_block_size.height
|
123
|
+
actual_block_width = actual_block_size.width
|
124
|
+
|
125
|
+
stride = image_size.width * pixel_length
|
126
|
+
|
127
|
+
# Iterating the block's pixels and comparing the source and target.
|
128
|
+
channel_bytes = []
|
129
|
+
actual_block_height.times do |h|
|
130
|
+
offset = (((block_size * block_row) + h) * stride) + (block_size * block_column * pixel_length) + channel
|
131
|
+
actual_block_width.times do |_w|
|
132
|
+
source_byte = source_pixels[offset]
|
133
|
+
target_byte = target_pixels[offset]
|
134
|
+
identical = false if source_byte != target_byte
|
135
|
+
channel_bytes << target_byte
|
136
|
+
offset += pixel_length
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
# Returning the compare-and-copy result.
|
141
|
+
CompareAndCopyBlockChannelDataResult.new(identical, channel_bytes)
|
142
|
+
end
|
143
|
+
|
144
|
+
include Applitools::MethodTracer
|
145
|
+
end
|
146
|
+
end
|
@@ -0,0 +1,146 @@
|
|
1
|
+
require 'base64'
|
2
|
+
require 'tempfile'
|
3
|
+
|
4
|
+
module Applitools::Utils
|
5
|
+
# @!visibility private
|
6
|
+
QUADRANTS_COUNT = 4
|
7
|
+
|
8
|
+
RESAMPLE_INCREMENTALLY_FRACTION = 2
|
9
|
+
|
10
|
+
module ImageUtils
|
11
|
+
extend self
|
12
|
+
|
13
|
+
# Creates an image object from the PNG bytes.
|
14
|
+
# @param [String] png_bytes A binary string of the PNG bytes of the image.
|
15
|
+
# @return [ChunkyPNG::Canvas] An image object.
|
16
|
+
def png_image_from_bytes(png_bytes)
|
17
|
+
ChunkyPNG::Image.from_blob(png_bytes)
|
18
|
+
end
|
19
|
+
|
20
|
+
# Creates an image instance from a base64 representation of its PNG encoding.
|
21
|
+
# @param [String] png_bytes The Base64 representation of a PNG image.
|
22
|
+
# @return [ChunkyPNG::Canvas] An image object.
|
23
|
+
def png_image_from_base64(png_bytes)
|
24
|
+
png_image_from_bytes(Base64.decode64(png_bytes))
|
25
|
+
end
|
26
|
+
|
27
|
+
# Get the raw PNG bytes of an image.
|
28
|
+
# @param [ChunkyPNG::Canvas] image The image object for which to get the PNG bytes.
|
29
|
+
# @return [String] The PNG bytes of the image.
|
30
|
+
def bytes_from_png_image(image)
|
31
|
+
image.to_blob(:fast_rgb)
|
32
|
+
end
|
33
|
+
|
34
|
+
# Get the Base64 representation of the raw PNG bytes of an image.
|
35
|
+
# @param [ChunkyPNG::Canvas] image The image object for which to get the PNG bytes.
|
36
|
+
# @return [String] the Base64 representation of the raw PNG bytes of an image.
|
37
|
+
def base64_from_png_image(image)
|
38
|
+
Base64.encode64(bytes_from_png_image(image))
|
39
|
+
end
|
40
|
+
|
41
|
+
# Rotates a matrix 90 deg clockwise or counter clockwise (depending whether num_quadrants is positive or negative,
|
42
|
+
# respectively).
|
43
|
+
# @param [ChunkyPNG::Canvas] image The image to rotate.
|
44
|
+
# @param [Integer] num_quadrants The number of rotations to perform. Positive values are used for clockwise rotation
|
45
|
+
# and negative values are used for counter-clockwise rotation.
|
46
|
+
def quadrant_rotate!(image, num_quadrants)
|
47
|
+
num_quadrants %= QUADRANTS_COUNT
|
48
|
+
case num_quadrants
|
49
|
+
when 0
|
50
|
+
image
|
51
|
+
when 1
|
52
|
+
image.rotate_right!
|
53
|
+
when 2
|
54
|
+
image.rotate_180!
|
55
|
+
when 3
|
56
|
+
image.rotate_left!
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
# Cuts the image according to passed crop_region. The method mutates an image.
|
61
|
+
# @param [ChunkyPNG::Canvas] image The image to cut
|
62
|
+
# @param [Applitools::Region] crop_region The region which represents cut bounds.
|
63
|
+
# The area outside crop_region will be removed from the image.
|
64
|
+
def cut!(image, crop_region)
|
65
|
+
image.crop! crop_region.left, crop_region.top, crop_region.width, crop_region.height
|
66
|
+
end
|
67
|
+
|
68
|
+
# Cuts the image according to passed crop_region. The method returns new instance of the image
|
69
|
+
# without changing the source image.
|
70
|
+
# @param [ChunkyPNG::Canvas] image The image to cut
|
71
|
+
# @param [Applitools::Region] crop_region The region which represents cut bounds.
|
72
|
+
# The area outside crop_region will be removed from the image.
|
73
|
+
def cut(image, crop_region)
|
74
|
+
cut! image.dup, crop_region
|
75
|
+
end
|
76
|
+
|
77
|
+
# Scales image by given +scale factor+ by modifying given image
|
78
|
+
# @param [Applitools::Screenshot] image An image to scale. (The source image will be modified
|
79
|
+
# by invoking the method)
|
80
|
+
# @param [Float] scale_ratio Scale factor.
|
81
|
+
# @return [Applitools::Screenshot]
|
82
|
+
def scale!(image, scale_ratio)
|
83
|
+
return image if scale_ratio == 1
|
84
|
+
image_ratio = image.width.to_f / image.height.to_f
|
85
|
+
scale_width = (image.width * scale_ratio).ceil
|
86
|
+
scale_height = (scale_width / image_ratio).ceil
|
87
|
+
resize_image!(image, scale_width, scale_height)
|
88
|
+
end
|
89
|
+
|
90
|
+
def scale(image, scale_ratio)
|
91
|
+
scale!(image.dup, scale_ratio)
|
92
|
+
end
|
93
|
+
|
94
|
+
def resize_image!(image, new_width, new_height)
|
95
|
+
Applitools::ArgumentGuard.not_nil(new_width, 'new_width')
|
96
|
+
Applitools::ArgumentGuard.not_nil(new_height, 'new_height')
|
97
|
+
Applitools::ArgumentGuard.not_nil(image, 'image')
|
98
|
+
Applitools::ArgumentGuard.is_a?(image, 'image', Applitools::Screenshot)
|
99
|
+
|
100
|
+
raise Applitools::EyesIllegalArgument.new "Invalid width: #{new_width}" if new_width <= 0
|
101
|
+
raise Applitools::EyesIllegalArgument.new "Invalid height: #{new_height}" if new_height <= 0
|
102
|
+
|
103
|
+
return image if image.width == new_width && image.height == new_height
|
104
|
+
|
105
|
+
if new_width > image.width || new_height > image.height
|
106
|
+
image.resample_bicubic!(new_width, new_height)
|
107
|
+
else
|
108
|
+
scale_image_incrementally!(image, new_width, new_height)
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
def resize_image(image, new_width, new_height)
|
113
|
+
resize_image!(image.dup, new_width, new_height)
|
114
|
+
end
|
115
|
+
|
116
|
+
def scale_image_incrementally!(image, new_width, new_height)
|
117
|
+
current_width = image.width
|
118
|
+
current_height = image.height
|
119
|
+
|
120
|
+
while current_width != new_width || current_height != new_height
|
121
|
+
prev_current_width = current_width
|
122
|
+
prev_current_height = current_height
|
123
|
+
if current_width > new_width
|
124
|
+
current_width -= (current_width / RESAMPLE_INCREMENTALLY_FRACTION)
|
125
|
+
current_width = new_width if current_width < new_width
|
126
|
+
end
|
127
|
+
|
128
|
+
if current_height > new_height
|
129
|
+
current_height -= (current_height / RESAMPLE_INCREMENTALLY_FRACTION)
|
130
|
+
current_height = new_height if current_height < new_height
|
131
|
+
end
|
132
|
+
|
133
|
+
return image if prev_current_width == current_width && prev_current_height == current_height
|
134
|
+
Applitools::EyesLogger.debug "Incremental dimensions: #{current_width} x #{current_height}"
|
135
|
+
image.resample_bicubic!(current_width, current_height)
|
136
|
+
end
|
137
|
+
image
|
138
|
+
end
|
139
|
+
|
140
|
+
def scale_image_incrementally(image, new_width, new_height)
|
141
|
+
scale_image_incrementally!(image.dup, new_width, new_height)
|
142
|
+
end
|
143
|
+
|
144
|
+
include Applitools::MethodTracer
|
145
|
+
end
|
146
|
+
end
|
@@ -0,0 +1,68 @@
|
|
1
|
+
require 'bigdecimal'
|
2
|
+
|
3
|
+
module Applitools::Utils
|
4
|
+
extend self
|
5
|
+
|
6
|
+
def underscore(str)
|
7
|
+
str.gsub(/::/, '/').gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2').gsub(/([a-z\d])([A-Z])/, '\1_\2').tr('-', '_').downcase
|
8
|
+
end
|
9
|
+
|
10
|
+
def uncapitalize(str)
|
11
|
+
str[0, 1].downcase + str[1..-1]
|
12
|
+
end
|
13
|
+
|
14
|
+
def camelcase(str)
|
15
|
+
tokens = str.split('_')
|
16
|
+
uncapitalize(tokens.shift) + tokens.map(&:capitalize).join
|
17
|
+
end
|
18
|
+
|
19
|
+
def wrap(object)
|
20
|
+
if object.nil?
|
21
|
+
[]
|
22
|
+
elsif object.respond_to?(:to_ary)
|
23
|
+
object.to_ary || [object]
|
24
|
+
else
|
25
|
+
[object]
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def underscore_hash_keys(hash)
|
30
|
+
convert_hash_keys(hash, :underscore)
|
31
|
+
end
|
32
|
+
|
33
|
+
def camelcase_hash_keys(hash)
|
34
|
+
convert_hash_keys(hash, :camelcase)
|
35
|
+
end
|
36
|
+
|
37
|
+
def boolean_value(value)
|
38
|
+
if value
|
39
|
+
true
|
40
|
+
else
|
41
|
+
false
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def symbolize_keys(hash)
|
46
|
+
hash.each_with_object({}) do |(k, v), memo|
|
47
|
+
memo[k.to_sym] = v
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
def extract_options!(array)
|
52
|
+
return array.pop if array.last.instance_of? Hash
|
53
|
+
{}
|
54
|
+
end
|
55
|
+
|
56
|
+
private
|
57
|
+
|
58
|
+
def convert_hash_keys(value, method)
|
59
|
+
case value
|
60
|
+
when Array
|
61
|
+
value.map { |v| convert_hash_keys(v, method) }
|
62
|
+
when Hash
|
63
|
+
Hash[value.map { |k, v| [send(method, k.to_s).to_sym, convert_hash_keys(v, method)] }]
|
64
|
+
else
|
65
|
+
value
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
data/lib/eyes_core.rb
ADDED
@@ -0,0 +1,70 @@
|
|
1
|
+
require 'forwardable'
|
2
|
+
require 'delegate'
|
3
|
+
require 'time'
|
4
|
+
|
5
|
+
module Applitools
|
6
|
+
# @!visibility private
|
7
|
+
class << self
|
8
|
+
# @!visibility private
|
9
|
+
def require_dir(dir)
|
10
|
+
Dir[File.join(File.dirname(File.expand_path(__FILE__)), 'applitools', dir, '*.rb')].sort.each do |f|
|
11
|
+
require f
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
# @!visibility private
|
17
|
+
class EyesError < StandardError; end
|
18
|
+
# @!visibility private
|
19
|
+
class EyesAbort < EyesError; end
|
20
|
+
# @!visibility private
|
21
|
+
class EyesIllegalArgument < EyesError; end
|
22
|
+
# @!visibility private
|
23
|
+
class EyesNoSuchFrame < EyesError; end
|
24
|
+
# @!visibility private
|
25
|
+
class OutOfBoundsException < EyesError; end
|
26
|
+
# @!visibility private
|
27
|
+
class EyesDriverOperationException < EyesError; end
|
28
|
+
# @!visibility private
|
29
|
+
class EyesNotOpenException < EyesError; end
|
30
|
+
# @!visibility private
|
31
|
+
class EyesCoordinateTypeConversionException < EyesError; end
|
32
|
+
|
33
|
+
# @!visibility private
|
34
|
+
class AbstractMethodCalled < EyesError
|
35
|
+
attr_accessor :method_name, :object
|
36
|
+
|
37
|
+
def initialize(method_name, object)
|
38
|
+
@method = method_name
|
39
|
+
@object = object
|
40
|
+
message = "Abstract method #{method_name} is called for #{object}. "\
|
41
|
+
'You should override it in a descendant class.'
|
42
|
+
super message
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
# @!visibility private
|
47
|
+
class TestFailedError < StandardError
|
48
|
+
attr_accessor :test_results
|
49
|
+
|
50
|
+
def initialize(message, test_results = nil)
|
51
|
+
super(message)
|
52
|
+
|
53
|
+
@test_results = test_results
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
# @!visibility private
|
58
|
+
class NewTestError < TestFailedError; end
|
59
|
+
end
|
60
|
+
|
61
|
+
require_relative 'applitools/method_tracer'
|
62
|
+
require_relative 'applitools/extensions'
|
63
|
+
require_relative 'applitools/version'
|
64
|
+
require_relative 'applitools/chunky_png_patch'
|
65
|
+
|
66
|
+
Applitools.require_dir 'core'
|
67
|
+
Applitools.require_dir 'connectivity'
|
68
|
+
Applitools.require_dir 'utils'
|
69
|
+
|
70
|
+
require_relative 'applitools/eyes_logger'
|
metadata
ADDED
@@ -0,0 +1,273 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: eyes_core
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 3.0.4
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Applitools Team
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2017-03-14 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: oily_png
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.2'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.2'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: chunky_png
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - '='
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: 1.3.6
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - '='
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: 1.3.6
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: faraday
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: oj
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :runtime
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: bundler
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - ">="
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - ">="
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: rake
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - ">="
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - ">="
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: rspec
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - ">="
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '3'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - ">="
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '3'
|
111
|
+
- !ruby/object:Gem::Dependency
|
112
|
+
name: rubocop
|
113
|
+
requirement: !ruby/object:Gem::Requirement
|
114
|
+
requirements:
|
115
|
+
- - "<="
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: 0.46.0
|
118
|
+
type: :development
|
119
|
+
prerelease: false
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
requirements:
|
122
|
+
- - "<="
|
123
|
+
- !ruby/object:Gem::Version
|
124
|
+
version: 0.46.0
|
125
|
+
- !ruby/object:Gem::Dependency
|
126
|
+
name: pry
|
127
|
+
requirement: !ruby/object:Gem::Requirement
|
128
|
+
requirements:
|
129
|
+
- - ">="
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: '0'
|
132
|
+
type: :development
|
133
|
+
prerelease: false
|
134
|
+
version_requirements: !ruby/object:Gem::Requirement
|
135
|
+
requirements:
|
136
|
+
- - ">="
|
137
|
+
- !ruby/object:Gem::Version
|
138
|
+
version: '0'
|
139
|
+
- !ruby/object:Gem::Dependency
|
140
|
+
name: pry-byebug
|
141
|
+
requirement: !ruby/object:Gem::Requirement
|
142
|
+
requirements:
|
143
|
+
- - ">="
|
144
|
+
- !ruby/object:Gem::Version
|
145
|
+
version: '0'
|
146
|
+
type: :development
|
147
|
+
prerelease: false
|
148
|
+
version_requirements: !ruby/object:Gem::Requirement
|
149
|
+
requirements:
|
150
|
+
- - ">="
|
151
|
+
- !ruby/object:Gem::Version
|
152
|
+
version: '0'
|
153
|
+
- !ruby/object:Gem::Dependency
|
154
|
+
name: byebug
|
155
|
+
requirement: !ruby/object:Gem::Requirement
|
156
|
+
requirements:
|
157
|
+
- - ">="
|
158
|
+
- !ruby/object:Gem::Version
|
159
|
+
version: '0'
|
160
|
+
type: :development
|
161
|
+
prerelease: false
|
162
|
+
version_requirements: !ruby/object:Gem::Requirement
|
163
|
+
requirements:
|
164
|
+
- - ">="
|
165
|
+
- !ruby/object:Gem::Version
|
166
|
+
version: '0'
|
167
|
+
- !ruby/object:Gem::Dependency
|
168
|
+
name: pry-doc
|
169
|
+
requirement: !ruby/object:Gem::Requirement
|
170
|
+
requirements:
|
171
|
+
- - ">="
|
172
|
+
- !ruby/object:Gem::Version
|
173
|
+
version: '0'
|
174
|
+
type: :development
|
175
|
+
prerelease: false
|
176
|
+
version_requirements: !ruby/object:Gem::Requirement
|
177
|
+
requirements:
|
178
|
+
- - ">="
|
179
|
+
- !ruby/object:Gem::Version
|
180
|
+
version: '0'
|
181
|
+
- !ruby/object:Gem::Dependency
|
182
|
+
name: pry-stack_explorer
|
183
|
+
requirement: !ruby/object:Gem::Requirement
|
184
|
+
requirements:
|
185
|
+
- - ">="
|
186
|
+
- !ruby/object:Gem::Version
|
187
|
+
version: '0'
|
188
|
+
type: :development
|
189
|
+
prerelease: false
|
190
|
+
version_requirements: !ruby/object:Gem::Requirement
|
191
|
+
requirements:
|
192
|
+
- - ">="
|
193
|
+
- !ruby/object:Gem::Version
|
194
|
+
version: '0'
|
195
|
+
description: Applitools Ruby SDK
|
196
|
+
email:
|
197
|
+
- team@applitools.com
|
198
|
+
executables: []
|
199
|
+
extensions:
|
200
|
+
- ext/eyes_core/extconf.rb
|
201
|
+
extra_rdoc_files: []
|
202
|
+
files:
|
203
|
+
- ext/eyes_core/extconf.rb
|
204
|
+
- ext/eyes_core/eyes_core.c
|
205
|
+
- ext/eyes_core/eyes_core.h
|
206
|
+
- lib/applitools/capybara.rb
|
207
|
+
- lib/applitools/chunky_png/resampling.rb
|
208
|
+
- lib/applitools/chunky_png_patch.rb
|
209
|
+
- lib/applitools/connectivity/proxy.rb
|
210
|
+
- lib/applitools/connectivity/server_connector.rb
|
211
|
+
- lib/applitools/core/app_environment.rb
|
212
|
+
- lib/applitools/core/app_output.rb
|
213
|
+
- lib/applitools/core/app_output_with_screenshot.rb
|
214
|
+
- lib/applitools/core/argument_guard.rb
|
215
|
+
- lib/applitools/core/batch_info.rb
|
216
|
+
- lib/applitools/core/eyes_base.rb
|
217
|
+
- lib/applitools/core/eyes_screenshot.rb
|
218
|
+
- lib/applitools/core/fixed_cut_provider.rb
|
219
|
+
- lib/applitools/core/fixed_scale_provider.rb
|
220
|
+
- lib/applitools/core/helpers.rb
|
221
|
+
- lib/applitools/core/location.rb
|
222
|
+
- lib/applitools/core/match_result.rb
|
223
|
+
- lib/applitools/core/match_results.rb
|
224
|
+
- lib/applitools/core/match_window_data.rb
|
225
|
+
- lib/applitools/core/match_window_task.rb
|
226
|
+
- lib/applitools/core/mouse_trigger.rb
|
227
|
+
- lib/applitools/core/rectangle_size.rb
|
228
|
+
- lib/applitools/core/region.rb
|
229
|
+
- lib/applitools/core/screenshot.rb
|
230
|
+
- lib/applitools/core/session.rb
|
231
|
+
- lib/applitools/core/session_start_info.rb
|
232
|
+
- lib/applitools/core/test_results.rb
|
233
|
+
- lib/applitools/core/text_trigger.rb
|
234
|
+
- lib/applitools/core/trigger.rb
|
235
|
+
- lib/applitools/extensions.rb
|
236
|
+
- lib/applitools/eyes_logger.rb
|
237
|
+
- lib/applitools/images/eyes.rb
|
238
|
+
- lib/applitools/images/eyes_images_screenshot.rb
|
239
|
+
- lib/applitools/method_tracer.rb
|
240
|
+
- lib/applitools/sauce.rb
|
241
|
+
- lib/applitools/utils/eyes_selenium_utils.rb
|
242
|
+
- lib/applitools/utils/image_delta_compressor.rb
|
243
|
+
- lib/applitools/utils/image_utils.rb
|
244
|
+
- lib/applitools/utils/utils.rb
|
245
|
+
- lib/applitools/version.rb
|
246
|
+
- lib/eyes_core.rb
|
247
|
+
homepage: https://www.applitools.com
|
248
|
+
licenses:
|
249
|
+
- Apache License, Version 2.0
|
250
|
+
metadata:
|
251
|
+
yard.run: yri
|
252
|
+
post_install_message:
|
253
|
+
rdoc_options: []
|
254
|
+
require_paths:
|
255
|
+
- lib
|
256
|
+
- ext
|
257
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
258
|
+
requirements:
|
259
|
+
- - ">="
|
260
|
+
- !ruby/object:Gem::Version
|
261
|
+
version: '0'
|
262
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
263
|
+
requirements:
|
264
|
+
- - ">="
|
265
|
+
- !ruby/object:Gem::Version
|
266
|
+
version: '0'
|
267
|
+
requirements: []
|
268
|
+
rubyforge_project:
|
269
|
+
rubygems_version: 2.6.8
|
270
|
+
signing_key:
|
271
|
+
specification_version: 4
|
272
|
+
summary: Applitools Ruby SDK
|
273
|
+
test_files: []
|