dynamodb-api 0.8.1 → 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
2
  SHA256:
3
- metadata.gz: e7fc7f62b75b2847e3b61765cffcc823b1af80a09f202cceef1a74d3a549de43
4
- data.tar.gz: e1a80833c322c480c084fe33512db8012f25f683147de888e40f6a6d046677d9
3
+ metadata.gz: 884abb76fafa637862d01d8e3f75b0a49c34653d5aeb24a593f8865aae6d8011
4
+ data.tar.gz: fba9e304ecffb92392d602982d1f2e4f82c36b6b0dce4c702a378c4280d5c0a4
5
5
  SHA512:
6
- metadata.gz: 4e3a874f279f32c37b16a77ba649aa9cfc83615103f5df9b58a64a06496e796d31396728e0e0e1c6d7bc6538ea0be5c02c49249933f6c4bfc830f71498b88a89
7
- data.tar.gz: 9628ccc8dc2ff42c0ec495a5485546091f82e29ba1895e4345c1a7a31d7a2298f629a7e4370caeb51e6966c4076aba9cadc81e7500c0595c82a1c867d205b171
6
+ metadata.gz: 3c12330b1af83f9a73ba0965cc5c8189418825e26f98d3f859e5171666960e1f5d17c616534fb051d17e06e293234e4e1161182c5f3caa769e66e0d1842e7fbf
7
+ data.tar.gz: 1a2b02ae868c6392dd40863de0c864f69bd2501186b7aef53f0cd407be968f5f5490f2ac8b76919e2acb1bdded7f56b9ff68b664a607fbc0d85126cbb8871d55
@@ -21,7 +21,7 @@ Aws.config.update(
21
21
  )
22
22
 
23
23
  Dynamodb::Api.config do |config|
24
- config.endpoint = 'http://0.0.0.0:8000'
24
+ config.endpoint = 'http://dynamodb:8000'
25
25
  end
26
26
 
27
27
  IRB.start(__FILE__)
@@ -7,6 +7,6 @@ services:
7
7
  volumes:
8
8
  - .:/app
9
9
  dynamodb:
10
- image: cnadiminti/dynamodb-local:2018-04-11
10
+ image: amazon/dynamodb-local
11
11
  ports:
12
12
  - 8000:8000
@@ -12,9 +12,13 @@ module Dynamodb
12
12
  raise NotImplementedError, "You must implement #{self.class}##{__method__}"
13
13
  end
14
14
 
15
+ def next
16
+ raise NotImplementedError, "You must implement #{self.class}##{__method__}"
17
+ end
18
+
15
19
  private
16
20
 
17
- def build_query
21
+ def build_input
18
22
  raise NotImplementedError, "You must implement #{self.class}##{__method__}"
19
23
  end
20
24
 
@@ -30,20 +34,31 @@ module Dynamodb
30
34
  clause&.name ? clause.name : SelectClause.new.name
31
35
  end
32
36
 
33
- def build_filter_clause
34
- return {} if filter_clause&.expression.blank?
35
- {
36
- filter_expression: filter_clause.expression,
37
- expression_attribute_values: filter_clause.values,
38
- }
37
+ # Build filter clause.
38
+ # `filter_expression`: e.g. "Artist = :a"
39
+ # `expression_attribute_values`: e.g. { ":a" => "No One You Know" }
40
+ #
41
+ # @param input [Aws::DynamoDB::Types::ScanInput]
42
+ # @return [Aws::DynamoDB::Types::ScanInput]
43
+ def build_filter_clause(input)
44
+ return input if filter_clause&.expression.blank?
45
+ input[:filter_expression] = filter_clause.expression
46
+ if filter_clause.values.present?
47
+ if input[:expression_attribute_values].nil?
48
+ input[:expression_attribute_values] = {}
49
+ end
50
+ input[:expression_attribute_values].
51
+ merge!(filter_clause.values)
52
+ end
53
+ input
39
54
  end
40
55
 
41
- def build_expression_attribute_names(params)
56
+ def build_expression_attribute_names(input)
42
57
  if filter_clause&.reserved_words.present?
43
58
  expression_attribute.add(filter_clause.reserved_words)
44
59
  end
45
60
  if expression_attribute.names.present?
46
- params[:expression_attribute_names] = expression_attribute.names
61
+ input[:expression_attribute_names] = expression_attribute.names
47
62
  end
48
63
  end
49
64
  end
@@ -16,6 +16,8 @@ module Dynamodb
16
16
  option :table_name_prefix, default: ''
17
17
  option :index_name_prefix, default: ''
18
18
 
19
+ # @param value [String] the table name
20
+ # @return [String] the table name
19
21
  def build_table_name(value)
20
22
  return value unless table_name_prefix?
21
23
  "#{table_name_prefix}#{value}"
@@ -4,21 +4,24 @@ module Dynamodb
4
4
  module Api
5
5
  module Map
6
6
  class Operator # :nodoc:
7
+ # Replace the Dynamodb Operators
8
+ # @param k [String] The Dynamodb Operator
9
+ # @return [String]
7
10
  def self.key(k)
8
11
  k = k.gsub(' ', '')
9
12
  case k
10
- when '='
11
- 'EQ'
12
- when '!='
13
- 'NE'
14
- when '<='
15
- 'LE'
16
- when '<'
17
- 'LT'
18
- when '>='
19
- 'GE'
20
- when '>'
21
- 'GT'
13
+ when 'EQ'
14
+ '='
15
+ when 'NE'
16
+ '!='
17
+ when 'LE'
18
+ '<='
19
+ when 'LT'
20
+ '<'
21
+ when 'GE'
22
+ '>='
23
+ when 'GT'
24
+ '>'
22
25
  else
23
26
  k
24
27
  end
@@ -6,16 +6,16 @@ module Dynamodb
6
6
  module Api
7
7
  class Query < Base # :nodoc:
8
8
  def all
9
- result = Adapter.client.query(build_query)
9
+ result = Adapter.client.query(build_input)
10
10
  @last_evaluated_key = result.last_evaluated_key
11
11
  result
12
12
  end
13
13
 
14
14
  def next
15
15
  return nil if @last_evaluated_key.blank?
16
- result = Adapter.client.query(
17
- build_query.merge(exclusive_start_key: @last_evaluated_key)
18
- )
16
+ input = build_input
17
+ input[:exclusive_start_key] = @last_evaluated_key
18
+ result = Adapter.client.query(input)
19
19
  @last_evaluated_key = result.last_evaluated_key
20
20
  return nil if result.count.zero?
21
21
  result
@@ -23,21 +23,34 @@ module Dynamodb
23
23
 
24
24
  private
25
25
 
26
- def build_query
27
- build_params = base_params.merge(build_filter_clause)
28
- build_params[:scan_index_forward] = order_direct(order_clause)
29
- build_params[:select] = select_name(select_clause)
30
- build_expression_attribute_names(build_params)
31
- build_params[:limit] = limit_clause.number if limit_clause&.number
32
- build_params
26
+ # Build options.
27
+ #
28
+ # @return [Aws::DynamoDB::Types::ScanInput]
29
+ def build_input
30
+ input = Aws::DynamoDB::Types::QueryInput.new
31
+ input[:expression_attribute_values] = {}
32
+ input = base_input(input)
33
+ input = build_filter_clause(input)
34
+ input[:scan_index_forward] = order_direct(order_clause)
35
+ input[:select] = select_name(select_clause)
36
+ build_expression_attribute_names(input)
37
+ input[:limit] = limit_clause.number if limit_clause&.number
38
+ input
33
39
  end
34
40
 
