Module: SfdoAPI

Defined in:
lib/SFDO/API.rb

Instance Method Summary collapse

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(method_called, *args, &block) ⇒ Object



211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
# File 'lib/SFDO/API.rb', line 211

def method_missing(method_called, *args, &block)
  breakdown = method_called.to_s.split('_')
  obj_type = breakdown.last.capitalize

  case method_called.to_s
  when /^delete_all_/
    delete_all *args
  when /^delete_one/
    delete obj_type, *args
  when /^create_/
    create obj_type, *args
  when /^select_api/
    select_api *args
  else
    super.method_missing
  end
end

Instance Method Details

#api_clientObject



5
6
7
8
9
10
11
12
13
14
15
16
17
18
# File 'lib/SFDO/API.rb', line 5

def api_client
  if ENV['SF_ACCESS_TOKEN'] && ENV['SF_INSTANCE_URL']
    @api_client ||= Restforce.new(oauth_token: ENV['SF_ACCESS_TOKEN'],
                                  instance_url: ENV['SF_INSTANCE_URL'],
                                  api_version: '33.0')
    yield
  else
    @api_client ||= Restforce.new api_version: '33.0',
                                  refresh_token: ENV['SF_REFRESH_TOKEN'],
                                  client_id: ENV['SF_CLIENT_KEY'],
                                  client_secret: ENV['SF_CLIENT_SECRET']
    yield
  end
end

#create(type, obj_hash) ⇒ Object



20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
# File 'lib/SFDO/API.rb', line 20

def create(type, obj_hash)
  true_fields = {}

  type = true_object_name(type)
  obj_mash = Hashie::Mash.new obj_hash

  obj_mash.map { |x, y| true_fields.store(true_field_name(x, type), y) }

  if is_valid_obj_hash?(type, obj_hash, @fields_acceptibly_nil)
    obj_id = api_client do
      @api_client.create! type, true_fields
    end
  end
  obj_id
end

#delete(obj_id) ⇒ Object



189
190
191
# File 'lib/SFDO/API.rb', line 189

def delete(obj_id)
  delete_by_id(obj_id)
end

#delete_all(id) ⇒ Object



199
200
201
202
203
# File 'lib/SFDO/API.rb', line 199

def delete_all(id)
  api_client do
    id.each(&:destroy)
  end
end

#delete_by_id(obj_id) ⇒ Object



193
194
195
196
197
# File 'lib/SFDO/API.rb', line 193

def delete_by_id(obj_id)
  api_client do
    @api_client.destroy(true_object_name(obj_id), obj_id)
  end
end

#get_object_describe(object_name) ⇒ Object



173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
# File 'lib/SFDO/API.rb', line 173

def get_object_describe(object_name)
  api_client do
    @description = @api_client.get("/services/data/v35.0/sobjects/#{object_name}/describe")
    describeobject = Hashie::Mash.new(@description.body)

    required = describeobject.fields.map do |x|
      Hashie::Mash.new(
        fieldName: x.name,
        required: (!x.nillable && !x.defaultedOnCreate),
        default: x.defaultValue
      )
    end
    return required
  end
end

#get_required_fields_on_object(obj_name) ⇒ Object



163
164
165
166
167
168
169
170
171
# File 'lib/SFDO/API.rb', line 163

def get_required_fields_on_object(obj_name)
  @object_fields = {} if @object_fields.nil?

  if @object_fields[obj_name].nil?
    @object_fields[obj_name] = get_object_describe(obj_name)
  end

  @object_fields[obj_name].select(&:required)
end

#is_valid_obj_hash?(object_name, obj_hash, fields_acceptibly_nil) ⇒ Boolean

Returns:

  • (Boolean)


71
72
73
74
75
76
77
78
79
80
81
82
83
# File 'lib/SFDO/API.rb', line 71

def is_valid_obj_hash?(object_name, obj_hash, fields_acceptibly_nil)
  required_fields = get_required_fields_on_object(object_name).map(&:fieldName)
  valid = true
  required_fields.each do |f|
    valid = false if (!obj_hash.key? f.to_sym) && (begin
      !fields_acceptibly_nil[object_name].contains? f
      puts 'This field must be populated in order to create this object in this environment: ' + f.inspect
    rescue
      false
    end)
  end
  valid
end

#obj_names_without_custom_additionsObject



143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
# File 'lib/SFDO/API.rb', line 143

