Skip to content

Instantly share code, notes, and snippets.

@patorash
Last active June 17, 2021 04:13
Show Gist options
  • Save patorash/be7fe58e9a2d3237db67c619f6cd9948 to your computer and use it in GitHub Desktop.
Save patorash/be7fe58e9a2d3237db67c619f6cd9948 to your computer and use it in GitHub Desktop.
ElasticsearchRelationConnection for graphqu-ruby with elasticsearch-model
module Connections
class ElasticsearchRelationConnection < GraphQL::Pagination::RelationConnection
def nodes
@nodes ||= limited_nodes.records.to_a
end
# Rubocopにload_nodesメソッドが不要と言われた
# しかし、継承元のRelationConnectionで呼ばれているのでnodesメソッドのエイリアスにしておく
# また、元々private methodだったので変更しておく
alias_method :load_nodes, :nodes
private :load_nodes
# GraphQL::Pagination::RelationConnectionの実装を改修
# `@paged_node_offset`にオフセットが入っているので、2重で足さないようにした。
def cursor_for(item)
load_nodes
# index in nodes + existing offset + 1 (because it's offset, not index)
# offset = @nodes.index(item) + 1 + (@paged_nodes_offset || 0) + (relation_offset(items) || 0)
offset = @nodes.index(item) + 1 + (@paged_nodes_offset || 0)
encode(offset.to_s)
end
private
# @param [Elasticsearch::Model::Response::Response]
# @param [Integer] size LimitSize
# @return [Boolean] sizeよりも残りが大きければtrueを返す
def relation_larger_than(relation, size)
initial_offset = relation_offset(relation)
relation_count(relation) > initial_offset + size
end
# @param [Elasticsearch::Model::Response::Response]
# @return [Integer] オフセットの値
def relation_offset(relation)
relation.search.definition.fetch(:from, 0)
end
# @param [Elasticsearch::Model::Response::Response]
# @return [Integer, nil] 取得数
def relation_limit(relation)
relation.search.definition[:size]
end
# @param [Elasticsearch::Model::Response::Response]
# @return [Integer] 総ヒット数
def relation_count(relation)
relation.results.total
end
# @param [Elasticsearch::Model::Response::Response]
# @return [ActiveRecord::Relation]
def null_relation(relation)
relation.records.none
end
def limited_nodes
super()
rescue ArgumentError => _e
# カーソルの先頭より前の要素を取得しようとするとArgumentErrorになったため、
# 例外を補足して空のActiveRecord::Relationを返すようにした
ApplicationRecord.none
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment