Class: GraphQL::Schema::Visibility

Inherits:
Object
  • Object
show all
Defined in:
lib/graphql/schema/visibility.rb,
lib/graphql/schema/visibility/profile.rb,
lib/graphql/schema/visibility/migration.rb

Overview

Use this plugin to make some parts of your schema hidden from some viewers.

Defined Under Namespace

Classes: Migration, Profile

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(schema, dynamic:, preload:, profiles:, migration_errors:) ⇒ Visibility

Returns a new instance of Visibility.



18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
# File 'lib/graphql/schema/visibility.rb', line 18

def initialize(schema, dynamic:, preload:, profiles:, migration_errors:)
  @schema = schema
  schema.use_visibility_profile = true
  if migration_errors
    schema.visibility_profile_class = Migration
  end
  @preload = preload
  @profiles = profiles
  @cached_profiles = {}
  @dynamic = dynamic
  @migration_errors = migration_errors
  if preload
    # Traverse the schema now (and in the *_configured hooks below)
    # To make sure things are loaded during boot
    @preloaded_types = Set.new
    types_to_visit = [
      @schema.query,
      @schema.mutation,
      @schema.subscription,
      *@schema.introspection_system.types.values,
      *@schema.introspection_system.entry_points.map { |ep| ep.type.unwrap },
      *@schema.orphan_types,
    ]
    # Root types may have been nil:
    types_to_visit.compact!
    ensure_all_loaded(types_to_visit)

    profiles.each do |profile_name, example_ctx|
      example_ctx[:visibility_profile] = profile_name
      prof = profile_for(example_ctx, profile_name)
      prof.all_types # force loading
    end
  end
end

Instance Attribute Details

#cached_profilesObject (readonly)

Returns the value of attribute cached_profiles.



109
110
111
# File 'lib/graphql/schema/visibility.rb', line 109

def cached_profiles
  @cached_profiles
end

Class Method Details

.use(schema, dynamic: false, profiles: EmptyObjects::EMPTY_HASH, preload: (Rails) ? Rails.env.production? : nil), migration_errors: false) ⇒ Object

Parameters:

  • schema (Class<GraphQL::Schema>)
  • profiles (Hash<Symbol => Hash>) (defaults to: EmptyObjects::EMPTY_HASH)

    A hash of name => context pairs for preloading visibility profiles

  • preload (Boolean) (defaults to: (Rails) ? Rails.env.production? : nil))

    if true, load the default schema profile and all named profiles immediately (defaults to true for Rails.env.production?)

  • migration_errors (Boolean) (defaults to: false)

    if true, raise an error when Visibility and Warden return different results



14
15
16
# File 'lib/graphql/schema/visibility.rb', line 14

def self.use(schema, dynamic: false, profiles: EmptyObjects::EMPTY_HASH, preload: (defined?(Rails) ? Rails.env.production? : nil), migration_errors: false)
  schema.visibility = self.new(schema, dynamic: dynamic, preload: preload, profiles: profiles, migration_errors: migration_errors)
end

Instance Method Details

#dup_for(other_schema) ⇒ Visibility

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.

Make another Visibility for schema based on this one

Returns:



95
96
97
98
99
100
101
102
103
# File 'lib/graphql/schema/visibility.rb', line 95

def dup_for(other_schema)
  self.class.new(
    other_schema,
    dynamic: @dynamic,
    preload: @preload,
    profiles: @profiles,
    migration_errors: @migration_errors
  )
end

#introspection_system_configured(introspection_system) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



82
83
84
85
86
87
88
89
90
# File 'lib/graphql/schema/visibility.rb', line 82

def introspection_system_configured(introspection_system)
  if @preload
    introspection_types = [
      *@schema.introspection_system.types.values,
      *@schema.introspection_system.entry_points.map { |ep| ep.type.unwrap },
    ]
    ensure_all_loaded(introspection_types)
  end
end

#migration_errors?Boolean

Returns:

  • (Boolean)


105
106
107
# File 'lib/graphql/schema/visibility.rb', line 105

def migration_errors?
  @migration_errors
end

#mutation_configured(mutation_type) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



61
62
63
64
65
# File 'lib/graphql/schema/visibility.rb', line 61

def mutation_configured(mutation_type)
  if @preload
    ensure_all_loaded([mutation_type])
  end
end

#orphan_types_configured(orphan_types) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



75
76
77
78
79
# File 'lib/graphql/schema/visibility.rb', line 75

def orphan_types_configured(orphan_types)
  if @preload
    ensure_all_loaded(orphan_types)
  end
end

#profile_for(context, visibility_profile) ⇒ Object



111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
# File 'lib/graphql/schema/visibility.rb', line 111

def profile_for(context, visibility_profile)
  if @profiles.any?
    if visibility_profile.nil?
      if @dynamic
        if context.is_a?(Query::NullContext)
          top_level_profile
        else
          @schema.visibility_profile_class.new(context: context, schema: @schema)
        end
      elsif @profiles.any?
        raise ArgumentError, "#{@schema} expects a visibility profile, but `visibility_profile:` wasn't passed. Provide a `visibility_profile:` value or add `dynamic: true` to your visibility configuration."
      end
    elsif !@profiles.include?(visibility_profile)
      raise ArgumentError, "`#{visibility_profile.inspect}` isn't allowed for `visibility_profile:` (must be one of #{@profiles.keys.map(&:inspect).join(", ")}). Or, add `#{visibility_profile.inspect}` to the list of profiles in the schema definition."
    else
      @cached_profiles[visibility_profile] ||= @schema.visibility_profile_class.new(name: visibility_profile, context: context, schema: @schema)
    end
  elsif context.is_a?(Query::NullContext)
    top_level_profile
  else
    @schema.visibility_profile_class.new(context: context, schema: @schema)
  end
end

#query_configured(query_type) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



54
55
56
57
58
# File 'lib/graphql/schema/visibility.rb', line 54

def query_configured(query_type)
  if @preload
    ensure_all_loaded([query_type])
  end
end

#subscription_configured(subscription_type) ⇒ Object

This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.



68
69
70
71
72
# File 'lib/graphql/schema/visibility.rb', line 68

def subscription_configured(subscription_type)
  if @preload
    ensure_all_loaded([subscription_type])
  end
end