35
- def base_params
36
- {
37
- table_name: from_clause.name,
38
- index_name: index_clause.name,
39
- key_conditions: where_clause.key_conditions,
40
- }
41
+ # Build required options.
42
+ # `key_condition_expression`: e.g. "Artist = :a"
43
+ # `expression_attribute_values`: e.g. { ":a" => "No One You Know" }
44
+ #
45
+ # @param input [Aws::DynamoDB::Types::ScanInput]
46
+ # @return [Aws::DynamoDB::Types::ScanInput]
47
+ def base_input(input)
48
+ input[:table_name] = from_clause.name
49
+ input[:index_name] = index_clause.name
50
+ input[:key_condition_expression] = where_clause.key_condition
51
+ input[:expression_attribute_values].
52
+ merge!(where_clause.attribute_values)
53
+ input
41
54
  end
42
55
  end
43
56
  end
@@ -24,8 +24,8 @@ module Dynamodb
24
24
  self
25
25
  end
26
26
 
27
- def where(key_conditions)
28
- self.where_clause = Relation::WhereClause.new(key_conditions)
27
+ def where(expression)
28
+ self.where_clause = Relation::WhereClause.new(expression)
29
29
  self
30
30
  end
31
31
 
@@ -4,24 +4,89 @@ module Dynamodb
4
4
  module Api
5
5
  module Relation
6
6
  class WhereClause # :nodoc:
7
- attr_reader :key_conditions
7
+ attr_reader :key_condition
8
+ attr_reader :attribute_values
8
9
 
9
10
  KEY = 0
10
11
  VALUE = 2
11
12
  OPERATOR = 1
13
+ FROM = 0
14
+ TO = 1
12
15
 
13
- def initialize(key_conditions)
14
- @key_conditions = build(key_conditions)
16
+ # @param conditions [Array]
17
+ def initialize(conditions)
18
+ built_conditions = build(conditions)
19
+ @key_condition = built_conditions[:key_conditions]
20
+ @attribute_values = built_conditions[:attribute_values]
15
21
  end
16
22
 
17
23
  private
18
24
 
