Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
G
gitlab-ce
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
1
Merge Requests
1
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
gitlab-ce
Commits
3d29bff4
Commit
3d29bff4
authored
Oct 28, 2019
by
Brett Walker
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Add feature flag :graphql_keyset_pagination
To allow falling back to old keyset pagination
parent
1c508188
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
200 additions
and
0 deletions
+200
-0
lib/gitlab/graphql/connections/keyset/connection.rb
lib/gitlab/graphql/connections/keyset/connection.rb
+7
-0
lib/gitlab/graphql/connections/keyset/legacy_keyset_connection.rb
...ab/graphql/connections/keyset/legacy_keyset_connection.rb
+66
-0
spec/lib/gitlab/graphql/connections/keyset/legacy_keyset_connection_spec.rb
...aphql/connections/keyset/legacy_keyset_connection_spec.rb
+127
-0
No files found.
lib/gitlab/graphql/connections/keyset/connection.rb
View file @
3d29bff4
...
@@ -27,11 +27,18 @@ module Gitlab
...
@@ -27,11 +27,18 @@ module Gitlab
class
Connection
<
GraphQL
::
Relay
::
BaseConnection
class
Connection
<
GraphQL
::
Relay
::
BaseConnection
include
Gitlab
::
Utils
::
StrongMemoize
include
Gitlab
::
Utils
::
StrongMemoize
# TODO https://gitlab.com/gitlab-org/gitlab/issues/35104
include
Gitlab
::
Graphql
::
Connections
::
Keyset
::
LegacyKeysetConnection
def
cursor_from_node
(
node
)
def
cursor_from_node
(
node
)
return
legacy_cursor_from_node
(
node
)
if
use_legacy_pagination?
encoded_json_from_ordering
(
node
)
encoded_json_from_ordering
(
node
)
end
end
def
sliced_nodes
def
sliced_nodes
return
legacy_sliced_nodes
if
use_legacy_pagination?
@sliced_nodes
||=
@sliced_nodes
||=
begin
begin
OrderInfo
.
validate_ordering
(
ordered_nodes
,
order_list
)
OrderInfo
.
validate_ordering
(
ordered_nodes
,
order_list
)
...
...
lib/gitlab/graphql/connections/keyset/legacy_keyset_connection.rb
0 → 100644
View file @
3d29bff4
# frozen_string_literal: true
# TODO https://gitlab.com/gitlab-org/gitlab/issues/35104
module
Gitlab
module
Graphql
module
Connections
module
Keyset
module
LegacyKeysetConnection
def
legacy_cursor_from_node
(
node
)
encode
(
node
[
legacy_order_field
].
to_s
)
end
# rubocop: disable CodeReuse/ActiveRecord
def
legacy_sliced_nodes
@sliced_nodes
||=
begin
sliced
=
nodes
sliced
=
sliced
.
where
(
legacy_before_slice
)
if
before
.
present?
sliced
=
sliced
.
where
(
legacy_after_slice
)
if
after
.
present?
sliced
end
end
# rubocop: enable CodeReuse/ActiveRecord
private
def
use_legacy_pagination?
strong_memoize
(
:feature_disabled
)
do
Feature
.
disabled?
(
:graphql_keyset_pagination
,
default_enabled:
true
)
end
end
def
legacy_before_slice
if
legacy_sort_direction
==
:asc
arel_table
[
legacy_order_field
].
lt
(
decode
(
before
))
else
arel_table
[
legacy_order_field
].
gt
(
decode
(
before
))
end
end
def
legacy_after_slice
if
legacy_sort_direction
==
:asc
arel_table
[
legacy_order_field
].
gt
(
decode
(
after
))
else
arel_table
[
legacy_order_field
].
lt
(
decode
(
after
))
end
end
def
legacy_order_info
@legacy_order_info
||=
nodes
.
order_values
.
first
end
def
legacy_order_field
@legacy_order_field
||=
legacy_order_info
&
.
expr
&
.
name
||
nodes
.
primary_key
end
def
legacy_sort_direction
@legacy_order_direction
||=
legacy_order_info
&
.
direction
||
:desc
end
end
end
end
end
end
spec/lib/gitlab/graphql/connections/keyset/legacy_keyset_connection_spec.rb
0 → 100644
View file @
3d29bff4
# frozen_string_literal: true
# TODO https://gitlab.com/gitlab-org/gitlab/issues/35104
require
'spec_helper'
describe
Gitlab
::
Graphql
::
Connections
::
Keyset
::
LegacyKeysetConnection
do
describe
'old keyset_connection'
do
let
(
:described_class
)
{
Gitlab
::
Graphql
::
Connections
::
Keyset
::
Connection
}
let
(
:nodes
)
{
Project
.
all
.
order
(
id: :asc
)
}
let
(
:arguments
)
{
{}
}
subject
(
:connection
)
do
described_class
.
new
(
nodes
,
arguments
,
max_page_size:
3
)
end
before
do
stub_feature_flags
(
graphql_keyset_pagination:
false
)
end
def
encoded_property
(
value
)
Base64Bp
.
urlsafe_encode64
(
value
.
to_s
,
padding:
false
)
end
describe
'#cursor_from_nodes'
do
let
(
:project
)
{
create
(
:project
)
}
it
'returns an encoded ID'
do
expect
(
connection
.
cursor_from_node
(
project
))
.
to
eq
(
encoded_property
(
project
.
id
))
end
context
'when an order was specified'
do
let
(
:nodes
)
{
Project
.
order
(
:updated_at
)
}
it
'returns the encoded value of the order'
do
expect
(
connection
.
cursor_from_node
(
project
))
.
to
eq
(
encoded_property
(
project
.
updated_at
))
end
end
end
describe
'#sliced_nodes'
do
let
(
:projects
)
{
create_list
(
:project
,
4
)
}
context
'when before is passed'
do
let
(
:arguments
)
{
{
before:
encoded_property
(
projects
[
1
].
id
)
}
}
it
'only returns the project before the selected one'
do
expect
(
subject
.
sliced_nodes
).
to
contain_exactly
(
projects
.
first
)
end
context
'when the sort order is descending'
do
let
(
:nodes
)
{
Project
.
all
.
order
(
id: :desc
)
}
it
'returns the correct nodes'
do
expect
(
subject
.
sliced_nodes
).
to
contain_exactly
(
*
projects
[
2
..-
1
])
end
end
end
context
'when after is passed'
do
let
(
:arguments
)
{
{
after:
encoded_property
(
projects
[
1
].
id
)
}
}
it
'only returns the project before the selected one'
do
expect
(
subject
.
sliced_nodes
).
to
contain_exactly
(
*
projects
[
2
..-
1
])
end
context
'when the sort order is descending'
do
let
(
:nodes
)
{
Project
.
all
.
order
(
id: :desc
)
}
it
'returns the correct nodes'
do
expect
(
subject
.
sliced_nodes
).
to
contain_exactly
(
projects
.
first
)
end
end
end
context
'when both before and after are passed'
do
let
(
:arguments
)
do
{
after:
encoded_property
(
projects
[
1
].
id
),
before:
encoded_property
(
projects
[
3
].
id
)
}
end
it
'returns the expected set'
do
expect
(
subject
.
sliced_nodes
).
to
contain_exactly
(
projects
[
2
])
end
end
end
describe
'#paged_nodes'
do
let!
(
:projects
)
{
create_list
(
:project
,
5
)
}
it
'returns the collection limited to max page size'
do
expect
(
subject
.
paged_nodes
.
size
).
to
eq
(
3
)
end
it
'is a loaded memoized array'
do
expect
(
subject
.
paged_nodes
).
to
be_an
(
Array
)
expect
(
subject
.
paged_nodes
.
object_id
).
to
eq
(
subject
.
paged_nodes
.
object_id
)
end
context
'when `first` is passed'
do
let
(
:arguments
)
{
{
first:
2
}
}
it
'returns only the first elements'
do
expect
(
subject
.
paged_nodes
).
to
contain_exactly
(
projects
.
first
,
projects
.
second
)
end
end
context
'when `last` is passed'
do
let
(
:arguments
)
{
{
last:
2
}
}
it
'returns only the last elements'
do
expect
(
subject
.
paged_nodes
).
to
contain_exactly
(
projects
[
3
],
projects
[
4
])
end
end
context
'when both are passed'
do
let
(
:arguments
)
{
{
first:
2
,
last:
2
}
}
it
'raises an error'
do
expect
{
subject
.
paged_nodes
}.
to
raise_error
(
Gitlab
::
Graphql
::
Errors
::
ArgumentError
)
end
end
end
end
end
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment