Module: CanvasApi::GraphQLHelpers

Included in:
Render
Defined in:
lib/canvas_api/graphql_helpers.rb

Instance Method Summary collapse

Instance Method Details

#graphql_fields(model, resource_name) ⇒ Object



67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
# File 'lib/canvas_api/graphql_helpers.rb', line 67

def graphql_fields(model, resource_name)
  model["properties"].map do |name, property|
    # HACK. This property doesn't have any metadata. Throw in a couple lines of code
    # specific to this field.
    if name == "created_source" && property == "manual|sis|api"
      "#{name}: new GraphQLEnumType({ name: '#{name}', values: { manual: { value: 'manual' }, sis: { value: 'sis' }, api: { value: 'api' } } })"
    else

      description = ""
      if property["description"].present? && property["example"].present?
        description << "#{safe_js(property['description'])}. Example: #{safe_js(property['example'])}".gsub("..", "").gsub("\n", " ")
      end

      if type = graphql_type(name, property)
        resolve = graphql_resolve(name, property)
        resolve = "#{resolve}, " if resolve.present?
        "#{name}: { type: #{type}, #{resolve}description: \"#{description}\" }"
      end

    end
  end.compact
end

#graphql_primitive(type, format) ⇒ Object



35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
# File 'lib/canvas_api/graphql_helpers.rb', line 35

def graphql_primitive(type, format)
  case type
  when "integer"
    "GraphQLInt"
  when "number"
    if format == "float64"
      "GraphQLFloat"
    else
      # TODO many of the LMS types with 'number' don't indicate a type so we have to guess
      # Hopefully that changes. For now we go with float
      "GraphQLFloat"
    end
  when "string"
    "GraphQLString"
  when "boolean"
    "GraphQLBoolean"
  when "datetime"
    "GraphQLDateTime"
  else
    raise "Unable to match requested primitive '#{type}' to GraphQL Type."
  end
end

#graphql_resolve(name, property) ⇒ Object



58
59
60
61
62
63
64
65
# File 'lib/canvas_api/graphql_helpers.rb', line 58

def graphql_resolve(name, property)
  if property["$ref"]
    "resolve(model){ return model.#{name}; }"
  elsif property["type"] == "array" && property["items"] && property["items"]["$ref"]
    "resolve(model){ return model.#{name}; }"
  end
  "resolve(model){ return model.#{name}; }"
end

#graphql_type(name, property) ⇒ Object



5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
# File 'lib/canvas_api/graphql_helpers.rb', line 5

def graphql_type(name, property)
  if property["$ref"]
    "#{property['$ref']}, resolve: function(model){ return model.#{name}; }"
  else
    type = property["type"]
    case type
    when "integer", "string", "boolean", "datetime", "number"
      graphql_primitive(type, property["format"])
    when "array"
      begin
        type = if property["items"]["$ref"]
                 property["items"]["$ref"]
               else
                 graphql_primitive(property["items"]["type"], property["items"]["format"])
               end
      rescue
        puts "Unable to discover list type for '#{name}' ('#{property}'). Defaulting to GraphQLString"
        type = "GraphQLString"
      end
      "new GraphQLList(#{type})"
    when "object"
      puts "Using string type for '#{name}' ('#{property}') of type object."
      "GraphQLString"
    else
      puts "Unable to match '#{name}' requested property '#{property}' to GraphQL Type."
      "GraphQLString"
    end
  end
end

#safe_js(str) ⇒ Object



90
91
92
93
94
95
# File 'lib/canvas_api/graphql_helpers.rb', line 90

def safe_js(str)
  str = str.join(", ") if str.is_a?(Array)
  str = str.map { |_k, v| v }.join(", ") if str.is_a?(Hash)
  return str unless str.is_a?(String)
  str.gsub('"', "'")
end