19
- def build(key_conditions)
20
- conditions = format_conditions(key_conditions)
21
- conditions.each_with_object({}) do |c, h|
22
- h[c[KEY]] = {
23
- attribute_value_list: format_value(c[VALUE]),
24
- comparison_operator: Map::Operator.key(c[OPERATOR]),
25
+ # Build where clause.
26
+ #
27
+ # @param conditions [Array]
28
+ def build(conditions)
29
+ init = { key_conditions: [], attribute_values: {} }
30
+ conditions = format_conditions(conditions)
31
+ built = conditions.each_with_object(init) do |c, h|
32
+ h[:key_conditions] <<
33
+ format_key_condition(c[KEY], c[OPERATOR])
34
+ h[:attribute_values].
35
+ merge!(format_values(c[KEY], c[OPERATOR], c[VALUE]))
36
+ end
37
+ built[:key_conditions] =
38
+ built[:key_conditions].join(' AND ')
39
+ built
40
+ end
41
+
42
+ # Format to the `key_condition_expression`.
43
+ # e.g.
44
+ # `format_key_condition("Artist", "=")` =>
45
+ # `"Artist = :Artist"`
46
+ #
47
+ # `format_key_condition("Artist", "begins_with")` =>
48
+ # `"begins_with(Artist, :Artist)"`
49
+ #
50
+ # `format_key_condition("Year", "between")` =>
51
+ # `"Year between :from_Year and :to_Year"`
52
+ #
53
+ # @param key [String] a attribute name
54
+ # @param operator [String] a operator
55
+ # @return [String] Formatted expression.
56
+ def format_key_condition(key, operator)
57
+ case operator.downcase
58
+ when 'begins_with'
59
+ "#{operator.downcase}(#{key}, :#{key})"
60
+ when 'between'
61
+ "#{key} #{operator.downcase}" \
62
+ " :from_#{key} AND :to_#{key}"
63
+ else
64
+ "#{key} #{Map::Operator.key(operator)} :#{key}"
65
+ end
66
+ end
67
+
68
+ # Format to the `expression_attribute_values`
69
+ # e.g.
70
+ # `format_values("Artist", "=", "blue")` =>
71
+ # `{ ":Artist" => "blue" }`
72
+ #
73
+ # `format_values("Year", "between", [1999, 2020])` =>
74
+ # `{ ":from_Year" => 1999, ":to_Year" => 2020 }`
75
+ #
76
+ # @param key [String] a attribute name
77
+ # @param operator [String] a operator
78
+ # @param values [Object] values
79
+ # @return [Hash<Object>] Formatted expression.
80
+ def format_values(key, operator, values)
81
+ case operator.downcase
82
+ when 'between'
83
+ {
84
+ ":from_#{key}" => values[FROM],
85
+ ":to_#{key}" => values[TO],
86
+ }
87
+ else
88
+ {
89
+ ":#{key}" => values.is_a?(Array) ? values[0] : values,
25
90
  }
26
91
  end
27
92
  end
@@ -30,11 +95,6 @@ module Dynamodb
30
95
  return [conditions] unless conditions[0].is_a?(Array)
31
96
  conditions
32
97
  end
33
-
34
- def format_value(value)
35
- return [value] unless value.is_a?(Array)
36
- value
37
- end
38
98
  end
39
99
  end
40
100
  end
@@ -6,36 +6,36 @@ module Dynamodb
6
6
  module Api
7
7
  class Scan < Base # :nodoc:
8
8
  def all
9
- result = Adapter.client.scan(build_query)
9
+ result = Adapter.client.scan(build_input)
10
10
  @last_evaluated_key = result.last_evaluated_key
11
11
  result
12
12
  end
13
13
 
14
14
  def next
15
15
  return nil if @last_evaluated_key.blank?
16
- result = Adapter.client.scan(
17
- build_query.merge(exclusive_start_key: @last_evaluated_key)
18
- )
16
+ input = build_input
17
+ input[:exclusive_start_key] = @last_evaluated_key
18
+ result = Adapter.client.scan(input)
19
19
  @last_evaluated_key = result.last_evaluated_key
20
20
  result
21
21
  end
22
22
 
23
23
  private
24
24
 
25
- def build_query
26
- build_params = base_params.merge(build_filter_clause)
27
- build_params[:index_name] = index_clause.name if index_clause&.name
28
- build_params[:key_conditions] = where_clause.key_conditions if where_clause&.key_conditions
29
- build_params[:select] = select_name(select_clause)
30
- build_expression_attribute_names(build_params)
31
- build_params[:limit] = limit_clause.number if limit_clause&.number
32
- build_params
25
+ def build_input
26
+ input = Aws::DynamoDB::Types::ScanInput.new
27
+ input = base_input(input)
28
+ input = build_filter_clause(input)
29
+ input[:index_name] = index_clause.name if index_clause&.name
30
+ input[:select] = select_name(select_clause)
31
+ build_expression_attribute_names(input)
32
+ input[:limit] = limit_clause.number if limit_clause&.number
33
+ input
33
34
  end
34
35
 
35
- def base_params
36
- {
37
- table_name: from_clause.name,
38
- }
36
+ def base_input(input)
37
+ input[:table_name] = from_clause.name
38
+ input
39
39
  end
40
40
  end
41
41
  end
@@ -1,5 +1,5 @@
1
1
  module Dynamodb
2
2
  module Api
3
- VERSION = '0.8.1'.freeze
3
+ VERSION = '0.9.0'.freeze
4
4
  end
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dynamodb-api
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.8.1
4
+ version: 0.9.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - WalkerSumida
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2019-06-05 00:00:00.000000000 Z
11
+ date: 2020-02-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: aws-sdk
@@ -193,8 +193,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
193
193
  - !ruby/object:Gem::Version
194
194
  version: '0'
195
195
  requirements: []
196
- rubyforge_project:
197
- rubygems_version: 2.7.6
196
+ rubygems_version: 3.0.3
198
197
  signing_key:
199
198
  specification_version: 4
200
199
  summary: aws dynamodb api