Module: JSS::SelfServable

Included in:
OSXConfigurationProfile, Policy
Defined in:
lib/jss/api_object/self_servable.rb

Overview

A mix-in module for handling Self Service data for objects in the JSS.

The JSS objects that have Self Service data return it in a :self_service subset, which have somewhat similar data, i.e. a hash with at least these keys:

  • :self_service_description

  • :self_service_icon

  • :feature_on_main_page

  • :self_service_categories

Config Profiles in self service have this key:

  • :security

Additionally, items that apper in macOS Slf Svc have these keys:

  • :install_button_text

  • :force_users_to_view_description

See the attribute definitions for details of these values and structures.

Including this module in an APIObject subclass and calling #parse_self_service in the subclass’s constructor will give it matching attributes with ‘self_service_’ appended if needed, e.g. #self_service_feature_on_main_page

Classes including this module must:

  • Define the constant SELF_SERVICE_TARGET which contains either :macos or :ios

  • Define the constant SELF_SERVICE_PAYLOAD which contains one of :policy, :profile, :app, or :ebook

  • Call #parse_self_service in the subclass’s constructor, after calling super

  • Define the method #in_self_service? which returns a Boolean indicating that the item is available in self service. Different API objects indicate this in different ways (and macOS app store apps don’t provide it at all via the API, so self service can’t be implemented fully)

  • Define the methods #add_to_self_service and #remove_from_self_service, which is handled differently for policies, apps/ebooks, and profiles

  • Define the method #user_removable? which returns Boolean indicating that the item can be removed by the user in SSvc. macOS profiles store this in the :user_removable key of the :general subset as a boolean, whereas iOS profiles store it in the :security hash of the :self_service data as one of 3 strings

  • Define the method #user_removable= which sets the appropriate values depending on the class. (see above)

  • Define a #set_icon_to method which takes the id of a previously uploaded icon, or a local path (String or Pathname) to an image file to use.

  • Include the result of #self_service_xml in their #rest_xml output

Generating XML for PUT or POST:

If the class including this module is creatable or updatable, calling #self_service_xml returns a REXML element representing the Self Service subset, to be included with the #rest_xml output of the subclass.

Because some self-service-related data is located outside of the Self Service data subset (e.g. the deployment method for profiles is in the general subset), classes including this module must also account for that and add an appropriate XML element as needed.

Constant Summary collapse

SELF_SERVABLE =

Constants

true
IOS_PROFILE_REMOVAL_OPTIONS =
['Always', 'With Authorization', 'Never'].freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#self_service_categoriesArray<Hash> (readonly)

Each Hash has these keys about the category

  • :id => [Integer] the JSS id of the category

  • :name => [String] the name of the category

Most objects also include one or both of these keys:

  • :display_in => [Boolean] should the item be displayed in this category in SSvc? (OSX SSvc only)

  • :feature_in => [Boolean] should the item be featured in this category in SSVC? (OSX SSvc only)

NOTE: as of Casper 9.61 there’s a bug in the JSON output from the API, and only the last category is returned, if more than one are set.

Returns:

  • (Array<Hash>)

    The categories in which this item should appear in SSvc



131
132
133
# File 'lib/jss/api_object/self_servable.rb', line 131

def self_service_categories
  @self_service_categories
end

#self_service_descriptionString

Returns The verbage that appears in SelfSvc for this item.

Returns:

  • (String)

    The verbage that appears in SelfSvc for this item



113
114
115
# File 'lib/jss/api_object/self_servable.rb', line 113

def self_service_description
  @self_service_description
end

#self_service_feature_on_main_pageBoolean

Returns Should this item feature on the main page of SSvc?.

Returns:

  • (Boolean)

    Should this item feature on the main page of SSvc?



116
117
118
# File 'lib/jss/api_object/self_servable.rb', line 116

def self_service_feature_on_main_page
  @self_service_feature_on_main_page
end

#self_service_force_users_to_view_descriptionBoolean

Returns Should an extra window appear before the user can install the item? (OSX SSvc only).

Returns:

  • (Boolean)

    Should an extra window appear before the user can install the item? (OSX SSvc only)



158
159
160
# File 'lib/jss/api_object/self_servable.rb', line 158

def self_service_force_users_to_view_description
  @self_service_force_users_to_view_description
end

#self_service_iconHash (readonly)

The Hash contains these keys with info about the icon:

  • :uri => [String] the URI for retriving the icon

  • :id => [Integer] the JSS id number for the icon (not all SSvc items have this)

  • :data => [String] the icon image encoded as Base64 (not all SSvc items have this)

  • :filename => [String] The name of the image file uploaded to the JSS, if applicable

Returns:

  • (Hash)

    The icon that appears in SelfSvc for this item



141
142
143
# File 'lib/jss/api_object/self_servable.rb', line 141

def self_service_icon
  @self_service_icon
end

#self_service_install_button_textString

Returns The text label on the install button in SSvc (OSX SSvc only).

Returns:

  • (String)

    The text label on the install button in SSvc (OSX SSvc only)



155
156
157
# File 'lib/jss/api_object/self_servable.rb', line 155

