ruby-jss 0.6.3
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of ruby-jss might be problematic. Click here for more details.
- checksums.yaml +7 -0
- data/.yardopts +7 -0
- data/CHANGES.md +112 -0
- data/LICENSE.txt +174 -0
- data/README.md +426 -0
- data/THANKS.md +6 -0
- data/bin/cgrouper +485 -0
- data/bin/subnet-update +400 -0
- data/lib/jss-api.rb +2 -0
- data/lib/jss.rb +190 -0
- data/lib/jss/api_connection.rb +410 -0
- data/lib/jss/api_object.rb +616 -0
- data/lib/jss/api_object/advanced_search.rb +389 -0
- data/lib/jss/api_object/advanced_search/advanced_computer_search.rb +95 -0
- data/lib/jss/api_object/advanced_search/advanced_mobile_device_search.rb +96 -0
- data/lib/jss/api_object/advanced_search/advanced_user_search.rb +95 -0
- data/lib/jss/api_object/building.rb +92 -0
- data/lib/jss/api_object/category.rb +147 -0
- data/lib/jss/api_object/computer.rb +852 -0
- data/lib/jss/api_object/creatable.rb +98 -0
- data/lib/jss/api_object/criteriable.rb +189 -0
- data/lib/jss/api_object/criteriable/criteria.rb +231 -0
- data/lib/jss/api_object/criteriable/criterion.rb +228 -0
- data/lib/jss/api_object/department.rb +93 -0
- data/lib/jss/api_object/distribution_point.rb +560 -0
- data/lib/jss/api_object/extendable.rb +221 -0
- data/lib/jss/api_object/extension_attribute.rb +466 -0
- data/lib/jss/api_object/extension_attribute/computer_extension_attribute.rb +362 -0
- data/lib/jss/api_object/extension_attribute/mobile_device_extension_attribute.rb +189 -0
- data/lib/jss/api_object/extension_attribute/user_extension_attribute.rb +117 -0
- data/lib/jss/api_object/group.rb +380 -0
- data/lib/jss/api_object/group/computer_group.rb +124 -0
- data/lib/jss/api_object/group/mobile_device_group.rb +139 -0
- data/lib/jss/api_object/group/user_group.rb +139 -0
- data/lib/jss/api_object/ldap_server.rb +535 -0
- data/lib/jss/api_object/locatable.rb +286 -0
- data/lib/jss/api_object/matchable.rb +97 -0
- data/lib/jss/api_object/mobile_device.rb +556 -0
- data/lib/jss/api_object/netboot_server.rb +148 -0
- data/lib/jss/api_object/network_segment.rb +414 -0
- data/lib/jss/api_object/osx_configuration_profile.rb +262 -0
- data/lib/jss/api_object/package.rb +839 -0
- data/lib/jss/api_object/peripheral.rb +335 -0
- data/lib/jss/api_object/peripheral_type.rb +295 -0
- data/lib/jss/api_object/policy.rb +898 -0
- data/lib/jss/api_object/purchasable.rb +316 -0
- data/lib/jss/api_object/removable_macaddr.rb +98 -0
- data/lib/jss/api_object/scopable.rb +136 -0
- data/lib/jss/api_object/scopable/scope.rb +621 -0
- data/lib/jss/api_object/script.rb +631 -0
- data/lib/jss/api_object/self_servable.rb +356 -0
- data/lib/jss/api_object/site.rb +93 -0
- data/lib/jss/api_object/software_update_server.rb +109 -0
- data/lib/jss/api_object/updatable.rb +117 -0
- data/lib/jss/api_object/uploadable.rb +138 -0
- data/lib/jss/api_object/user.rb +272 -0
- data/lib/jss/client.rb +504 -0
- data/lib/jss/compatibility.rb +66 -0
- data/lib/jss/composer.rb +185 -0
- data/lib/jss/configuration.rb +306 -0
- data/lib/jss/db_connection.rb +298 -0
- data/lib/jss/exceptions.rb +95 -0
- data/lib/jss/ruby_extensions.rb +35 -0
- data/lib/jss/ruby_extensions/filetest.rb +43 -0
- data/lib/jss/ruby_extensions/hash.rb +79 -0
- data/lib/jss/ruby_extensions/ipaddr.rb +91 -0
- data/lib/jss/ruby_extensions/pathname.rb +77 -0
- data/lib/jss/ruby_extensions/string.rb +59 -0
- data/lib/jss/ruby_extensions/time.rb +63 -0
- data/lib/jss/server.rb +108 -0
- data/lib/jss/utility.rb +478 -0
- data/lib/jss/version.rb +31 -0
- metadata +187 -0
@@ -0,0 +1,898 @@
|
|
1
|
+
### Copyright 2016 Pixar
|
2
|
+
###
|
3
|
+
### Licensed under the Apache License, Version 2.0 (the "Apache License")
|
4
|
+
### with the following modification; you may not use this file except in
|
5
|
+
### compliance with the Apache License and the following modification to it:
|
6
|
+
### Section 6. Trademarks. is deleted and replaced with:
|
7
|
+
###
|
8
|
+
### 6. Trademarks. This License does not grant permission to use the trade
|
9
|
+
### names, trademarks, service marks, or product names of the Licensor
|
10
|
+
### and its affiliates, except as required to comply with Section 4(c) of
|
11
|
+
### the License and to reproduce the content of the NOTICE file.
|
12
|
+
###
|
13
|
+
### You may obtain a copy of the Apache License at
|
14
|
+
###
|
15
|
+
### http://www.apache.org/licenses/LICENSE-2.0
|
16
|
+
###
|
17
|
+
### Unless required by applicable law or agreed to in writing, software
|
18
|
+
### distributed under the Apache License with the above modification is
|
19
|
+
### distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
20
|
+
### KIND, either express or implied. See the Apache License for the specific
|
21
|
+
### language governing permissions and limitations under the Apache License.
|
22
|
+
###
|
23
|
+
###
|
24
|
+
|
25
|
+
###
|
26
|
+
module JSS
|
27
|
+
|
28
|
+
######################
|
29
|
+
### Module Constants
|
30
|
+
######################
|
31
|
+
|
32
|
+
|
33
|
+
######################
|
34
|
+
### Module Variables
|
35
|
+
######################
|
36
|
+
|
37
|
+
######################
|
38
|
+
### Module Methods
|
39
|
+
######################
|
40
|
+
|
41
|
+
|
42
|
+
#####################################
|
43
|
+
### Classes
|
44
|
+
#####################################
|
45
|
+
|
46
|
+
###
|
47
|
+
### A class implementing a JSS Policy.
|
48
|
+
###
|
49
|
+
### Like many API objects, the data comes from the API in sections, and
|
50
|
+
### the items in the :general section are mapped to direct attributes
|
51
|
+
### of this Class.
|
52
|
+
###
|
53
|
+
###
|
54
|
+
### Policy instances are partially read-only:
|
55
|
+
### - New policies cannot be created via this class, please use the WebApp.
|
56
|
+
### - Only a few attributes can be changed and updated via the Policy class:
|
57
|
+
### - - name
|
58
|
+
### - - frequency
|
59
|
+
### - - target_drive
|
60
|
+
### - - offline
|
61
|
+
### - - enabled
|
62
|
+
### - - category
|
63
|
+
### - - triggers
|
64
|
+
### - - scope, see {JSS::Scopable} and {JSS::Scopable::Scope}
|
65
|
+
### - - files and processes
|
66
|
+
### All other values and sections must be edited via the Web App.
|
67
|
+
###
|
68
|
+
### Policies may be deleted via this class
|
69
|
+
###
|
70
|
+
### @see JSS::APIObject
|
71
|
+
###
|
72
|
+
class Policy < JSS::APIObject
|
73
|
+
|
74
|
+
#####################################
|
75
|
+
### Mix-Ins
|
76
|
+
#####################################
|
77
|
+
|
78
|
+
include JSS::Updatable
|
79
|
+
include JSS::Scopable
|
80
|
+
include JSS::Uploadable
|
81
|
+
|
82
|
+
#####################################
|
83
|
+
### Class Methods
|
84
|
+
#####################################
|
85
|
+
|
86
|
+
#####################################
|
87
|
+
### Class Constants
|
88
|
+
#####################################
|
89
|
+
|
90
|
+
|
91
|
+
### The base for REST resources of this class
|
92
|
+
RSRC_BASE = "policies"
|
93
|
+
|
94
|
+
### the hash key used for the JSON list output of all objects in the JSS
|
95
|
+
RSRC_LIST_KEY = :policies
|
96
|
+
|
97
|
+
### The hash key used for the JSON object output.
|
98
|
+
### It's also used in various error messages
|
99
|
+
RSRC_OBJECT_KEY = :policy
|
100
|
+
|
101
|
+
### these keys, as well as :id and :name, are present in valid API JSON data for this class
|
102
|
+
VALID_DATA_KEYS = [:scope, :user_interaction, :files_processes ]
|
103
|
+
|
104
|
+
|
105
|
+
SECTIONS = [
|
106
|
+
:general,
|
107
|
+
:maintenance,
|
108
|
+
:account_maintenance,
|
109
|
+
:scripts,
|
110
|
+
:self_service,
|
111
|
+
:package_configuration,
|
112
|
+
:scope,
|
113
|
+
:user_interaction,
|
114
|
+
:reboot,
|
115
|
+
:files_processes,
|
116
|
+
:dock_items,
|
117
|
+
:disk_encryption,
|
118
|
+
:printers
|
119
|
+
]
|
120
|
+
|
121
|
+
FREQUENCIES = {
|
122
|
+
:ongoing => "Ongoing",
|
123
|
+
:once_per_computer => "Once per computer",
|
124
|
+
:once_per_user =>"Once per user",
|
125
|
+
:daily => "Once every day",
|
126
|
+
:weekly => "Once every week",
|
127
|
+
:monthly => "Once every month"
|
128
|
+
}
|
129
|
+
|
130
|
+
RESTART_WHEN = {
|
131
|
+
:if_pkg_requires => "Restart if a package or update requires it",
|
132
|
+
:now => "Restart immediately",
|
133
|
+
:delayed => "Restart",
|
134
|
+
:dont => "Do not restart"
|
135
|
+
}
|
136
|
+
|
137
|
+
RESTART_DISKS = {
|
138
|
+
:current => "Current Startup Disk",
|
139
|
+
:selected => "Currently Selected Startup Disk (No Bless)",
|
140
|
+
:netboot => "NetBoot",
|
141
|
+
:os_installer => "inPlaceOSUpgradeDirectory"
|
142
|
+
} # Note: any other value in :specify_startup is a path to some other drive to boot from, e.g. /Volumes/Foo
|
143
|
+
|
144
|
+
ACCOUNT_ACTIONS = {
|
145
|
+
:create => "Create",
|
146
|
+
:change_pw => "Reset",
|
147
|
+
:delete => "Delete",
|
148
|
+
:disable_fv2 => "DisableFileVault"
|
149
|
+
}
|
150
|
+
|
151
|
+
MGMT_ACCOUNT_ACTIONS = {
|
152
|
+
:no_change => "doNotChange",
|
153
|
+
:change_pw => "specified",
|
154
|
+
:generate_pw => "random",
|
155
|
+
:enable_fv2 => "fileVaultEnable",
|
156
|
+
:disable_fv2 => "fileVaultDisable"
|
157
|
+
}
|
158
|
+
|
159
|
+
PACKAGE_ACTIONS = {
|
160
|
+
:install => "Install",
|
161
|
+
:remove => "Uninstall",
|
162
|
+
:cache =>"Cache",
|
163
|
+
:install_cache => "Install Cached"
|
164
|
+
}
|
165
|
+
|
166
|
+
SCRIPT_PRIORITIES = {:pre => "Before", :post => "After"}
|
167
|
+
|
168
|
+
PRINTER_ACTIIONS = {:map => "install", :unmap => "uninstall"}
|
169
|
+
|
170
|
+
DOCK_ITEM_ACTIONS = {:add_start => "Add To Beginning", :add_end => "Add To End", :remove => "Remove"}
|
171
|
+
|
172
|
+
NETWORK_REQUIREMENTS = {:any => "Any", :ethernet => "EtherNet"}
|
173
|
+
|
174
|
+
TRIGGER_EVENTS = {
|
175
|
+
:startup => :trigger_startup,
|
176
|
+
:login => :trigger_login,
|
177
|
+
:logout => :trigger_logout,
|
178
|
+
:checkin => :trigger_checkin,
|
179
|
+
:network_state => :trigger_network_state_changed ,
|
180
|
+
:enrollment => :trigger_enrollment_complete ,
|
181
|
+
:custom => :trigger_other
|
182
|
+
}
|
183
|
+
|
184
|
+
TRIGGER_TYPES = {:event => "EVENT", :user => "USER_INITIATED"}
|
185
|
+
|
186
|
+
SCOPE_TARGET_KEY = :computers
|
187
|
+
|
188
|
+
######################
|
189
|
+
### Attributes
|
190
|
+
######################
|
191
|
+
|
192
|
+
##### General
|
193
|
+
### This data comes from the :general hash in the raw JSON data
|
194
|
+
### and correspond to the general section of the Edit Policy window in
|
195
|
+
### the JSS WebApp. They are general settings for this policy.
|
196
|
+
### We'll map it to direct attributes.
|
197
|
+
|
198
|
+
### @return [String] policy category name
|
199
|
+
attr_reader :category
|
200
|
+
|
201
|
+
### @return [String] how often to run the policy on each computer
|
202
|
+
attr_reader :frequency
|
203
|
+
|
204
|
+
### @return [String] which drive should the policy target
|
205
|
+
attr_reader :target_drive
|
206
|
+
|
207
|
+
### @return [Boolean] should be policy be available offline
|
208
|
+
attr_reader :offline
|
209
|
+
|
210
|
+
### @return [Boolean] is the policy enabled?
|
211
|
+
attr_reader :enabled
|
212
|
+
|
213
|
+
### @return [String] a string with the site name
|
214
|
+
attr_reader :site
|
215
|
+
|
216
|
+
|
217
|
+
### @return [Hash]
|
218
|
+
###
|
219
|
+
### Overrides for various defaults
|
220
|
+
###
|
221
|
+
### The hash looks like: !{ :distribution_point => "", :force_afp_smb => false, :netboot_server => "current", :target_drive => "default", :sus => "default"}
|
222
|
+
attr_reader :override_default_settings
|
223
|
+
|
224
|
+
### The API has a :network_requirements key in the general section, but
|
225
|
+
### in the UI its in a subsection called Client Side Limitiations.
|
226
|
+
### so we'll store it in a hash called client_side_limitations,
|
227
|
+
### defined below.
|
228
|
+
|
229
|
+
### the network_limitations hash of the general section seems to be redundant.
|
230
|
+
### it contains minimum_network_connection ("Ethernet" or "No Minimum")
|
231
|
+
### which is also reflected in the general[:network_requirements] ("Ethernet" or "Any")
|
232
|
+
### it contains network_segments, which are also listed
|
233
|
+
### in the limitations hash of the scope section
|
234
|
+
### it contains any_ip_address, which is true or false based on there being
|
235
|
+
### any network_segment limitations.
|
236
|
+
### Therefore, we'll ignore it, and use the other places for that data
|
237
|
+
|
238
|
+
### The API has a general key ":date_time_limitations" which has this
|
239
|
+
### this data:
|
240
|
+
### :activation - Time
|
241
|
+
### :expiration - Time
|
242
|
+
### :no_execute_on - An array of short day names as symbols, e.g. [:sun, :mon, :wed, :thu]
|
243
|
+
### :no_execute_start - Time
|
244
|
+
### :no_execute_end - Time
|
245
|
+
### but in the UI, those are set in the Server Side Limitiations and Client Side Limitiations.
|
246
|
+
### areas, so we'll store them in matching hashes below.
|
247
|
+
### attr_reader :date_time_limitations
|
248
|
+
|
249
|
+
### @return [Hash]
|
250
|
+
###
|
251
|
+
### The server-side limitations of this policy.
|
252
|
+
###
|
253
|
+
### The keys are :activation and :expiration, both are Times.
|
254
|
+
###
|
255
|
+
### the data comes from the API in the date_time_limitations hash of the general
|
256
|
+
### section, but the UI shows them in the Server Side Limitations area.
|
257
|
+
### This attribute is just for convience and consistency, and just
|
258
|
+
### refers to the data in their API locations
|
259
|
+
attr_reader :server_side_limitations
|
260
|
+
|
261
|
+
### @return [Hash]
|
262
|
+
###
|
263
|
+
### The client-side limitations of this policy.
|
264
|
+
###
|
265
|
+
### The keys are:
|
266
|
+
### - :no_execute_on - An array of short day names as strings, e.g. ["Sun", "Mon", "Tue"]
|
267
|
+
### - :no_execute_start - Time
|
268
|
+
### - :no_execute_end - Time
|
269
|
+
### - :network_connection - String
|
270
|
+
### The data for the first three comes from the API in the date_time_limitations
|
271
|
+
### hash of the general section.
|
272
|
+
### The fourth comes from the network_requirements of the general section of the API,
|
273
|
+
### but the UI shows them in the Client Side Limitations area.
|
274
|
+
###
|
275
|
+
### This attribute is just for convience and consistency, and just
|
276
|
+
### refers to the data in their API locations
|
277
|
+
attr_reader :client_side_limitations
|
278
|
+
|
279
|
+
### @return [String]
|
280
|
+
###
|
281
|
+
### Either EVENT or USER_INITIATED
|
282
|
+
###
|
283
|
+
### If it's EVENT, then one or more of the members @trigger_events must true.
|
284
|
+
attr_reader :trigger
|
285
|
+
|
286
|
+
### @return [Hash]
|
287
|
+
###
|
288
|
+
### The triggers that cause this policy to execute on a client when the @trigger is "EVENT"
|
289
|
+
###
|
290
|
+
### This is a hash with the following keys. Each comes from the API
|
291
|
+
### as a key in the :general hash, but they make more sense separated out
|
292
|
+
### like this.
|
293
|
+
### - :trigger_startup => Bool
|
294
|
+
### - :trigger_login => Bool
|
295
|
+
### - :trigger_logout => Bool
|
296
|
+
### - :trigger_checkin => Bool
|
297
|
+
### - :trigger_network_state_changed => Bool
|
298
|
+
### - :trigger_enrollment_complete => Bool
|
299
|
+
### - :trigger_other => the String that causes a custom trigger
|
300
|
+
###
|
301
|
+
### To edit a value, call
|
302
|
+
### set_trigger_event(type, new_val)
|
303
|
+
### where type is one of the keys in TRIGGER_EVENTS and new val is the new value (usually boolean)
|
304
|
+
###
|
305
|
+
attr_reader :trigger_events
|
306
|
+
|
307
|
+
##### client machine maintenence
|
308
|
+
### These are the computer maint. tasks
|
309
|
+
### that might be performed by this policy
|
310
|
+
### All are boolean
|
311
|
+
|
312
|
+
### @return [Boolean] client maintenance task
|
313
|
+
attr_reader :verify_startup_disk
|
314
|
+
|
315
|
+
### @return [Boolean] client maintenance task
|
316
|
+
attr_reader :permissions_repair
|
317
|
+
|
318
|
+
### @return [Boolean] client maintenance task
|
319
|
+
attr_reader :recon
|
320
|
+
|
321
|
+
### @return [Boolean] client maintenance task
|
322
|
+
attr_reader :fix_byhost
|
323
|
+
|
324
|
+
### @return [Boolean] client maintenance task
|
325
|
+
attr_reader :reset_name
|
326
|
+
|
327
|
+
### @return [Boolean] client maintenance task
|
328
|
+
attr_reader :flush_system_cache
|
329
|
+
|
330
|
+
### @return [Boolean] client maintenance task
|
331
|
+
attr_reader :install_cached_pkgs
|
332
|
+
|
333
|
+
### @return [Boolean] client maintenance task
|
334
|
+
attr_reader :flush_user_cache
|
335
|
+
|
336
|
+
### attr_reader :heal # deprecated
|
337
|
+
### attr_reader :prebinding # deprecated
|
338
|
+
|
339
|
+
##### client account maint
|
340
|
+
### acct related maintenence performed by this policy
|
341
|
+
|
342
|
+
### @return [Array<Hash>]
|
343
|
+
###
|
344
|
+
### The directory bindings applied
|
345
|
+
###
|
346
|
+
### each hash is like: !{:name => "LDAP", :id => 4}
|
347
|
+
attr_reader :directory_bindings
|
348
|
+
|
349
|
+
|
350
|
+
### @return [Hash] the open firmware mode and password
|
351
|
+
attr_reader :open_firmware_efi_password
|
352
|
+
|
353
|
+
### @return [Hash]
|
354
|
+
###
|
355
|
+
### The management accout changes applied by the policy
|
356
|
+
###
|
357
|
+
### The keys are:
|
358
|
+
### - :action see MGMT_ACCOUNT_ACTIONS
|
359
|
+
### - :managed_password
|
360
|
+
### - :managed_password_md5
|
361
|
+
### - :managed_password_sha256
|
362
|
+
### - :managed_password_length # for random generating pws
|
363
|
+
###
|
364
|
+
attr_reader :management_account
|
365
|
+
|
366
|
+
### @return [Array<Hash>]
|
367
|
+
###
|
368
|
+
### Local accts acted-upon by this policy
|
369
|
+
###
|
370
|
+
### Keys are:
|
371
|
+
### - :action => "Create",
|
372
|
+
### - :hint => "foo bar",
|
373
|
+
### - :picture => "/path/to/pic.tif",
|
374
|
+
### - :admin => true,
|
375
|
+
### - :home => "/Users/chrisltest",
|
376
|
+
### - :realname => "ChrisTest Lasell",
|
377
|
+
### - :filevault_enabled => true,
|
378
|
+
### - :username => "chrisltest",
|
379
|
+
### - :password_md5 => "3858f62230ac3c915f300c664312c63f",
|
380
|
+
### - : password => "foobar",
|
381
|
+
### - :password_sha256=> "c3ab8ff13720e8ad9047dd39466b3c8974e592c2fa383d4a3960714caef0c4f2"
|
382
|
+
###
|
383
|
+
attr_reader :accounts
|
384
|
+
|
385
|
+
### @return [Array<Hash>]
|
386
|
+
###
|
387
|
+
### The pkgs handled by this policy
|
388
|
+
###
|
389
|
+
### Hash keys are:
|
390
|
+
### - :action => "Install"
|
391
|
+
### - :update_autorun => false,
|
392
|
+
### - :feu => false,
|
393
|
+
### - :name => "rbgem-json-1.6.5-4.pkg",
|
394
|
+
### - :id => 1073
|
395
|
+
###
|
396
|
+
attr_reader :packages
|
397
|
+
|
398
|
+
### @return [Array<Hash>]
|
399
|
+
###
|
400
|
+
### The scripts run by this policy
|
401
|
+
###
|
402
|
+
### Hash keys are:
|
403
|
+
### - :name => "chromegetter.sh",
|
404
|
+
### - :parameter4 => "",
|
405
|
+
### - :parameter5 => "",
|
406
|
+
### - :parameter6 => "",
|
407
|
+
### - :parameter7 => "",
|
408
|
+
### - :parameter8 => "",
|
409
|
+
### - :parameter9 => "",
|
410
|
+
### - :parameter10 => "",
|
411
|
+
### - :parameter11 => "",
|
412
|
+
### - :id => 1428,
|
413
|
+
### - :priority => "After"
|
414
|
+
###
|
415
|
+
attr_reader :scripts
|
416
|
+
|
417
|
+
|
418
|
+
### @return [Hash]
|
419
|
+
###
|
420
|
+
### Self-service-related data for this policy
|
421
|
+
###
|
422
|
+
### The hash keys are:
|
423
|
+
### - :self_service_icon => !{:uri => String,:id => Integer, :filename => String}
|
424
|
+
### - :use_for_self_service => true,
|
425
|
+
### - :install_button_text => "Install",
|
426
|
+
### - :self_service_description => "Descriptive text",
|
427
|
+
### - :force_users_to_view_description => false
|
428
|
+
###
|
429
|
+
### Note: we'll add a ruby-std convenience method below "self_service?"
|
430
|
+
### which returns the :use_for_self_service key.
|
431
|
+
attr_reader :self_service
|
432
|
+
|
433
|
+
#### user interaction
|
434
|
+
### These are extracted from the :user_interaction hash
|
435
|
+
### in the JSON output, which looks like this:
|
436
|
+
### :message_start => "",
|
437
|
+
### :allow_users_to_defer => false,
|
438
|
+
### :allow_deferral_until_utc => "",
|
439
|
+
### :message_finish => ""
|
440
|
+
###
|
441
|
+
|
442
|
+
### @return [Boolean] can the user defer the policy?
|
443
|
+
attr_reader :user_may_defer
|
444
|
+
|
445
|
+
### @return [Time] when is the user no longer allowed to defer?
|
446
|
+
attr_reader :user_may_defer_until
|
447
|
+
|
448
|
+
### @return [String] the message shown the user at policy start
|
449
|
+
attr_reader :user_message_start
|
450
|
+
|
451
|
+
### @return [String] the message shown the user at policy end
|
452
|
+
attr_reader :user_message_finish
|
453
|
+
|
454
|
+
### @return [Hash]
|
455
|
+
###
|
456
|
+
### Reboot options for the policy
|
457
|
+
###
|
458
|
+
### The hash keys are:
|
459
|
+
### - :user_logged_in => "Do not restart",
|
460
|
+
### - :minutes_until_reboot => 5,
|
461
|
+
### - :message=> "This computer will restart in 5 minutes. Please save anything you are working on and log out by choosing Log Out from the bottom of the Apple menu.",
|
462
|
+
### - :startup_disk => "Current Startup Disk",
|
463
|
+
### - :specify_startup => "",
|
464
|
+
### - :no_user_logged_in => "Do not restart"
|
465
|
+
###
|
466
|
+
attr_reader :reboot_options
|
467
|
+
|
468
|
+
##### files & processes
|
469
|
+
### a hash like this:
|
470
|
+
### {:spotlight_search => "Spotlight This",
|
471
|
+
### :search_for_process => "SafariProcess",
|
472
|
+
### :search_by_path => "/this/is/a/path",
|
473
|
+
### :kill_process => true,
|
474
|
+
### :delete_file => true,
|
475
|
+
### :run_command => "/usr/local/pixar/sbin/force-fde-logout --setup",
|
476
|
+
### :locate_file => "this-is-a-filename",
|
477
|
+
### :update_locate_database => true}
|
478
|
+
###
|
479
|
+
### NOTE, since these items are editable, they have custom getters/setters
|
480
|
+
### so that the hash isn't directly changable without @need_to_update.
|
481
|
+
### attr_reader :files_processes
|
482
|
+
|
483
|
+
|
484
|
+
### @return [Array<Hash>]
|
485
|
+
###
|
486
|
+
### The dock items handled by this policy
|
487
|
+
###
|
488
|
+
### each item hash looks like: !{:name => "Mail", :id => 14, :action => "Add To Beginning"}
|
489
|
+
attr_reader :dock_items
|
490
|
+
|
491
|
+
### @return [Hash]
|
492
|
+
###
|
493
|
+
### Disk encryption options for this policy
|
494
|
+
###
|
495
|
+
### The hash looks like !{:disk_encryption_configuration_id => 3, :action => "apply"}
|
496
|
+
attr_reader :disk_encryption
|
497
|
+
|
498
|
+
### @return [Array<Hash>]
|
499
|
+
###
|
500
|
+
### The printers handled by this policy
|
501
|
+
###
|
502
|
+
### Each Hash looks like: !{:make_default => false, :name => "torlan", :id => 3, :action => "install"}
|
503
|
+
attr_reader :printers
|
504
|
+
|
505
|
+
#####################################
|
506
|
+
### Public Instance Methods
|
507
|
+
#####################################
|
508
|
+
|
509
|
+
###
|
510
|
+
### @see APIObject#initialize
|
511
|
+
###
|
512
|
+
def initialize(args = {})
|
513
|
+
|
514
|
+
super
|
515
|
+
|
516
|
+
|
517
|
+
gen = @init_data[:general]
|
518
|
+
@category = JSS::APIObject.get_name(gen[:category])
|
519
|
+
@frequency = gen[:frequency]
|
520
|
+
@target_drive = gen[:target_drive]
|
521
|
+
@offline = gen[:offline]
|
522
|
+
@enabled = gen[:enabled]
|
523
|
+
@site = JSS::APIObject.get_name(gen[:site][:name])
|
524
|
+
@override_default_settings = gen[:override_default_settings]
|
525
|
+
@trigger = gen[:trigger ]
|
526
|
+
@trigger_events = {
|
527
|
+
:trigger_startup => gen[:trigger_startup ],
|
528
|
+
:trigger_login => gen[:trigger_login ],
|
529
|
+
:trigger_logout => gen[:trigger_logout ],
|
530
|
+
:trigger_checkin => gen[:trigger_checkin ],
|
531
|
+
:trigger_network_state_changed => gen[:trigger_network_state_changed ],
|
532
|
+
:trigger_enrollment_complete => gen[:trigger_enrollment_complete ],
|
533
|
+
:trigger_other => gen[:trigger_other ]
|
534
|
+
}
|
535
|
+
|
536
|
+
dtl = gen[:date_time_limitations]
|
537
|
+
|
538
|
+
@server_side_limitations = {
|
539
|
+
:activation => JSS.epoch_to_time(dtl[:activation_date_epoch]),
|
540
|
+
:expiration => JSS.epoch_to_time(dtl[:expiration_date_epoch])
|
541
|
+
}
|
542
|
+
|
543
|
+
@client_side_limitations = {
|
544
|
+
:no_execute_on => dtl[:no_execute_on], # NOTE- there's a bug in the JSON output, it's been reported to JAMF.
|
545
|
+
:no_execute_start => dtl[:no_execute_start], # String like "1:01 AM"
|
546
|
+
:no_execute_end => dtl[:no_execute_end], # String like "2:02 PM"
|
547
|
+
:network_requirements => gen[:network_requirements]
|
548
|
+
}
|
549
|
+
|
550
|
+
maint = @init_data[:maintenance]
|
551
|
+
@verify_startup_disk = maint[:verify]
|
552
|
+
@permissions_repair = maint[:permissions]
|
553
|
+
@recon = maint[:recon]
|
554
|
+
@fix_byhost = maint[:byhost]
|
555
|
+
@reset_name = maint[:reset_name]
|
556
|
+
@flush_system_cache = maint[:system_cache]
|
557
|
+
@install_cached_pkgs = maint[:install_all_cached_packages]
|
558
|
+
@flush_user_cache = maint[:user_cache]
|
559
|
+
|
560
|
+
amaint = @init_data[:account_maintenance]
|
561
|
+
@directory_bindings = amaint[:directory_bindings]
|
562
|
+
@open_firmware_efi_password = amaint[:open_firmware_efi_password]
|
563
|
+
@management_account = amaint[:management_account]
|
564
|
+
@accounts = amaint[:accounts]
|
565
|
+
|
566
|
+
@packages = @init_data[:package_configuration][:packages] ? @init_data[:package_configuration][:packages] : []
|
567
|
+
|
568
|
+
@scripts = @init_data[:scripts]
|
569
|
+
|
570
|
+
@self_service = @init_data[:self_service]
|
571
|
+
|
572
|
+
uint = @init_data[:user_interaction]
|
573
|
+
@user_may_defer = uint[:allow_users_to_defer]
|
574
|
+
@user_may_defer_until = JSS.parse_datetime uint[:allow_deferral_until_utc]
|
575
|
+
@user_message_start = uint[:message_start]
|
576
|
+
@user_message_finish = uint[:message_finish]
|
577
|
+
|
578
|
+
@reboot_options = @init_data[:reboot]
|
579
|
+
|
580
|
+
@files_processes = @init_data[:files_processes]
|
581
|
+
|
582
|
+
@dock_items = @init_data[:dock_items]
|
583
|
+
|
584
|
+
@disk_encryption = @init_data[:disk_encryption]
|
585
|
+
|
586
|
+
@printers = @init_data[:printers]
|
587
|
+
|
588
|
+
parse_scope
|
589
|
+
|
590
|
+
end # init
|
591
|
+
|
592
|
+
###
|
593
|
+
### Change the enabled state of this item
|
594
|
+
###
|
595
|
+
### @param new_val[Boolean] the new state.
|
596
|
+
###
|
597
|
+
### @return [void]
|
598
|
+
###
|
599
|
+
def enabled= (new_val)
|
600
|
+
return nil if @enabled == new_val
|
601
|
+
raise JSS::InvalidDataError, "New value must be true or false" unless JSS::TRUE_FALSE.include? new_val
|
602
|
+
@enabled = new_val
|
603
|
+
@need_to_update = true
|
604
|
+
end
|
605
|
+
|
606
|
+
###
|
607
|
+
### Set a new frequency for this policy.
|
608
|
+
###
|
609
|
+
### @param freq[Symbol] the desired frequency, must be one of the keys of {FREQUENCIES}
|
610
|
+
###
|
611
|
+
### @return [void]
|
612
|
+
###
|
613
|
+
def frequency= (freq)
|
614
|
+
raise JSS::InvalidDataError, "New frequency must be one of :#{FREQUENCIES.keys.join ", :"}" unless FREQUENCIES.keys.include? freq
|
615
|
+
@frequency = FREQUENCIES[freq]
|
616
|
+
@need_to_update = true
|
617
|
+
end
|
618
|
+
|
619
|
+
###
|
620
|
+
### Set a new target drive for this policy.
|
621
|
+
###
|
622
|
+
### @param path_to_drive[String,Pathname] the full path to the target drive, must start with a '/'
|
623
|
+
###
|
624
|
+
### @return [void]
|
625
|
+
###
|
626
|
+
def target_drive= (path_to_drive)
|
627
|
+
raise JSS::InvalidDataError, "Path to target drive must be absolute" unless path_to_drive.to_s.start_with? '/'
|
628
|
+
@target_drive = path_to_drive.to_s
|
629
|
+
@need_to_update = true
|
630
|
+
end
|
631
|
+
|
632
|
+
###
|
633
|
+
### Set whether this policy is available offline.
|
634
|
+
###
|
635
|
+
### @param new_val[Boolean]
|
636
|
+
###
|
637
|
+
### @return [void]
|
638
|
+
###
|
639
|
+
def offline= (new_val)
|
640
|
+
raise JSS::InvalidDataError, "New value must be boolean true or false" unless JSS::TRUE_FALSE.include? new_val
|
641
|
+
@offline = new_val
|
642
|
+
@need_to_update = true
|
643
|
+
end
|
644
|
+
|
645
|
+
###
|
646
|
+
### Change the category of this item, arg is a category name
|
647
|
+
###
|
648
|
+
### @param new_val[String] the name of the new category
|
649
|
+
###
|
650
|
+
### @return [void]
|
651
|
+
###
|
652
|
+
def category= (new_val = JSS::Category::DEFAULT_CATEGORY)
|
653
|
+
return nil if @category == new_val
|
654
|
+
new_val = nil if new_val == ''
|
655
|
+
new_val ||= JSS::Category::DEFAULT_CATEGORY
|
656
|
+
raise JSS::NoSuchItemError, "No category '#{new_val}' in the JSS" unless JSS::Category.all_names(:refresh).include? new_val
|
657
|
+
@category = new_val
|
658
|
+
@need_to_update = true
|
659
|
+
end
|
660
|
+
|
661
|
+
###
|
662
|
+
### Change a trigger event
|
663
|
+
###
|
664
|
+
### @param type[Symbol] the type of trigger, one of the keys of {TRIGGER_EVENTS}
|
665
|
+
###
|
666
|
+
### @param new_val[Boolean] whether the type of trigger is active or not.
|
667
|
+
###
|
668
|
+
### @return [void]
|
669
|
+
###
|
670
|
+
def set_trigger_event (type, new_val)
|
671
|
+
raise JSS::InvalidDataError, "Trigger type must be one of #{TRIGGER_EVENTS.keys.join(', ')}" unless TRIGGER_EVENTS.keys.include? type
|
672
|
+
if type == :custom
|
673
|
+
raise JSS::InvalidDataError, "Custom triggers must be Strings" unless new_val.kind_of? String
|
674
|
+
else
|
675
|
+
raise JSS::InvalidDataError, "Non-custom triggers must be true or false" unless JSS::TRUE_FALSE.include? new_val
|
676
|
+
end
|
677
|
+
@trigger_events[TRIGGER_EVENTS[type]] = new_val
|
678
|
+
@need_to_update = true
|
679
|
+
end
|
680
|
+
|
681
|
+
###
|
682
|
+
### @return [String] The unix shell command to run on ths client.
|
683
|
+
###
|
684
|
+
def run_command ; @files_processes[:run_command] ; end
|
685
|
+
|
686
|
+
###
|
687
|
+
### Set the unix shell command to be run on the client
|
688
|
+
###
|
689
|
+
### @param command[String] the unix shell command to be run on the client
|
690
|
+
###
|
691
|
+
### @return [void]
|
692
|
+
###
|
693
|
+
def run_command= (command)
|
694
|
+
raise JSS::InvalidDataError, "Command to run must be a String" unless command.is_a? String
|
695
|
+
@files_processes[:run_command] = command
|
696
|
+
@need_to_update = true
|
697
|
+
end
|
698
|
+
|
699
|
+
###
|
700
|
+
### @return [Boolean] Should we update the database used by the locate command?
|
701
|
+
###
|
702
|
+
def update_locate_database? ; @files_processes[:update_locate_database] ; end
|
703
|
+
|
704
|
+
###
|
705
|
+
### Set whether or not to update the database used by the locate command.
|
706
|
+
###
|
707
|
+
### @param tf[Boolean] whether or not to update the database used by the locate command.
|
708
|
+
###
|
709
|
+
### @return [void]
|
710
|
+
###
|
711
|
+
def update_locate_database= (tf)
|
712
|
+
@files_processes[:update_locate_database] = tf ? true : false
|
713
|
+
@need_to_update = true
|
714
|
+
end
|
715
|
+
|
716
|
+
###
|
717
|
+
### @return [String] The process name to search for on the client
|
718
|
+
###
|
719
|
+
def search_for_process
|
720
|
+
@files_processes[:search_for_process]
|
721
|
+
end
|
722
|
+
|
723
|
+
###
|
724
|
+
### @return [Boolean] Should the searched-for process be killed if found.
|
725
|
+
###
|
726
|
+
def kill_process?
|
727
|
+
@files_processes[:kill_process]
|
728
|
+
end
|
729
|
+
|
730
|
+
###
|
731
|
+
### Set the process name to search for, and if it should be killed if found.
|
732
|
+
###
|
733
|
+
### Setter methods (which end with =) can't easily take
|
734
|
+
### multiple arguments, so we instead name them "set_blah_blah"
|
735
|
+
### rather than "blah_blah="
|
736
|
+
###
|
737
|
+
### @param process[String] the process name to search for
|
738
|
+
###
|
739
|
+
### @param kill[Boolean] should be process be killed if found
|
740
|
+
###
|
741
|
+
### @return [void]
|
742
|
+
###
|
743
|
+
def set_search_for_process (process, kill = false)
|
744
|
+
@files_processes[:search_for_process] = process.to_s
|
745
|
+
@files_processes[:kill_process] = kill ? true : false
|
746
|
+
@need_to_update = true
|
747
|
+
end
|
748
|
+
|
749
|
+
###
|
750
|
+
### @return [Pathname] The path to search for
|
751
|
+
###
|
752
|
+
def search_by_path ; Pathname.new @files_processes[:search_by_path] ; end
|
753
|
+
|
754
|
+
###
|
755
|
+
### @return [Boolean] Should the searched-for path be deleted if found?
|
756
|
+
###
|
757
|
+
def delete_file? ; @files_processes[:delete_file] ; end
|
758
|
+
|
759
|
+
###
|
760
|
+
### Set the path to search for, a String or Pathname, and whether or not to delete it if found.
|
761
|
+
###
|
762
|
+
### Setter methods (which end with =) can't easily take
|
763
|
+
### multiple arguments, so we instead name them "set_blah_blah"
|
764
|
+
### rather than "blah_blah="
|
765
|
+
###
|
766
|
+
### @param path[String,Pathname] the path to search for
|
767
|
+
###
|
768
|
+
### @param delete[Boolean] should the path be deleted if found
|
769
|
+
###
|
770
|
+
### @return [void]
|
771
|
+
###
|
772
|
+
def set_search_by_path (path, delete = false)
|
773
|
+
raise JSS::InvalidDataError, "Path to search for must be a String or a Pathname" unless path.is_a? String or path.is_a? Pathname
|
774
|
+
@files_processes[:search_by_path] = path.to_s
|
775
|
+
@files_processes[:delete_file] = delete ? true : false
|
776
|
+
@need_to_update = true
|
777
|
+
end
|
778
|
+
|
779
|
+
###
|
780
|
+
### @return [String] The term to search for using spotlight
|
781
|
+
###
|
782
|
+
def spotlight_search ; @files_processes[:spotlight_search] ; end
|
783
|
+
|
784
|
+
### Set the term to seach for using spotlight
|
785
|
+
###
|
786
|
+
### @param term[String] the term to seach for using spotlight
|
787
|
+
###
|
788
|
+
### @return [void]
|
789
|
+
###
|
790
|
+
def spotlight_search= (term)
|
791
|
+
raise JSS::InvalidDataError, "Spotlight search term must be a String" unless term.is_a? String
|
792
|
+
@files_processes[:spotlight_search] = term
|
793
|
+
@need_to_update = true
|
794
|
+
end
|
795
|
+
|
796
|
+
###
|
797
|
+
### @return [String] The term to seach for using the locate command
|
798
|
+
###
|
799
|
+
def locate_file ; @files_processes[:locate_file] ; end
|
800
|
+
|
801
|
+
### Set the term to seach for using the locate command
|
802
|
+
###
|
803
|
+
### @param term[String] the term to seach for using the locate command
|
804
|
+
###
|
805
|
+
### @return [void]
|
806
|
+
###
|
807
|
+
def locate_file= (term)
|
808
|
+
raise JSS::InvalidDataError, "Term to locate must be a String" unless term.is_a? String
|
809
|
+
@files_processes[:locate_file] = term
|
810
|
+
@need_to_update = true
|
811
|
+
end
|
812
|
+
|
813
|
+
### @return [Array] the id's of the packages handled by the policy
|
814
|
+
def package_ids; @packages.map{|p| p[:id]} ; end
|
815
|
+
|
816
|
+
### @return [Array] the names of the packages handled by the policy
|
817
|
+
def package_names; @packages.map{|p| p[:name]} ; end
|
818
|
+
|
819
|
+
### @return [Array] the id's of the scripts handled by the policy
|
820
|
+
def script_ids; @scripts.map{|p| p[:id]} ; end
|
821
|
+
|
822
|
+
### @return [Array] the names of the scripts handled by the policy
|
823
|
+
def script_names; @scripts.map{|p| p[:name]} ; end
|
824
|
+
|
825
|
+
### @return [Array] the id's of the directory_bindings handled by the policy
|
826
|
+
def directory_binding_ids; @directory_bindings.map{|p| p[:id]} ; end
|
827
|
+
|
828
|
+
### @return [Array] the names of the directory_bindings handled by the policy
|
829
|
+
def directory_binding_names; @directory_bindings.map{|p| p[:name]} ; end
|
830
|
+
|
831
|
+
### @return [Array] the id's of the dock_items handled by the policy
|
832
|
+
def dock_item_ids; @dock_items.map{|p| p[:id]} ; end
|
833
|
+
|
834
|
+
### @return [Array] the names of the dock_items handled by the policy
|
835
|
+
def dock_item_names; @dock_items.map{|p| p[:name]} ; end
|
836
|
+
|
837
|
+
### @return [Array] the id's of the printers handled by the policy
|
838
|
+
def printer_ids; @printers.map{|p| p[:id]} ; end
|
839
|
+
|
840
|
+
### @return [Array] the names of the printers handled by the policy
|
841
|
+
def printer_names; @printers.map{|p| p[:name]} ; end
|
842
|
+
|
843
|
+
### @return [Boolean] is this policy available in SelfService?
|
844
|
+
def self_service?; @self_service[:use_for_self_service] ; end
|
845
|
+
|
846
|
+
### Try to execute this policy on this machine.
|
847
|
+
###
|
848
|
+
### @param show_output[Boolean] should the stdout and stderr of the
|
849
|
+
### 'jamf policy' command be sent to stdout in realtime?
|
850
|
+
###
|
851
|
+
### @return [Boolean, nil] The success of the 'jamf policy' command, or nil
|
852
|
+
### if the policy couldn't be executed (out of scope, policy disabled, etc)
|
853
|
+
###
|
854
|
+
def run (show_output = false)
|
855
|
+
return nil unless enabled?
|
856
|
+
output = JSS::Client.run_jamf("policy", "-id #{id}", show_output)
|
857
|
+
return nil if output.include? 'No policies were found for the ID'
|
858
|
+
return $?.exitstatus == 0 ? true : false
|
859
|
+
end
|
860
|
+
|
861
|
+
### Aliases
|
862
|
+
alias enabled? enabled
|
863
|
+
alias pkgs packages
|
864
|
+
alias command_to_run run_command
|
865
|
+
alias delete_path? delete_file?
|
866
|
+
alias execute run
|
867
|
+
|
868
|
+
#####################################
|
869
|
+
### Private Instance Methods
|
870
|
+
#####################################
|
871
|
+
private
|
872
|
+
|
873
|
+
def rest_xml
|
874
|
+
doc = REXML::Document.new APIConnection::XML_HEADER
|
875
|
+
obj = doc.add_element RSRC_OBJECT_KEY.to_s
|
876
|
+
|
877
|
+
general = obj.add_element "general"
|
878
|
+
general.add_element('name').text = @name
|
879
|
+
general.add_element('enabled').text = @enabled
|
880
|
+
general.add_element('frequency').text = @frequency
|
881
|
+
general.add_element('target_drive').text = @target_drive
|
882
|
+
general.add_element('offline').text = @offline
|
883
|
+
general.add_element('category').add_element('name').text = @category
|
884
|
+
|
885
|
+
JSS.hash_to_rexml_array(@trigger_events).each{|t| general << t}
|
886
|
+
|
887
|
+
obj << @scope.scope_xml
|
888
|
+
|
889
|
+
files_processes = obj.add_element "files_processes"
|
890
|
+
JSS.hash_to_rexml_array(@files_processes).each{|f| files_processes << f}
|
891
|
+
|
892
|
+
return doc.to_s
|
893
|
+
end
|
894
|
+
|
895
|
+
end # class policy
|
896
|
+
|
897
|
+
end # module
|
898
|
+
|