fakeredis 0.7.0 → 0.9.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 1be2134927d3b7838ee3e2fd4376791bea516561
4
- data.tar.gz: 2b3e0c64b79df1358151bbd1405000395fa06e86
2
+ SHA256:
3
+ metadata.gz: 472bc70d16d42ddd98a542825b81fdd5d8f7af18a8b704f5022046895ca5a867
4
+ data.tar.gz: 7f0b48ebe4cfa88e99b9d949be3e0bd6816dbc3c0629062d42e0e1fce92a03fc
5
5
  SHA512:
6
- metadata.gz: cfb37be84fd30d941fadc44a177e2029cd2de063fc090bc3004166a72f5dba6e7378e9c918aa1d156d44b8277f830dfedbd34aad57142770512f420f4f12fae3
7
- data.tar.gz: 2f841badb4c16e9ff6d3c35b697b9ee262022bc8286553e7187a47173af742114eacd5cccdb3d0477c111457fc9a7f50fdb7de970a25c04ba1be33318c84a1ac
6
+ metadata.gz: fcef2e419257364269044dbd0d8b21d0aacdaeb613d91e83abaef77a18a6c5551e72ded9e90ac334d17760aaf80e4c0fec9fd72f15e3a80efe63c7be5b3f2903
7
+ data.tar.gz: 6076a543910d3eec4a6fb8912ce1be5b44bea9fa71cbd76fd62f8b0a130eb97d85a4a2390d05ef5bd2a1eae699c487b01de537f9781c8aa39553c198f53c9618
@@ -0,0 +1,74 @@
1
+ # For most projects, this workflow file will not need changing; you simply need
2
+ # to commit it to your repository.
3
+ #
4
+ # You may wish to alter this file to override the set of languages analyzed,
5
+ # or to provide custom queries or build logic.
6
+ #
7
+ # ******** NOTE ********
8
+ # We have attempted to detect the languages in your repository. Please check
9
+ # the `language` matrix defined below to confirm you have the correct set of
10
+ # supported CodeQL languages.
11
+ #
12
+ name: "CodeQL"
13
+
14
+ on:
15
+ push:
16
+ branches: [ "master" ]
17
+ pull_request:
18
+ # The branches below must be a subset of the branches above
19
+ branches: [ "master" ]
20
+ schedule:
21
+ - cron: '34 3 * * 3'
22
+
23
+ jobs:
24
+ analyze:
25
+ name: Analyze
26
+ runs-on: ubuntu-latest
27
+ permissions:
28
+ actions: read
29
+ contents: read
30
+ security-events: write
31
+
32
+ strategy:
33
+ fail-fast: false
34
+ matrix:
35
+ language: [ 'ruby' ]
36
+ # CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ]
37
+ # Learn more about CodeQL language support at https://aka.ms/codeql-docs/language-support
38
+
39
+ steps:
40
+ - name: Checkout repository
41
+ uses: actions/checkout@v3
42
+
43
+ # Initializes the CodeQL tools for scanning.
44
+ - name: Initialize CodeQL
45
+ uses: github/codeql-action/init@v2
46
+ with:
47
+ languages: ${{ matrix.language }}
48
+ # If you wish to specify custom queries, you can do so here or in a config file.
49
+ # By default, queries listed here will override any specified in a config file.
50
+ # Prefix the list here with "+" to use these queries and those in the config file.
51
+
52
+ # Details on CodeQL's query packs refer to : https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#using-queries-in-ql-packs
53
+ # queries: security-extended,security-and-quality
54
+
55
+
56
+ # Autobuild attempts to build any compiled languages (C/C++, C#, Go, or Java).
57
+ # If this step fails, then you should remove it and run the build manually (see below)
58
+ - name: Autobuild
59
+ uses: github/codeql-action/autobuild@v2
60
+
61
+ # ℹ️ Command-line programs to run using the OS shell.
62
+ # 📚 See https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#jobsjob_idstepsrun
63
+
64
+ # If the Autobuild fails above, remove it and uncomment the following three lines.
65
+ # modify them (or add more) to build your code if your project, please refer to the EXAMPLE below for guidance.
66
+
67
+ # - run: |
68
+ # echo "Run, Build Application using script"
69
+ # ./location_of_script_within_repo/buildscript.sh
70
+
71
+ - name: Perform CodeQL Analysis
72
+ uses: github/codeql-action/analyze@v2
73
+ with:
74
+ category: "/language:${{matrix.language}}"
@@ -0,0 +1,33 @@
1
+ # This workflow uses actions that are not certified by GitHub.
2
+ # They are provided by a third-party and are governed by
3
+ # separate terms of service, privacy policy, and support
4
+ # documentation.
5
+
6
+ # GitHub recommends pinning actions to a commit SHA.
7
+ # To get a newer version, you will need to update the SHA.
8
+ # You can also reference a tag or branch, but the action may change without warning.
9
+
10
+ name: Ruby CI
11
+
12
+ on:
13
+ push:
14
+ branches: [ master ]
15
+ pull_request:
16
+ branches: [ master ]
17
+
18
+ jobs:
19
+ test:
20
+ runs-on: ${{ matrix.os }}-latest
21
+ strategy:
22
+ fail-fast: false
23
+ matrix:
24
+ os: [ubuntu, macos]
25
+ ruby: [3.0, 3.1, 3.2, head, debug, jruby, jruby-head, truffleruby, truffleruby-head]
26
+ continue-on-error: ${{ endsWith(matrix.ruby, 'head') || matrix.ruby == 'debug' }}
27
+ steps:
28
+ - uses: actions/checkout@v3
29
+ - uses: ruby/setup-ruby@v1
30
+ with:
31
+ ruby-version: ${{ matrix.ruby }}
32
+ - run: bundle install
33
+ - run: bundle exec rake
data/.gitignore CHANGED
@@ -1,7 +1,6 @@
1
1
  *.gem