def self_service_install_button_text
  @self_service_install_button_text
end

#self_service_user_removableHash (readonly)

The keys are

  • :removal_disallowed => [String] one of the items in PROFILE_REMOVAL_OPTIONS

  • :password => [String] if :removal_disallowed is “With Authorization”, this contains the passwd (in plaintext) needed to remove the profile.

NOTE that the key should be called :removal_allowed, since ‘Never’ means it can’t be removed.

Returns:

  • (Hash)

    The security settings for profiles in SSvc



152
153
154
# File 'lib/jss/api_object/self_servable.rb', line 152

def self_service_user_removable
  @self_service_user_removable
end

Instance Method Details

#add_self_service_category(new_cat, display_in: true, feature_in: false) ⇒ void Also known as: change_self_service_category

This method returns an undefined value.

Add or change one of the categories for this item in SSvc.

Parameters:

  • new_cat (String)

    the name of a category for this item in SelfSvc

  • display_in (Boolean) (defaults to: true)

    should this item appear in the SelfSvc page for the new category?

  • feature_in (Boolean) (defaults to: false)

    should this item be featured in the SelfSvc page for the new category?

Raises:



254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
# File 'lib/jss/api_object/self_servable.rb', line 254

def add_self_service_category(new_cat, display_in: true, feature_in: false)
  new_cat.strip!
  raise JSS::NoSuchItemError, "No category '#{new_cat}' in the JSS" unless JSS::Category.all_names(:refresh).include? new_cat
  raise JSS::InvalidDataError, 'display_in must be true or false' unless JSS::TRUE_FALSE.include? display_in
  raise JSS::InvalidDataError, 'feature_in must be true or false' unless JSS::TRUE_FALSE.include? feature_in

  new_data = { name: new_cat, display_in: display_in, feature_in: feature_in }

  # see if this category is already among our categories.
  idx = @self_service_categories.index { |c| c[:name] == new_cat }

  if idx
    @self_service_categories[idx] = new_data
  else
    @self_service_categories << new_data
  end

  @need_to_update = true
end

#parse_self_servicevoid

This method returns an undefined value.

Call this during initialization of objects that have a self_service subset and the self_service attributes will be populated (as primary attributes) from @init_data



171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
# File 'lib/jss/api_object/self_servable.rb', line 171

def parse_self_service
  @init_data[:self_service] ||= {}
  @ss_data = @init_data[:self_service]

  @self_service_description = @ss_data[:self_service_description]
  @self_service_icon = @ss_data[:self_service_icon]
  @self_service_icon ||= {}

  @self_service_feature_on_main_page = @ss_data[:feature_on_main_page]
  @self_service_feature_on_main_page ||= false

  @self_service_categories = @ss_data[:self_service_categories]
  @self_service_categories ||= []

  # make this an empty hash if needed
  @self_service_security = @ss_data[:security]
  @self_service_security ||= {}

  @self_service_install_button_text = @ss_data[:install_button_text]
  @self_service_install_button_text ||= 'Install'

  @self_service_force_users_to_view_description = @ss_data[:force_users_to_view_description]
  @self_service_force_users_to_view_description ||= false
end

#remove_self_service_category(cat) ⇒ void

This method returns an undefined value.

Remove a category from those for this item in SSvc

Parameters:

  • cat (String)

    the name of the category to remove



280
281
282
283
# File 'lib/jss/api_object/self_servable.rb', line 280

def remove_self_service_category(cat)
  @self_service_categories.reject! { |c| c[:name] == cat }
  @need_to_update = true
end

#self_service_xmlREXML::Element

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.

Return a REXML <location> element to be included in the rest_xml of objects that have a Location subset

Returns:

  • (REXML::Element)


293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
# File 'lib/jss/api_object/self_servable.rb', line 293

def self_service_xml
  ssvc = REXML::Element.new('self_service')

  ssvc.add_element('self_service_description').text = @self_service_description
  ssvc.add_element('feature_on_main_page').text = @self_service_feature_on_main_page

  cats = ssvc.add_element('self_service_categories')
  @self_service_categories.each do |cat|
    catelem = cats.add_element('category')
    catelem.add_element('name').text = cat[:name]
    catelem.add_element('display_in').text = cat[:display_in] if cat.keys.include? :display_in
    catelem.add_element('feature_in').text = cat[:feature_in] if cat.keys.include? :feature_in
  end

  icon = ssvc.add_element('self_service_icon')
  @self_service_icon.each { |key, val|  icon.add_element(key.to_s).text = val }

  unless @self_service_security.empty?
    sec = ssvc.add_element('security')
    sec.add_element('removal_disallowed').text = @self_service_security[:removal_disallowed] if @self_service_security[:removal_disallowed]
    sec.add_element('password').text = @self_service_security[:password] if @self_service_security[:password]
  end

  ssvc.add_element('install_button_text').text = @self_service_install_button_text if @self_service_install_button_text
  ssvc.add_element('force_users_to_view_description').text = @self_service_force_users_to_view_description \
    unless @self_service_force_users_to_view_description.nil?

  ssvc
end