def obj_names_without_custom_additions
  if @obj_names_without_custom_additions.nil? || !@obj_names_without_custom_additions.respond_to?(:contains)
    @obj_names_without_custom_additions = {}
    org_describe.each do |z|
      tmp_var = z.name.split '__'
      save = ''
      case tmp_var.size
      when 2
        save = tmp_var.first
      when 3
        save = tmp_var[1]
      else
        save = tmp_var.last
      end
      @obj_names_without_custom_additions.store(save, z.name)
    end
  end
  @obj_names_without_custom_additions
end

#org_describeObject



85
86
87
88
89
90
91
92
# File 'lib/SFDO/API.rb', line 85

def org_describe
  if @org_description.nil? || !@org_description.respond_to?(:contains)
    @org_description = api_client do
      @api_client.describe
    end
  end
  @org_description
end

#prefix_to_nameObject



94
95
96
97
98
99
100
101
102
# File 'lib/SFDO/API.rb', line 94

def prefix_to_name
  if @prefix_to_name.nil? || !@prefix_to_name.respond_to?(:contains)
    @prefix_to_name = {}
    org_describe.each do |z|
      @prefix_to_name.store(z.keyPrefix, z.name)
    end
  end
  @prefix_to_name
end

#select_api(query) ⇒ Object



36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# File 'lib/SFDO/API.rb', line 36

def select_api(query)
  if query.match /where/i
    obj_name = query[/(?<=from )(.*)(?= where)|$/i]
  else
    obj_name = query[/(?<=from )(.*)$/i]
  end

  # GET TRUE OBJECT NAME BEFORE GETTING TRUE FIELD NAMES
  real_obj_name = true_object_name(obj_name)

  # REMOVE NEWLINES IF ANY
  query = query.gsub(/\n/, ' ')
  # REMOVE EXTRA SPACES
  query = query.gsub(/\s{2,}/, ' ')
  # GET FIELDS ONLY
  fields_array = query.split(' from ').first.scan /\w*\s*\s([a-zA-Z0-9_]*)/

  fields_array.each do |field|
    real_field = true_field_name(field[0], real_obj_name)

    if obj_name != real_obj_name
      query = query.gsub(/\b#{obj_name}\b/, real_obj_name)
    end

    if field[0] != real_field
      query = query.sub(field[0], real_field)
    end
  end

  results = api_client do
    @api_client.query query
  end
  results
end

#true_field_name(field, obj) ⇒ Object



104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
# File 'lib/SFDO/API.rb', line 104

def true_field_name(field, obj)
  # See if we've done an object describe on the object
  # If so, return the fields for the object
  # Otherwise do an object describe, save the object description and return the fields with their real names
  @full_describe = {} if @full_describe.nil?

  if @full_describe[obj].nil?
    object_description = get_object_describe(obj)
    fields = object_description.map do |f|

      # MANAGED CODE
      if f.fieldName.match /.*__.*__.*/
        substituted = f.fieldName.gsub(/\A.*?__/, '').gsub(/__c\z/, '')
      else
        # UNMANAGED CODE
        substituted = f.fieldName.gsub(/__c\z/, '')
      end

      { substituted => f.fieldName }
    end
    @full_describe[obj] = fields.reduce({}, :merge)
  end

  # RETURN THE REAL NAME FROM OUR HASH OF INPUT TO REAL NAMES
  @full_describe[obj][field]
end

#true_object_name(handle) ⇒ Object

either an ID or a string name



131
132
133
134
135
136
137
138
139
140
141
# File 'lib/SFDO/API.rb', line 131

def true_object_name(handle) # either an ID or a string name
  # handle = (handle.end_with?("__c") || handle.end_with?("__r")) ? handle[0...-3] : handle
  handle.end_with?('__c', '__r') ? handle[0...-3] : handle
  from_id = prefix_to_name[handle[0..2]]
  from_name = obj_names_without_custom_additions[handle]
  if !from_name.nil? || !from_id.nil?
    return from_name if from_id.nil?
    return from_id if from_name.nil?
  end
  'Unable to find object. Be sure to call SFDO-API without preceding namespace or following __c or __r'
end

#update_api(obj) ⇒ Object



205
206
207
208
209
# File 'lib/SFDO/API.rb', line 205

def update_api(obj)
  api_client do
    @api_client.update(obj.attributes.type, obj)
  end
end