2
2
  .bundle
3
3
  Gemfile.lock
4
- gemfiles/*.gemfile.lock
5
4
  pkg/*
6
5
  .rvmrc
7
6
  *.rbc
data/Gemfile CHANGED
@@ -3,11 +3,5 @@ source "https://rubygems.org"
3
3
  gem 'rake'
4
4
  gem 'rdoc'
5
5
 
6
- platforms :rbx do
7
- gem 'racc'
8
- gem 'rubysl', '~> 2.0'
9
- gem 'psych'
10
- end
11
-
12
6
  # Specify your gem's dependencies in fakeredis.gemspec
13
7
  gemspec
data/LICENSE CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (c) 2011-2018 Guillermo Iguaran
1
+ Copyright (c) 2011-2023 Guillermo Iguaran
2
2
 
3
3
  Permission is hereby granted, free of charge, to any person obtaining
4
4
  a copy of this software and associated documentation files (the
data/README.md CHANGED
@@ -1,4 +1,6 @@
1
- # FakeRedis [![Build Status](https://secure.travis-ci.org/guilleiguaran/fakeredis.png)](http://travis-ci.org/guilleiguaran/fakeredis)
1
+ # FakeRedis
2
+ ![Build Status](https://github.com/guilleiguaran/fakeredis/actions/workflows/ruby.yml/badge.svg)
3
+
2
4
  This a fake implementation of redis-rb for machines without Redis or test environments
3
5
 
4
6
 
@@ -100,5 +102,4 @@ Thanks to [all contributors](https://github.com/guilleiguaran/fakeredis/graphs/c
100
102
 
101
103
  ## Copyright
102
104
 
103
- Copyright (c) 2011-2018 Guillermo Iguaran. See LICENSE for
104
- further details.
105
+ Copyright (c) 2011-2023 Guillermo Iguaran. See LICENSE for further details.
data/fakeredis.gemspec CHANGED
@@ -18,6 +18,6 @@ Gem::Specification.new do |s|
18
18
  s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
19
  s.require_paths = ["lib"]
20
20
 
21
- s.add_runtime_dependency(%q<redis>, [">= 3.2", "< 5.0"])
22
- s.add_development_dependency(%q<rspec>, ["~> 3.0"])
21
+ s.add_runtime_dependency(%q<redis>, ["~> 4.8"])
22
+ s.add_development_dependency(%q<rspec>, ["~> 3"])
23
23
  end
@@ -15,12 +15,6 @@ module FakeRedis
15
15
  raise Redis::CommandError, "ERR unknown command '#{meffod}'"
16
16
  end
17
17
 
18
- if reply == true
19
- reply = 1
20
- elsif reply == false
21
- reply = 0
22
- end
23
-
24
18
  replies << reply
25
19
  nil
26
20
  end
@@ -44,10 +44,8 @@ module FakeRedis
44
44
  end
45
45
 
46
46
  def values_at(*keys)
47
- keys.each do |key|
48
- key = normalize(key)
49
- delete(key) if expired?(key)
50
- end
47
+ keys = keys.map { |key| normalize(key) }
48
+ keys.each { |key| delete(key) if expired?(key) }
51
49
  super
52
50
  end
53
51
 
@@ -0,0 +1,142 @@
1
+ require "fakeredis/geo_set"
2
+
3
+ module FakeRedis
4
+ module GeoCommands
5
+ DISTANCE_UNITS = {
6
+ "m" => 1,
7
+ "km" => 1000,
8
+ "ft" => 0.3048,
9
+ "mi" => 1609.34
10
+ }
11
+
12
+ REDIS_DOUBLE_PRECISION = 4
13
+ REDIS_GEOHASH_SIZE = 10
14
+
15
+ def geoadd(key, *members)
16
+ raise_argument_error("geoadd") if members.empty? || members.size % 3 != 0
17
+
18
+ set = (data[key] ||= GeoSet.new)
19
+ prev_size = set.size
20
+ members.each_slice(3) do |member|
21
+ set.add(*member)
22
+ end
23
+ set.size - prev_size
24
+ end
25
+
26
+ def geodist(key, member1, member2, unit = "m")
27
+ unit = unit.to_s
28
+ raise_command_error("ERR unsupported unit provided. please use #{DISTANCE_UNITS.keys.join(', ')}") unless DISTANCE_UNITS.include?(unit)
29
+
30
+ set = (data[key] || GeoSet.new)
31
+ point1 = set.get(member1)
32
+ point2 = set.get(member2)
33
+ if point1 && point2
34
+ distance = point1.distance_to(point2)
35
+ distance_in_units = distance / DISTANCE_UNITS[unit]
36
+ distance_in_units.round(REDIS_DOUBLE_PRECISION).to_s
37
+ end
38
+ end
39
+
40
+ def geohash(key, member)
41
+ members = Array(member)
42
+ raise_argument_error("geohash") if members.empty?
43
+ set = (data[key] || GeoSet.new)
44
+ members.map do |member|
45
+ point = set.get(member)
46
+ point.geohash(REDIS_GEOHASH_SIZE) if point
47
+ end
48
+ end
49
+
50
+ def geopos(key, member)
51
+ return nil unless data[key]
52
+
53
+ members = Array(member)
54
+ set = (data[key] || GeoSet.new)
55
+ members.map do |member|
56
+ point = set.get(member)
57
+ [point.lon.to_s, point.lat.to_s] if point
58
+ end
59
+ end
60
+
61
+ def georadius(*args)
62
+ args = args.dup
63
+ raise_argument_error("georadius") if args.size < 5
64
+ key, lon, lat, radius, unit, *rest = args
65
+ raise_argument_error("georadius") unless DISTANCE_UNITS.has_key?(unit)
66
+ radius *= DISTANCE_UNITS[unit]
67
+
68
+ set = (data[key] || GeoSet.new)
69
+ center = GeoSet::Point.new(lon, lat, nil)
70
+
71
+ do_georadius(set, center, radius, unit, rest)
72
+ end
73
+
74
+ def georadiusbymember(*args)
75
+ args = args.dup
76
+ raise_argument_error("georadiusbymember") if args.size < 4
77
+ key, member, radius, unit, *rest = args
78
+ raise_argument_error("georadiusbymember") unless DISTANCE_UNITS.has_key?(unit)
79
+ radius *= DISTANCE_UNITS[unit]
80
+
81
+ set = (data[key] || GeoSet.new)
82
+ center = set.get(member)
83
+ raise_command_error("ERR could not decode requested zset member") unless center
84
+
85
+ do_georadius(set, center, radius, unit, args)
86
+ end
87
+
88
+ private
89
+
90
+ def do_georadius(set, center, radius, unit, args)
91
+ points = set.points_within_radius(center, radius)
92
+
93
+ options = georadius_options(args)
94
+
95
+ if options[:asc]
96
+ points.sort_by! { |p| p.distance_to(center) }
97
+ elsif options[:desc]
98
+ points.sort_by! { |p| -p.distance_to(center) }
99
+ end
100
+
101
+ points = points.take(options[:count]) if options[:count]
102
+ extras = options[:extras]
103
+ return points.map(&:name) if extras.empty?
104
+
105
+ points.map do |point|
106
+ member = [point.name]
107
+
108
+ extras.each do |extra|
109
+ case extra
110
+ when "WITHCOORD"
111
+ member << [point.lon.to_s, point.lat.to_s]
112
+ when "WITHDIST"
113
+ distance = point.distance_to(center)
114
+ distance_in_units = distance / DISTANCE_UNITS[unit]
115
+ member << distance_in_units.round(REDIS_DOUBLE_PRECISION).to_s
116
+ when "WITHHASH"
117
+ member << point.geohash(REDIS_GEOHASH_SIZE)
118
+ end
119
+ end
120
+
121
+ member
122
+ end
123
+ end
124
+
125
+ def georadius_options(args)
126
+ options = {}
127
+ args = args.map { |arg| arg.to_s.upcase }
128
+
129
+ if idx = args.index("COUNT")
130
+ options[:count] = Integer(args[idx + 1])
131
+ end
132
+
133
+ options[:asc] = true if args.include?("ASC")
134
+ options[:desc] = true if args.include?("DESC")
135
+
136
+ extras = args & ["WITHCOORD", "WITHDIST", "WITHHASH"]
137
+ options[:extras] = extras
138
+
139
+ options
140
+ end
141
+ end
142
+ end
@@ -0,0 +1,84 @@
1
+ module FakeRedis
2
+ class GeoSet
3
+ class Point
4
+ BASE32 = "0123456789bcdefghjkmnpqrstuvwxyz" # (geohash-specific) Base32 map
5
+ EARTH_RADIUS_IN_M = 6_378_100.0
6
+
7
+ attr_reader :lon, :lat, :name
8
+
9
+ def initialize(lon, lat, name)
10
+ @lon = Float(lon)
11
+ @lat = Float(lat)
12
+ @name = name
13
+ end
14
+
15
+ def geohash(precision = 10)
16
+ latlon = [@lat, @lon]
17
+ ranges = [[-90.0, 90.0], [-180.0, 180.0]]
18
+ coordinate = 1
19
+
20
+ (0...precision).map do
21
+ index = 0 # index into base32 map
22
+
23
+ 5.times do |bit|
24
+ mid = (ranges[coordinate][0] + ranges[coordinate][1]) / 2
25
+ if latlon[coordinate] >= mid
26
+ index = index * 2 + 1
27
+ ranges[coordinate][0] = mid
28
+ else
29
+ index *= 2
30
+ ranges[coordinate][1] = mid
31
+ end
32
+
33
+ coordinate ^= 1
34
+ end
35
+
36
+ BASE32[index]
37
+ end.join
38
+ end
39
+
40
+ def distance_to(other)
41
+ lat1 = deg_to_rad(@lat)
42
+ lon1 = deg_to_rad(@lon)
43
+ lat2 = deg_to_rad(other.lat)
44
+ lon2 = deg_to_rad(other.lon)
45
+ haversine_distance(lat1, lon1, lat2, lon2)
46
+ end
47
+
48
+ private
49
+
50
+ def deg_to_rad(deg)
51
+ deg * Math::PI / 180.0
52
+ end
53
+
54
+ def haversine_distance(lat1, lon1, lat2, lon2)
55
+ h = Math.sin((lat2 - lat1) / 2) ** 2 + Math.cos(lat1) * Math.cos(lat2) *
56
+ Math.sin((lon2 - lon1) / 2) ** 2
57
+
58
+ 2 * EARTH_RADIUS_IN_M * Math.asin(Math.sqrt(h))
59
+ end
60
+ end
61
+
62
+ def initialize
63
+ @points = {}
64
+ end
65
+
66
+ def size
67
+ @points.size
68
+ end
69
+
70
+ def add(lon, lat, name)
71
+ @points[name] = Point.new(lon, lat, name)
72
+ end
73
+
74
+ def get(name)
75
+ @points[name]
76
+ end
77
+
78
+ def points_within_radius(center, radius)
79
+ @points.values.select do |point|
80
+ point.distance_to(center) <= radius
81
+ end
82
+ end
83
+ end
84
+ end
@@ -15,8 +15,8 @@ require 'fakeredis'
15
15
  module FakeRedis
16
16
  module Minitest
17
17
  def setup
18
- super
19
18
  Redis::Connection::Memory.reset_all_databases
19
+ super
20
20
  end
21
21
 
22
22
  ::Minitest::Test.send(:include, self)
@@ -6,7 +6,6 @@ module FakeRedis
6
6
  return [] if type(key) == 'none'
7
7
 
8
8
  unless %w(list set zset).include? type(key)
9
- warn "Operation against a key holding the wrong kind of value: Expected list, set or zset at #{key}."
10
9
  raise Redis::CommandError.new("WRONGTYPE Operation against a key holding the wrong kind of value")
11
10
  end
12
11
 
@@ -1,3 +1,3 @@
1
1
  module FakeRedis
2
- VERSION = "0.7.0"
2
+ VERSION = "0.9.0"
3
3
  end
@@ -17,7 +17,7 @@ module FakeRedis
17
17
  def select_by_score min, max
18
18
  min = _floatify(min, true)
19
19
  max = _floatify(max, false)
20
- reject {|_,v| v < min || v > max }
20
+ select {|_,v| v >= min && v <= max }
21
21
  end
22
22
 
23
23
  private
@@ -26,7 +26,7 @@ module FakeRedis
26
26
  def _floatify(str, increment = true)
27
27
  if (( inf = str.to_s.match(/^([+-])?inf/i) ))
28
28
  (inf[1] == "-" ? -1.0 : 1.0) / 0.0
29
- elsif (( number = str.to_s.match(/^\((\d+)/i) ))
29
+ elsif (( number = str.to_s.match(/^\((-?\d+)/i) ))
30
30
  number[1].to_i + (increment ? 1 : -1)
31
31
  else
32
32
  Float str.to_s
data/lib/fakeredis.rb CHANGED
@@ -15,4 +15,20 @@ module FakeRedis
15
15
  def self.disable
16
16
  Redis::Connection.drivers.delete_if {|driver| Redis::Connection::Memory == driver }
17
17
  end
18
+
19
+ def self.disabling
20
+ return yield unless enabled?
21
+
22
+ disable
23
+ yield
24
+ enable
25
+ end
26
+
27
+ def self.enabling
28
+ return yield if enabled?
29
+
30
+ enable
31
+ yield
32
+ disable
33
+ end
18
34
  end