ruby-jss 1.2.4a1 → 1.2.4a2
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 +4 -4
- data/lib/jamf/api/abstract_classes/collection_resource.rb +9 -9
- data/lib/jamf/api/abstract_classes/json_object.rb +17 -6
- data/lib/jamf/api/connection.rb +109 -87
- data/lib/jamf/api/connection/token.rb +4 -4
- data/lib/jamf/validate.rb +3 -3
- data/lib/jamf/version.rb +1 -1
- data/lib/jss/version.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f394d84e5b001b374b534b114addc50cf5ea911804926912c84b0a57bb1cf658
|
4
|
+
data.tar.gz: 5bdaecdfc2e51632b0defe59d7c91f69b9da3b72605461793251a97a0364167f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c72272007ed1015d0647cb49ffba9701be8b19293cdad46eb04eff7a3c47d505441faf4ed95fb25de0774b4899a92c6659e4079b7c74d9893d83154f65aa619b
|
7
|
+
data.tar.gz: 84d17e840a8e7872222dd1ed4b0ea026a04d6a44dfeeed1f07181f8569919049120838d6aa4c2d6736a9cfbee8ccc42bc42fb8437223cbb655e1670801ac734f
|
@@ -239,10 +239,10 @@ module Jamf
|
|
239
239
|
raise Jamf::UnsupportedError, "#{self}'s are not currently creatable via the API" unless self.creatable?
|
240
240
|
|
241
241
|
validate_not_abstract
|
242
|
+
params.delete :id # no such animal when .creating
|
242
243
|
|
243
|
-
|
244
|
+
validate_create_params(params, cnx)
|
244
245
|
|
245
|
-
params.delete :id # no such animal when .creating
|
246
246
|
params[:creating_from_create] = true
|
247
247
|
new params, cnx: cnx
|
248
248
|
end
|
@@ -356,15 +356,16 @@ module Jamf
|
|
356
356
|
end # create_list_methods
|
357
357
|
private_class_method :create_list_methods
|
358
358
|
|
359
|
-
# validate that our .create data
|
360
|
-
# They can't be nil or empty.
|
359
|
+
# validate that our .create data is OK
|
361
360
|
#
|
362
|
-
def self.
|
363
|
-
|
364
|
-
raise
|
361
|
+
def self.validate_create_params(params, cnx)
|
362
|
+
params.keys.each do |param|
|
363
|
+
raise ArgumentError, "Unknown parameter: #{param}" unless self::OBJECT_MODEL.key? param
|
364
|
+
|
365
|
+
params[param] = validate_attr param, params[param], cnx: cnx
|
365
366
|
end
|
366
367
|
end
|
367
|
-
private_class_method :
|
368
|
+
private_class_method :validate_create_params
|
368
369
|
|
369
370
|
# Given an indentier attr. key, and a value,
|
370
371
|
# return the id where that ident has that value, or nil
|
@@ -385,7 +386,6 @@ module Jamf
|
|
385
386
|
end
|
386
387
|
private_class_method :id_from_other_ident
|
387
388
|
|
388
|
-
|
389
389
|
# Instance Methods
|
390
390
|
#####################################
|
391
391
|
|
@@ -749,6 +749,11 @@ module Jamf
|
|
749
749
|
# If the attribute is defined as a :string, :integer, :float or :bool
|
750
750
|
# without an enum or validator, it is confirmed to be the correct type
|
751
751
|
#
|
752
|
+
# If the attribute is required, it can't be nil or empty
|
753
|
+
#
|
754
|
+
# If the attribute is an identifier, and the class is a subclass of
|
755
|
+
# CollectionResource, it must be unique among the collection
|
756
|
+
#
|
752
757
|
# Otherwise, the value is returned unchanged.
|
753
758
|
#
|
754
759
|
# If the attribute is defined as an identifier, it must be unique among
|
@@ -767,9 +772,11 @@ module Jamf
|
|
767
772
|
def self.validate_attr(attr_name, value, cnx: Jamf.cnx)
|
768
773
|
attr_def = self::OBJECT_MODEL[attr_name]
|
769
774
|
|
775
|
+
raise ArgumentError, "Unknown attribute: #{attr_name} for #{self} objects" unless attr_def
|
776
|
+
|
770
777
|
# validate our value, which will raise an error or
|
771
778
|
# convert the value to the required type.
|
772
|
-
|
779
|
+
value =
|
773
780
|
|
774
781
|
# by enum, must be a value of the enum
|
775
782
|
if attr_def[:enum]
|
@@ -778,16 +785,15 @@ module Jamf
|
|
778
785
|
|
779
786
|
# by class, the class validates the value passed with .new
|
780
787
|
elsif attr_def[:class].is_a? Class
|
781
|
-
|
782
788
|
klass = attr_def[:class]
|
783
789
|
# validation happens in klass.new
|
784
790
|
value.is_a?(klass) ? value : klass.new(value, cnx: cnx)
|
785
791
|
|
786
|
-
# by Validate method - pass to the method
|
792
|
+
# by specified Validate method - pass to the method
|
787
793
|
elsif attr_def[:validator]
|
788
794
|
Jamf::Validate.send(attr_def[:validator], value)
|
789
795
|
|
790
|
-
# By json type - pass to the matching validate method
|
796
|
+
# By json primative type - pass to the matching validate method
|
791
797
|
elsif JSON_TYPE_CLASSES.include? attr_def[:class]
|
792
798
|
Jamf::Validate.send(attr_def[:class], value)
|
793
799
|
|
@@ -796,10 +802,15 @@ module Jamf
|
|
796
802
|
value
|
797
803
|
end # if
|
798
804
|
|
805
|
+
# if this is required, it can't be nil or empty
|
806
|
+
if attr_def[:required]
|
807
|
+
raise Jamf::MissingDataError, "Required attribute '#{attr_name}:' may not be nil or empty" if value.to_s.empty?
|
808
|
+
end
|
809
|
+
|
799
810
|
# if this is an identifier, it must be unique
|
800
|
-
Jamf::Validate.
|
811
|
+
Jamf::Validate.doesnt_exist(value, self, attr_name, cnx: cnx) if attr_def[:identifier] && superclass == Jamf::CollectionResource
|
801
812
|
|
802
|
-
|
813
|
+
value
|
803
814
|
end # validate_attr(attr_name, value)
|
804
815
|
private_class_method :validate_attr
|
805
816
|
|
data/lib/jamf/api/connection.rb
CHANGED
@@ -263,30 +263,50 @@ module Jamf
|
|
263
263
|
# This sets all the instance vars to nil, and flushes/creates the caches
|
264
264
|
disconnect
|
265
265
|
|
266
|
-
#
|
267
|
-
params
|
268
|
-
|
266
|
+
# This sets @token, and adds host, port, user to params from a Token object
|
267
|
+
parse_token params
|
268
|
+
|
269
|
+
# Get host, port, user and pw from a URL, add to params if needed
|
270
|
+
parse_url url, params
|
269
271
|
|
270
272
|
# apply defaults from config, client, and then this class.
|
271
273
|
apply_connection_defaults params
|
272
274
|
|
273
|
-
#
|
275
|
+
# make sure we have the minimum needed params for a connection
|
274
276
|
verify_basic_params params
|
277
|
+
|
278
|
+
# turn the params into instance vars
|
275
279
|
parse_connect_params params
|
276
280
|
|
277
|
-
@token
|
281
|
+
# if no @token already, get one from from
|
282
|
+
# either a token string or a pw
|
283
|
+
@token ||=
|
284
|
+
if params[:token].is_a? String
|
285
|
+
tk = token_from :token_string, params[:token]
|
286
|
+
# get the user from the token
|
287
|
+
@user = tk.user
|
288
|
+
tk
|
289
|
+
else
|
290
|
+
token_from :pw, acquire_password(params[:pw])
|
291
|
+
end
|
292
|
+
|
293
|
+
# Now get some values from our token
|
294
|
+
@base_url = @token.base_url
|
278
295
|
@login_time = @token.login_time
|
279
|
-
@user ||= @token.user
|
280
296
|
|
281
|
-
#
|
297
|
+
# and make our actual connection
|
282
298
|
@rest_cnx = create_connection
|
283
299
|
|
300
|
+
# make sure versions are good
|
284
301
|
validate_api_version
|
285
302
|
|
286
303
|
@connected = true
|
287
304
|
|
305
|
+
# start keepalive if needed
|
288
306
|
@keep_alive = params[:keep_alive].nil? ? false : params[:keep_alive]
|
289
|
-
@keep_alive
|
307
|
+
start_keep_alive if @keep_alive
|
308
|
+
|
309
|
+
# return our string output
|
290
310
|
to_s
|
291
311
|
end # connect
|
292
312
|
|
@@ -300,7 +320,8 @@ module Jamf
|
|
300
320
|
@token = nil
|
301
321
|
@base_url = nil
|
302
322
|
@rest_cnx = nil
|
303
|
-
@
|
323
|
+
@ssl_options = {}
|
324
|
+
@keep_alive = nil
|
304
325
|
flushcache
|
305
326
|
end
|
306
327
|
|
@@ -432,25 +453,6 @@ module Jamf
|
|
432
453
|
####################################
|
433
454
|
private
|
434
455
|
|
435
|
-
# given a token string or a password, get a valid token
|
436
|
-
# Token.new will raise an exception if the token string or
|
437
|
-
# credentials are invalid
|
438
|
-
def token_from(type, data)
|
439
|
-
token_params = {
|
440
|
-
user: @user,
|
441
|
-
base_url: @base_url,
|
442
|
-
timeout: @timeout,
|
443
|
-
ssl_options: @ssl_options
|
444
|
-
}
|
445
|
-
|
446
|
-
case type
|
447
|
-
when :token_string
|
448
|
-
token_params[:token_string] = data
|
449
|
-
when :pw
|
450
|
-
token_params[:pw] = data
|
451
|
-
end
|
452
|
-
self.class::Token.new token_params
|
453
|
-
end
|
454
456
|
|
455
457
|
# raise exception if not connected
|
456
458
|
def validate_connected
|
@@ -465,14 +467,47 @@ module Jamf
|
|
465
467
|
raise Jamf::InvalidConnectionError, "API version '#{vers}' too low, must be >= '#{MIN_API_VERSION}'"
|
466
468
|
end
|
467
469
|
|
468
|
-
|
469
|
-
|
470
|
+
##### Parse Params
|
471
|
+
###################################
|
472
|
+
|
473
|
+
# Get host, port, & user from a Token object
|
474
|
+
# or just the user from a token string.
|
475
|
+
def parse_token(params)
|
476
|
+
return unless params[:token].is_a? self.class::Token
|
477
|
+
|
478
|
+
verify_token params[:token]
|
479
|
+
@token = params[:token]
|
480
|
+
params[:host] = @token.host
|
481
|
+
params[:port] = @token.port
|
482
|
+
params[:user] = @token.user
|
483
|
+
end
|
484
|
+
|
485
|
+
# Raise execeptions if we were given an unusable token object
|
486
|
+
#
|
487
|
+
# @param params[Hash] The params for #connect
|
488
|
+
#
|
489
|
+
# @return [void]
|
490
|
+
#
|
491
|
+
def verify_token(token)
|
492
|
+
raise 'Cannot use token: it has expired' if token.expired?
|
493
|
+
raise 'Cannot use token: it is invalid' unless token.valid?
|
494
|
+
raise "Cannot use token: it expires in less than #{TOKEN_REUSE_MIN_LIFE} seconds" if token.secs_remaining < TOKEN_REUSE_MIN_LIFE
|
495
|
+
end
|
496
|
+
|
497
|
+
# Get host, port, user and pw from a URL, unless they are already in the params
|
498
|
+
#
|
499
|
+
# @return [String, nil] the pw if present
|
500
|
+
#
|
501
|
+
def parse_url(url, params)
|
502
|
+
return unless url
|
503
|
+
|
504
|
+
url = URI.parse url.to_s
|
470
505
|
raise ArgumentError, 'Invalid url, scheme must be https' unless url.scheme == HTTPS_SCHEME
|
471
506
|
|
472
|
-
params[:
|
473
|
-
params[:
|
474
|
-
params[:
|
475
|
-
params[:
|
507
|
+
params[:host] ||= url.host
|
508
|
+
params[:port] ||= url.port
|
509
|
+
params[:user] ||= url.user if url.user
|
510
|
+
params[:pw] ||= url.password if url.password
|
476
511
|
end
|
477
512
|
|
478
513
|
# Apply defaults from the Jamf.config,
|
@@ -486,12 +521,11 @@ module Jamf
|
|
486
521
|
#
|
487
522
|
def apply_connection_defaults(params)
|
488
523
|
apply_defaults_from_config(params)
|
524
|
+
|
489
525
|
# TODO: when clients are moved over
|
490
526
|
# apply_defaults_from_client(params)
|
491
|
-
apply_module_defaults(params)
|
492
527
|
|
493
|
-
|
494
|
-
params[:pw] ||= :prompt if STDIN.tty?
|
528
|
+
apply_module_defaults(params)
|
495
529
|
end
|
496
530
|
|
497
531
|
# Apply defaults from the Jamf.config
|
@@ -542,44 +576,27 @@ module Jamf
|
|
542
576
|
params[:timeout] ||= DFT_TIMEOUT
|
543
577
|
params[:open_timeout] ||= DFT_OPEN_TIMEOUT
|
544
578
|
params[:ssl_version] ||= DFT_SSL_VERSION
|
545
|
-
|
546
|
-
|
547
|
-
# From whatever was given in params[:pw], figure out the real password
|
548
|
-
#
|
549
|
-
# @param params[Hash] The params for #connect
|
550
|
-
#
|
551
|
-
# @return [String] The password for the connection
|
552
|
-
#
|
553
|
-
def acquire_password(params)
|
554
|
-
if params[:pw] == :prompt
|
555
|
-
Jamf.prompt_for_password "Enter the password for Jamf user #{params[:user]}@#{params[:host]}:"
|
556
|
-
elsif params[:pw].is_a?(Symbol) && params[:pw].to_s.start_with?('stdin')
|
557
|
-
params[:pw].to_s =~ /^stdin(\d+)$/
|
558
|
-
line = Regexp.last_match(1)
|
559
|
-
line ||= 1
|
560
|
-
Jamf.stdin line
|
561
|
-
else
|
562
|
-
params[:pw]
|
563
|
-
end
|
579
|
+
# if we have a TTY, pw defaults to :prompt
|
580
|
+
params[:pw] ||= :prompt if STDIN.tty?
|
564
581
|
end
|
565
582
|
|
566
583
|
# Raise execeptions if we don't have essential data for a new connection
|
567
|
-
#
|
584
|
+
# namely a host, user, and pw
|
568
585
|
# @param params[Hash] The params for #connect
|
569
586
|
#
|
570
587
|
# @return [void]
|
571
588
|
#
|
572
589
|
def verify_basic_params(params)
|
573
590
|
# if given a Token object, it has host, port, user, and base_url
|
574
|
-
# and
|
575
|
-
return if
|
591
|
+
# and is already parsed
|
592
|
+
return if @token
|
576
593
|
|
577
|
-
# must have a host, accept :server as well as :host
|
594
|
+
# must have a host, but accept legacy :server as well as :host
|
578
595
|
params[:host] ||= params[:server]
|
579
596
|
raise Jamf::MissingDataError, 'No Jamf :host specified, or in configuration.' unless params[:host]
|
580
597
|
|
581
598
|
# no need for user or pass if using a token string
|
582
|
-
return if params[:token]
|
599
|
+
return if params[:token].is_a? String
|
583
600
|
|
584
601
|
raise Jamf::MissingDataError, 'No Jamf :user specified, or in configuration.' unless params[:user]
|
585
602
|
raise Jamf::MissingDataError, "No :pw specified for user '#{params[:user]}'" unless params[:pw]
|
@@ -603,39 +620,44 @@ module Jamf
|
|
603
620
|
@name = "#{@user}@#{@host}:#{@port}" if @name == NOT_CONNECTED
|
604
621
|
end
|
605
622
|
|
606
|
-
#
|
607
|
-
|
608
|
-
|
609
|
-
|
610
|
-
|
611
|
-
|
612
|
-
|
613
|
-
|
614
|
-
|
615
|
-
|
616
|
-
|
617
|
-
|
623
|
+
# given a token string or a password, get a valid token
|
624
|
+
# Token.new will raise an exception if the token string or
|
625
|
+
# credentials are invalid
|
626
|
+
def token_from(type, data)
|
627
|
+
token_params = {
|
628
|
+
user: @user,
|
629
|
+
base_url: @base_url,
|
630
|
+
timeout: @timeout,
|
631
|
+
ssl_options: @ssl_options
|
632
|
+
}
|
633
|
+
|
634
|
+
case type
|
635
|
+
when :token_string
|
636
|
+
token_params[:token_string] = data
|
637
|
+
when :pw
|
638
|
+
token_params[:pw] = data
|
618
639
|
end
|
640
|
+
self.class::Token.new token_params
|
619
641
|
end
|
620
642
|
|
621
|
-
#
|
643
|
+
# From whatever was given in params[:pw], figure out the password to use
|
622
644
|
#
|
623
645
|
# @param params[Hash] The params for #connect
|
624
646
|
#
|
625
|
-
# @return [
|
647
|
+
# @return [String] The password for the connection
|
626
648
|
#
|
627
|
-
def
|
628
|
-
|
629
|
-
|
630
|
-
|
631
|
-
|
632
|
-
|
633
|
-
|
634
|
-
|
635
|
-
|
636
|
-
|
637
|
-
|
638
|
-
end
|
649
|
+
def acquire_password(param_pw)
|
650
|
+
if param_pw == :prompt
|
651
|
+
Jamf.prompt_for_password "Enter the password for Jamf user #{@user}@#{@host}:"
|
652
|
+
elsif param_pw.is_a?(Symbol) && param_pw.to_s.start_with?('stdin')
|
653
|
+
param_pw.to_s =~ /^stdin(\d+)$/
|
654
|
+
line = Regexp.last_match(1)
|
655
|
+
line ||= 1
|
656
|
+
Jamf.stdin line
|
657
|
+
else
|
658
|
+
param_pw
|
659
|
+
end # if
|
660
|
+
end # acquire pw
|
639
661
|
|
640
662
|
# create the faraday connection object
|
641
663
|
def create_connection(parse_json = true)
|
@@ -73,7 +73,6 @@ module Jamf
|
|
73
73
|
else
|
74
74
|
raise ArgumentError, 'Must provide either pw: or token_string:'
|
75
75
|
end
|
76
|
-
|
77
76
|
end # init
|
78
77
|
|
79
78
|
# Initialize from password
|
@@ -103,8 +102,9 @@ module Jamf
|
|
103
102
|
|
104
103
|
@auth_token = str
|
105
104
|
@user = resp.body.dig :account, :username
|
105
|
+
|
106
106
|
# use this token to get a fresh one with a known expiration
|
107
|
-
|
107
|
+
refresh
|
108
108
|
end # init_from_token_string
|
109
109
|
|
110
110
|
# @return [String]
|
@@ -162,7 +162,7 @@ module Jamf
|
|
162
162
|
end
|
163
163
|
|
164
164
|
# Use this token to get a fresh one
|
165
|
-
def
|
165
|
+
def refresh
|
166
166
|
raise 'Token has expired' if expired?
|
167
167
|
|
168
168
|
keep_alive_token_resp = token_connection(KEEP_ALIVE_RSRC, token: @auth_token).post
|
@@ -173,7 +173,7 @@ module Jamf
|
|
173
173
|
# parse_token_from_response keep_alive_rsrc.post('')
|
174
174
|
expires
|
175
175
|
end
|
176
|
-
alias refresh
|
176
|
+
alias keep_alive refresh
|
177
177
|
|
178
178
|
# Make this token invalid
|
179
179
|
def invalidate
|
data/lib/jamf/validate.rb
CHANGED
@@ -106,12 +106,12 @@ module Jamf
|
|
106
106
|
#
|
107
107
|
# @return [Object] the validated unique value
|
108
108
|
#
|
109
|
-
def self.
|
109
|
+
def self.doesnt_exist(val, klass, identifier, msg = nil, cnx: Jamf.cnx)
|
110
110
|
msg ||= "A #{klass} already exists with #{identifier} '#{val}'"
|
111
111
|
|
112
|
-
raise Jamf::InvalidDataError, "No identifier '#{
|
112
|
+
raise Jamf::InvalidDataError, "No identifier '#{identifier}' for #{klass}" unless klass.identifiers.include? identifier
|
113
113
|
|
114
|
-
return val unless klass.send("all_#{
|
114
|
+
return val unless klass.send("all_#{identifier}s", :refresh, cnx: cnx).include? val
|
115
115
|
|
116
116
|
raise Jamf::AlreadyExistsError, msg
|
117
117
|
end
|
data/lib/jamf/version.rb
CHANGED
data/lib/jss/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ruby-jss
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.2.
|
4
|
+
version: 1.2.4a2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Chris Lasell
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2019-11-
|
12
|
+
date: 2019-11-20 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: plist
|