gcloud 0.8.2 → 0.9.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +8 -8
- data/CHANGELOG.md +26 -0
- data/OVERVIEW.md +10 -8
- data/lib/gcloud.rb +12 -13
- data/lib/gcloud/bigquery/dataset/list.rb +2 -4
- data/lib/gcloud/bigquery/job/list.rb +3 -5
- data/lib/gcloud/bigquery/table/list.rb +3 -5
- data/lib/gcloud/datastore.rb +326 -97
- data/lib/gcloud/datastore/commit.rb +73 -56
- data/lib/gcloud/datastore/credentials.rb +1 -12
- data/lib/gcloud/datastore/cursor.rb +76 -0
- data/lib/gcloud/datastore/dataset.rb +337 -134
- data/lib/gcloud/datastore/dataset/lookup_results.rb +12 -12
- data/lib/gcloud/datastore/dataset/query_results.rb +117 -27
- data/lib/gcloud/datastore/entity.rb +159 -93
- data/lib/gcloud/datastore/errors.rb +0 -21
- data/lib/gcloud/datastore/gql_query.rb +211 -0
- data/lib/gcloud/datastore/grpc_utils.rb +131 -0
- data/lib/gcloud/datastore/key.rb +74 -65
- data/lib/gcloud/datastore/properties.rb +14 -1
- data/lib/gcloud/datastore/query.rb +188 -52
- data/lib/gcloud/datastore/service.rb +161 -0
- data/lib/gcloud/datastore/transaction.rb +175 -60
- data/lib/gcloud/dns/change/list.rb +2 -4
- data/lib/gcloud/dns/record/list.rb +2 -4
- data/lib/gcloud/dns/zone/list.rb +2 -4
- data/lib/gcloud/grpc_utils.rb +11 -0
- data/lib/gcloud/logging/entry.rb +6 -17
- data/lib/gcloud/logging/entry/list.rb +8 -9
- data/lib/gcloud/logging/metric/list.rb +4 -5
- data/lib/gcloud/logging/resource.rb +1 -12
- data/lib/gcloud/logging/resource_descriptor.rb +9 -12
- data/lib/gcloud/logging/resource_descriptor/list.rb +4 -5
- data/lib/gcloud/logging/sink/list.rb +4 -5
- data/lib/gcloud/pubsub/message.rb +1 -3
- data/lib/gcloud/pubsub/subscription.rb +5 -7
- data/lib/gcloud/pubsub/topic.rb +1 -3
- data/lib/gcloud/resource_manager/project/list.rb +2 -4
- data/lib/gcloud/translate/api.rb +5 -3
- data/lib/gcloud/translate/connection.rb +4 -4
- data/lib/gcloud/version.rb +1 -1
- metadata +9 -20
- data/lib/gcloud/datastore/connection.rb +0 -203
- data/lib/gcloud/datastore/proto.rb +0 -266
- data/lib/gcloud/proto/datastore_v1.pb.rb +0 -377
- data/lib/google/protobuf/any.rb +0 -17
- data/lib/google/protobuf/api.rb +0 -31
- data/lib/google/protobuf/duration.rb +0 -17
- data/lib/google/protobuf/empty.rb +0 -15
- data/lib/google/protobuf/field_mask.rb +0 -16
- data/lib/google/protobuf/source_context.rb +0 -16
- data/lib/google/protobuf/struct.rb +0 -35
- data/lib/google/protobuf/timestamp.rb +0 -17
- data/lib/google/protobuf/type.rb +0 -79
- data/lib/google/protobuf/wrappers.rb +0 -48
@@ -31,27 +31,6 @@ module Gcloud
|
|
31
31
|
class KeyfileError < Gcloud::Datastore::Error
|
32
32
|
end
|
33
33
|
|
34
|
-
##
|
35
|
-
# # ApiError
|
36
|
-
#
|
37
|
-
# Raised when an API call is not successful.
|
38
|
-
class ApiError < Gcloud::Datastore::Error
|
39
|
-
##
|
40
|
-
# The API method of the failed HTTP request.
|
41
|
-
attr_reader :method
|
42
|
-
|
43
|
-
##
|
44
|
-
# The response object of the failed HTTP request.
|
45
|
-
attr_reader :response
|
46
|
-
|
47
|
-
# @private
|
48
|
-
def initialize method, response = nil
|
49
|
-
super("API call to #{method} was not successful")
|
50
|
-
@method = method
|
51
|
-
@response = response
|
52
|
-
end
|
53
|
-
end
|
54
|
-
|
55
34
|
##
|
56
35
|
# # PropertyError
|
57
36
|
#
|
@@ -0,0 +1,211 @@
|
|
1
|
+
# Copyright 2016 Google Inc. All rights reserved.
|
2
|
+
#
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
4
|
+
# you may not use this file except in compliance with the License.
|
5
|
+
# You may obtain a copy of the License at
|
6
|
+
#
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
8
|
+
#
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
12
|
+
# See the License for the specific language governing permissions and
|
13
|
+
# limitations under the License.
|
14
|
+
|
15
|
+
|
16
|
+
require "gcloud/datastore/entity"
|
17
|
+
require "gcloud/datastore/key"
|
18
|
+
|
19
|
+
module Gcloud
|
20
|
+
module Datastore
|
21
|
+
##
|
22
|
+
# # GqlQuery
|
23
|
+
#
|
24
|
+
# Represents a GQL query.
|
25
|
+
#
|
26
|
+
# GQL is a SQL-like language for retrieving entities or keys from Datastore.
|
27
|
+
#
|
28
|
+
# @see https://cloud.google.com/datastore/docs/apis/gql/gql_reference GQL
|
29
|
+
# Reference
|
30
|
+
#
|
31
|
+
# @example
|
32
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
33
|
+
# gql_query.query_string = "SELECT * FROM Task ORDER BY created ASC"
|
34
|
+
# tasks = datastore.run gql_query
|
35
|
+
#
|
36
|
+
class GqlQuery
|
37
|
+
##
|
38
|
+
# Returns a new GqlQuery instance.
|
39
|
+
#
|
40
|
+
# @example
|
41
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
42
|
+
#
|
43
|
+
def initialize
|
44
|
+
@grpc = Google::Datastore::V1beta3::GqlQuery.new
|
45
|
+
end
|
46
|
+
|
47
|
+
##
|
48
|
+
# The GQL query string for the query. The string may contain named
|
49
|
+
# or positional argument binding sites that start with `@`. Corresponding
|
50
|
+
# binding values should be set with {#named_bindings=} or
|
51
|
+
# {#positional_bindings=}.
|
52
|
+
#
|
53
|
+
# @return [String] a GQL statement
|
54
|
+
#
|
55
|
+
def query_string
|
56
|
+
gql = @grpc.query_string.dup
|
57
|
+
gql.freeze
|
58
|
+
gql
|
59
|
+
end
|
60
|
+
|
61
|
+
##
|
62
|
+
# Sets the GQL query string for the query. The string may contain named
|
63
|
+
# or positional argument binding sites that start with `@`. Corresponding
|
64
|
+
# binding values should be set with {#named_bindings=} or
|
65
|
+
# {#positional_bindings=}.
|
66
|
+
#
|
67
|
+
# See the [GQL
|
68
|
+
# Reference](https://cloud.google.com/datastore/docs/apis/gql/gql_reference).
|
69
|
+
#
|
70
|
+
# @param [String] new_query_string a valid GQL statement
|
71
|
+
#
|
72
|
+
# @example
|
73
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
74
|
+
# gql_query.query_string = "SELECT * FROM Task " \
|
75
|
+
# "WHERE done = @done AND priority = @priority"
|
76
|
+
# gql_query.named_bindings = {done: false, priority: 4}
|
77
|
+
#
|
78
|
+
def query_string= new_query_string
|
79
|
+
@grpc.query_string = new_query_string.to_s
|
80
|
+
end
|
81
|
+
|
82
|
+
##
|
83
|
+
# Whether the query may contain literal values. When false, the query
|
84
|
+
# string must not contain any literals and instead must bind all values
|
85
|
+
# using {#named_bindings=} or {#positional_bindings=}.
|
86
|
+
#
|
87
|
+
# @return [Boolean] `true` if the query may contain literal values
|
88
|
+
#
|
89
|
+
def allow_literals
|
90
|
+
@grpc.allow_literals
|
91
|
+
end
|
92
|
+
|
93
|
+
##
|
94
|
+
# Sets whether the query may contain literal values. When false, the query
|
95
|
+
# string must not contain any literals and instead must bind all values
|
96
|
+
# using {#named_bindings=} or {#positional_bindings=}.
|
97
|
+
#
|
98
|
+
# @param [Boolean] new_allow_literals `true` if the query may contain
|
99
|
+
# literal values
|
100
|
+
#
|
101
|
+
# @example
|
102
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
103
|
+
# gql_query.query_string = "SELECT * FROM Task " \
|
104
|
+
# "WHERE completed = false AND priority = 4"
|
105
|
+
# gql_query.allow_literals = true
|
106
|
+
#
|
107
|
+
def allow_literals= new_allow_literals
|
108
|
+
@grpc.allow_literals = new_allow_literals
|
109
|
+
end
|
110
|
+
|
111
|
+
##
|
112
|
+
# The named binding values for a query that contains named argument
|
113
|
+
# binding sites that start with `@`.
|
114
|
+
#
|
115
|
+
# @return [Hash] a frozen hash that maps the binding site names in the
|
116
|
+
# query string to valid GQL arguments
|
117
|
+
#
|
118
|
+
def named_bindings
|
119
|
+
bindings = Hash[@grpc.named_bindings.map do |name, gql_query_param|
|
120
|
+
if gql_query_param.cursor
|
121
|
+
[name, Cursor.from_grpc(gql_query_param.cursor)]
|
122
|
+
else
|
123
|
+
[name, GRPCUtils.from_value(gql_query_param.value)]
|
124
|
+
end
|
125
|
+
end]
|
126
|
+
bindings.freeze
|
127
|
+
bindings
|
128
|
+
end
|
129
|
+
|
130
|
+
##
|
131
|
+
# Sets named binding values for a query that contains named argument
|
132
|
+
# binding sites that start with `@`.
|
133
|
+
#
|
134
|
+
# @param [Hash] new_named_bindings a hash that maps the binding site names
|
135
|
+
# in the query string to valid GQL arguments
|
136
|
+
#
|
137
|
+
# @example
|
138
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
139
|
+
# gql_query.query_string = "SELECT * FROM Task " \
|
140
|
+
# "WHERE done = @done AND priority = @priority"
|
141
|
+
# gql_query.named_bindings = {done: false, priority: 4}
|
142
|
+
#
|
143
|
+
def named_bindings= new_named_bindings
|
144
|
+
@grpc.named_bindings.clear
|
145
|
+
new_named_bindings.map do |name, value|
|
146
|
+
if value.is_a? Gcloud::Datastore::Cursor
|
147
|
+
@grpc.named_bindings[name.to_s] = \
|
148
|
+
Google::Datastore::V1beta3::GqlQueryParameter.new(
|
149
|
+
cursor: value.to_grpc)
|
150
|
+
else
|
151
|
+
@grpc.named_bindings[name.to_s] = \
|
152
|
+
Google::Datastore::V1beta3::GqlQueryParameter.new(
|
153
|
+
value: GRPCUtils.to_value(value))
|
154
|
+
end
|
155
|
+
end
|
156
|
+
end
|
157
|
+
|
158
|
+
##
|
159
|
+
# The binding values for a query that contains numbered argument binding
|
160
|
+
# sites that start with `@`.
|
161
|
+
#
|
162
|
+
# @return [Array] a frozen array containing the query arguments in the
|
163
|
+
# order of the numbered binding sites in the query string
|
164
|
+
#
|
165
|
+
def positional_bindings
|
166
|
+
bindings = @grpc.positional_bindings.map do |gql_query_param|
|
167
|
+
if gql_query_param.cursor
|
168
|
+
Cursor.from_grpc gql_query_param.cursor
|
169
|
+
else
|
170
|
+
GRPCUtils.from_value gql_query_param.value
|
171
|
+
end
|
172
|
+
end
|
173
|
+
bindings.freeze
|
174
|
+
bindings
|
175
|
+
end
|
176
|
+
|
177
|
+
##
|
178
|
+
# Sets the binding values for a query that contains numbered argument
|
179
|
+
# binding sites that start with `@`.
|
180
|
+
#
|
181
|
+
# @param [Array] new_positional_bindings query arguments in the order
|
182
|
+
# of the numbered binding sites in the query string
|
183
|
+
#
|
184
|
+
# @example
|
185
|
+
# gql_query = Gcloud::Datastore::GqlQuery.new
|
186
|
+
# gql_query.query_string = "SELECT * FROM Task" \
|
187
|
+
# "WHERE completed = @1 AND priority = @2"
|
188
|
+
# gql_query.positional_bindings = [false, 4]
|
189
|
+
#
|
190
|
+
def positional_bindings= new_positional_bindings
|
191
|
+
@grpc.positional_bindings.clear
|
192
|
+
new_positional_bindings.map do |value|
|
193
|
+
if value.is_a? Gcloud::Datastore::Cursor
|
194
|
+
@grpc.positional_bindings << \
|
195
|
+
Google::Datastore::V1beta3::GqlQueryParameter.new(
|
196
|
+
cursor: value.to_grpc)
|
197
|
+
else
|
198
|
+
@grpc.positional_bindings << \
|
199
|
+
Google::Datastore::V1beta3::GqlQueryParameter.new(
|
200
|
+
value: GRPCUtils.to_value(value))
|
201
|
+
end
|
202
|
+
end
|
203
|
+
end
|
204
|
+
|
205
|
+
# @private
|
206
|
+
def to_grpc
|
207
|
+
@grpc
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
end
|
@@ -0,0 +1,131 @@
|
|
1
|
+
# Copyright 2016 Google Inc. All rights reserved.
|
2
|
+
#
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
4
|
+
# you may not use this file except in compliance with the License.
|
5
|
+
# You may obtain a copy of the License at
|
6
|
+
#
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
8
|
+
#
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
12
|
+
# See the License for the specific language governing permissions and
|
13
|
+
# limitations under the License.
|
14
|
+
|
15
|
+
|
16
|
+
require "gcloud/grpc_utils"
|
17
|
+
require "gcloud/datastore/errors"
|
18
|
+
require "stringio"
|
19
|
+
|
20
|
+
module Gcloud
|
21
|
+
##
|
22
|
+
# @private Conversion to/from Datastore GRPC objects.
|
23
|
+
# This file adds Datastore methods to GRPCUtils.
|
24
|
+
module GRPCUtils
|
25
|
+
# rubocop:disable all
|
26
|
+
|
27
|
+
PROP_FILTER_OPS = { "<" => :LESS_THAN,
|
28
|
+
"lt" => :LESS_THAN,
|
29
|
+
"<=" => :LESS_THAN_OR_EQUAL,
|
30
|
+
"lte" => :LESS_THAN_OR_EQUAL,
|
31
|
+
">" => :GREATER_THAN,
|
32
|
+
"gt" => :GREATER_THAN,
|
33
|
+
">=" => :GREATER_THAN_OR_EQUAL,
|
34
|
+
"gte" => :GREATER_THAN_OR_EQUAL,
|
35
|
+
"=" => :EQUAL,
|
36
|
+
"eq" => :EQUAL,
|
37
|
+
"eql" => :EQUAL,
|
38
|
+
"~" => :HAS_ANCESTOR,
|
39
|
+
"~>" => :HAS_ANCESTOR,
|
40
|
+
"ancestor" => :HAS_ANCESTOR,
|
41
|
+
"has_ancestor" => :HAS_ANCESTOR,
|
42
|
+
"has ancestor" => :HAS_ANCESTOR }
|
43
|
+
|
44
|
+
##
|
45
|
+
# Get a property filter operator from op
|
46
|
+
def self.to_prop_filter_op op
|
47
|
+
PROP_FILTER_OPS[op.to_s.downcase] || :EQUAL
|
48
|
+
end
|
49
|
+
|
50
|
+
##
|
51
|
+
# Gets an object from a Google::Datastore::V1beta3::Value.
|
52
|
+
def self.from_value grpc_value
|
53
|
+
if grpc_value.value_type == :null_value
|
54
|
+
return nil
|
55
|
+
elsif grpc_value.value_type == :key_value
|
56
|
+
return Gcloud::Datastore::Key.from_grpc(grpc_value.key_value)
|
57
|
+
elsif grpc_value.value_type == :entity_value
|
58
|
+
return Gcloud::Datastore::Entity.from_grpc(grpc_value.entity_value)
|
59
|
+
elsif grpc_value.value_type == :boolean_value
|
60
|
+
return grpc_value.boolean_value
|
61
|
+
elsif grpc_value.value_type == :double_value
|
62
|
+
return grpc_value.double_value
|
63
|
+
elsif grpc_value.value_type == :integer_value
|
64
|
+
return grpc_value.integer_value
|
65
|
+
elsif grpc_value.value_type == :string_value
|
66
|
+
return grpc_value.string_value
|
67
|
+
elsif grpc_value.value_type == :array_value
|
68
|
+
return Array(grpc_value.array_value.values).map { |v| from_value v }
|
69
|
+
elsif grpc_value.value_type == :timestamp_value
|
70
|
+
return Time.at grpc_value.timestamp_value.seconds,
|
71
|
+
grpc_value.timestamp_value.nanos/1000.0
|
72
|
+
elsif grpc_value.value_type == :geo_point_value
|
73
|
+
return grpc_value.geo_point_value.to_hash
|
74
|
+
elsif grpc_value.value_type == :blob_value
|
75
|
+
return StringIO.new(grpc_value.blob_value.force_encoding("ASCII-8BIT"))
|
76
|
+
else
|
77
|
+
nil
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
##
|
82
|
+
# Stores an object into a Google::Datastore::V1beta3::Value.
|
83
|
+
def self.to_value value
|
84
|
+
v = Google::Datastore::V1beta3::Value.new
|
85
|
+
if NilClass === value
|
86
|
+
v.null_value = :NULL_VALUE
|
87
|
+
elsif TrueClass === value
|
88
|
+
v.boolean_value = true
|
89
|
+
elsif FalseClass === value
|
90
|
+
v.boolean_value = false
|
91
|
+
elsif Integer === value
|
92
|
+
v.integer_value = value
|
93
|
+
elsif Float === value
|
94
|
+
v.double_value = value
|
95
|
+
elsif defined?(BigDecimal) && BigDecimal === value
|
96
|
+
v.double_value = value
|
97
|
+
elsif Gcloud::Datastore::Key === value
|
98
|
+
v.key_value = value.to_grpc
|
99
|
+
elsif Gcloud::Datastore::Entity === value
|
100
|
+
v.entity_value = value.to_grpc
|
101
|
+
elsif String === value
|
102
|
+
v.string_value = value
|
103
|
+
elsif Array === value
|
104
|
+
v.array_value = Google::Datastore::V1beta3::ArrayValue.new(
|
105
|
+
values: value.map { |v| to_value v }
|
106
|
+
)
|
107
|
+
elsif value.respond_to? :to_time
|
108
|
+
v.timestamp_value = Google::Protobuf::Timestamp.new(
|
109
|
+
seconds: value.to_time.to_i, nanos: value.to_time.nsec)
|
110
|
+
elsif value.respond_to?(:to_hash) && value.keys.sort == [:latitude, :longitude]
|
111
|
+
v.geo_point_value = Google::Type::LatLng.new(value)
|
112
|
+
elsif value.respond_to?(:read) && value.respond_to?(:rewind)
|
113
|
+
value.rewind
|
114
|
+
v.blob_value = value.read.force_encoding("ASCII-8BIT")
|
115
|
+
else
|
116
|
+
fail Gcloud::Datastore::PropertyError,
|
117
|
+
"A property of type #{value.class} is not supported."
|
118
|
+
end
|
119
|
+
v
|
120
|
+
end
|
121
|
+
|
122
|
+
def self.encode_bytes bytes
|
123
|
+
Array(bytes.to_s).pack("m").chomp.encode("ASCII-8BIT")
|
124
|
+
end
|
125
|
+
|
126
|
+
def self.decode_bytes bytes
|
127
|
+
bytes.to_s.unpack("m").first.force_encoding Encoding::ASCII_8BIT
|
128
|
+
end
|
129
|
+
# rubocop:enable all
|
130
|
+
end
|
131
|
+
end
|
data/lib/gcloud/datastore/key.rb
CHANGED
@@ -13,8 +13,6 @@
|
|
13
13
|
# limitations under the License.
|
14
14
|
|
15
15
|
|
16
|
-
require "gcloud/datastore/proto"
|
17
|
-
|
18
16
|
module Gcloud
|
19
17
|
module Datastore
|
20
18
|
##
|
@@ -26,7 +24,7 @@ module Gcloud
|
|
26
24
|
# ID, assigned automatically by Datastore.
|
27
25
|
#
|
28
26
|
# @example
|
29
|
-
#
|
27
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
30
28
|
#
|
31
29
|
class Key
|
32
30
|
##
|
@@ -35,14 +33,14 @@ module Gcloud
|
|
35
33
|
# @return [String]
|
36
34
|
#
|
37
35
|
# @example
|
38
|
-
# key = Gcloud::Datastore::Key.new "
|
39
|
-
# key.kind #=> "
|
36
|
+
# key = Gcloud::Datastore::Key.new "TaskList"
|
37
|
+
# key.kind #=> "TaskList"
|
40
38
|
# key.kind = "Task"
|
41
39
|
#
|
42
40
|
attr_accessor :kind
|
43
41
|
|
44
42
|
##
|
45
|
-
# The
|
43
|
+
# The project of the Key.
|
46
44
|
#
|
47
45
|
# @return [String]
|
48
46
|
#
|
@@ -52,11 +50,13 @@ module Gcloud
|
|
52
50
|
# gcloud = Gcloud.new "my-todo-project",
|
53
51
|
# "/path/to/keyfile.json"
|
54
52
|
#
|
55
|
-
#
|
56
|
-
#
|
57
|
-
#
|
53
|
+
# datastore = gcloud.datastore
|
54
|
+
# task = datastore.find "Task", "sampleTask"
|
55
|
+
# task.key.project #=> "my-todo-project"
|
58
56
|
#
|
59
|
-
attr_accessor :
|
57
|
+
attr_accessor :project
|
58
|
+
alias_method :dataset_id, :project
|
59
|
+
alias_method :dataset_id=, :project=
|
60
60
|
|
61
61
|
##
|
62
62
|
# The namespace of the Key.
|
@@ -69,9 +69,9 @@ module Gcloud
|
|
69
69
|
# gcloud = Gcloud.new "my-todo-project",
|
70
70
|
# "/path/to/keyfile.json"
|
71
71
|
#
|
72
|
-
#
|
73
|
-
#
|
74
|
-
#
|
72
|
+
# datastore = gcloud.datastore
|
73
|
+
# task = datastore.find "Task", "sampleTask"
|
74
|
+
# task.key.namespace #=> "ns~todo-project"
|
75
75
|
#
|
76
76
|
attr_accessor :namespace
|
77
77
|
|
@@ -85,7 +85,7 @@ module Gcloud
|
|
85
85
|
# @return [Gcloud::Datastore::Dataset::Key]
|
86
86
|
#
|
87
87
|
# @example
|
88
|
-
#
|
88
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
89
89
|
#
|
90
90
|
def initialize kind = nil, id_or_name = nil
|
91
91
|
@kind = kind
|
@@ -103,12 +103,12 @@ module Gcloud
|
|
103
103
|
# @return [Integer, nil]
|
104
104
|
#
|
105
105
|
# @example
|
106
|
-
#
|
107
|
-
#
|
108
|
-
#
|
109
|
-
#
|
110
|
-
#
|
111
|
-
#
|
106
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
107
|
+
# task_key.id #=> nil
|
108
|
+
# task_key.name #=> "sampleTask"
|
109
|
+
# task_key.id = 654321
|
110
|
+
# task_key.id #=> 654321
|
111
|
+
# task_key.name #=> nil
|
112
112
|
#
|
113
113
|
def id= new_id
|
114
114
|
@name = nil if new_id
|
@@ -121,8 +121,8 @@ module Gcloud
|
|
121
121
|
# @return [Integer, nil]
|
122
122
|
#
|
123
123
|
# @example
|
124
|
-
#
|
125
|
-
#
|
124
|
+
# task_key = Gcloud::Datastore::Key.new "Task", 123456
|
125
|
+
# task_key.id #=> 123456
|
126
126
|
#
|
127
127
|
attr_reader :id
|
128
128
|
|
@@ -133,12 +133,12 @@ module Gcloud
|
|
133
133
|
# @return [String, nil]
|
134
134
|
#
|
135
135
|
# @example
|
136
|
-
#
|
137
|
-
#
|
138
|
-
#
|
139
|
-
#
|
140
|
-
#
|
141
|
-
#
|
136
|
+
# task_key = Gcloud::Datastore::Key.new "Task", 123456
|
137
|
+
# task_key.id #=> 123456
|
138
|
+
# task_key.name #=> nil
|
139
|
+
# task_key.name = "sampleTask"
|
140
|
+
# task_key.id #=> nil
|
141
|
+
# task_key.name #=> "sampleTask"
|
142
142
|
#
|
143
143
|
def name= new_name
|
144
144
|
@id = nil if new_name
|
@@ -151,19 +151,26 @@ module Gcloud
|
|
151
151
|
# @return [String, nil]
|
152
152
|
#
|
153
153
|
# @example
|
154
|
-
#
|
155
|
-
#
|
154
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
155
|
+
# task_key.name #=> "sampleTask"
|
156
156
|
#
|
157
157
|
attr_reader :name
|
158
158
|
|
159
159
|
##
|
160
|
-
#
|
160
|
+
# Set the parent of the Key.
|
161
161
|
#
|
162
162
|
# @return [Key, nil]
|
163
163
|
#
|
164
164
|
# @example
|
165
|
-
#
|
166
|
-
#
|
165
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
166
|
+
# task_key.parent = Gcloud::Datastore::Key.new "TaskList", "default"
|
167
|
+
#
|
168
|
+
# @example With multiple levels:
|
169
|
+
# user_key = Gcloud::Datastore::Key.new "User", "alice"
|
170
|
+
# task_list_key = Gcloud::Datastore::Key.new "TaskList", "default"
|
171
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
172
|
+
# task_list_key.parent = user_key
|
173
|
+
# task_key.parent = task_list_key
|
167
174
|
#
|
168
175
|
def parent= new_parent
|
169
176
|
# store key if given an entity
|
@@ -180,13 +187,13 @@ module Gcloud
|
|
180
187
|
# require "gcloud"
|
181
188
|
#
|
182
189
|
# gcloud = Gcloud.new
|
183
|
-
#
|
190
|
+
# datastore = gcloud.datastore
|
184
191
|
#
|
185
|
-
#
|
186
|
-
# query =
|
187
|
-
# ancestor(
|
188
|
-
# lists =
|
189
|
-
# lists.first.key.parent #=> Key("
|
192
|
+
# task_list = datastore.find "TaskList", "default"
|
193
|
+
# query = datastore.query("Task").
|
194
|
+
# ancestor(task_list)
|
195
|
+
# lists = datastore.run query
|
196
|
+
# lists.first.key.parent #=> Key("TaskList", "default")
|
190
197
|
#
|
191
198
|
attr_reader :parent
|
192
199
|
|
@@ -198,9 +205,9 @@ module Gcloud
|
|
198
205
|
# @return [Array<Array<(String, String)>>]
|
199
206
|
#
|
200
207
|
# @example
|
201
|
-
#
|
202
|
-
#
|
203
|
-
#
|
208
|
+
# task_key = Gcloud::Datastore::Key.new "Task", "sampleTask"
|
209
|
+
# task_key.parent = Gcloud::Datastore::Key.new "TaskList", "default"
|
210
|
+
# task_key.path #=> [["TaskList", "default"], ["Task", "sampleTask"]]
|
204
211
|
#
|
205
212
|
def path
|
206
213
|
new_path = parent ? parent.path : []
|
@@ -226,41 +233,43 @@ module Gcloud
|
|
226
233
|
end
|
227
234
|
|
228
235
|
##
|
229
|
-
# @private Convert the Key to a
|
230
|
-
def
|
231
|
-
|
232
|
-
|
233
|
-
|
236
|
+
# @private Convert the Key to a Google::Datastore::V1beta3::Key object.
|
237
|
+
def to_grpc
|
238
|
+
grpc_path = path.map do |pe_kind, pe_id_or_name|
|
239
|
+
path_args = { kind: pe_kind }
|
240
|
+
if pe_id_or_name.is_a? Integer
|
241
|
+
path_args[:id] = pe_id_or_name
|
242
|
+
elsif pe_id_or_name.is_a? String
|
243
|
+
path_args[:name] = pe_id_or_name unless pe_id_or_name.empty?
|
234
244
|
end
|
235
|
-
|
245
|
+
Google::Datastore::V1beta3::Key::PathElement.new(path_args)
|
246
|
+
end
|
247
|
+
grpc = Google::Datastore::V1beta3::Key.new(path: grpc_path)
|
248
|
+
if project || namespace
|
249
|
+
grpc.partition_id = Google::Datastore::V1beta3::PartitionId.new(
|
250
|
+
project_id: project.to_s, namespace_id: namespace.to_s)
|
236
251
|
end
|
252
|
+
grpc
|
237
253
|
end
|
238
254
|
|
239
|
-
# rubocop:disable all
|
240
|
-
|
241
255
|
##
|
242
|
-
# @private Create a new Key from a
|
243
|
-
def self.
|
244
|
-
|
245
|
-
key_proto = proto.dup
|
256
|
+
# @private Create a new Key from a Google::Datastore::V1beta3::Key object.
|
257
|
+
def self.from_grpc grpc
|
258
|
+
key_grpc = grpc.dup
|
246
259
|
key = Key.new
|
247
|
-
|
248
|
-
if
|
249
|
-
key = Key.new
|
250
|
-
proto_path_element.id || proto_path_element.name
|
251
|
-
end
|
252
|
-
if key_proto.partition_id
|
253
|
-
key.dataset_id = key_proto.partition_id.dataset_id
|
254
|
-
key.namespace = key_proto.partition_id.namespace
|
260
|
+
path_grpc = key_grpc.path.pop
|
261
|
+
if path_grpc
|
262
|
+
key = Key.new path_grpc.kind, (path_grpc.id || path_grpc.name)
|
255
263
|
end
|
256
|
-
if
|
257
|
-
key.
|
264
|
+
if key_grpc.partition_id
|
265
|
+
key.project = key_grpc.partition_id.project_id
|
266
|
+
key.namespace = key_grpc.partition_id.namespace_id
|
258
267
|
end
|
268
|
+
key.parent = Key.from_grpc(key_grpc) if key_grpc.path.count > 0
|
259
269
|
# Freeze the key to make it immutable.
|
260
270
|
key.freeze
|
261
271
|
key
|
262
272
|
end
|
263
|
-
# rubocop:enable all
|
264
273
|
end
|
265
274
|
end
|
266
275
|
end
|