PixarAnimationStudios / ruby-jss

ruby-jss provides native ruby access to the REST APIs of Jamf Pro, an enterprise/education tool for managing Apple devices, from jamf.com. The Jamf module provides access to both APIs. Jamf Pro objects are implemented as classes and interact with each other. Authentication tokens, data format and other details are handled under the hood to allow simpler, intuitive automation of Jamf-related tasks.
http://pixaranimationstudios.github.io/jss-api-gem/index.html
Other
99 stars 30 forks source link

No Pagination available to get the list of mobile devices. #89

Open sonaligvc opened 2 years ago

sonaligvc commented 2 years ago

There is "all" method present to get all the device objects but there are no pagination available.

My one of client have 60K mobile devices and "all" method is getting stuck and not working due to heavy records. I am looking forward to have pagination in "all" to get list of mobile devices.

Please reply soon.

glenfarclas17 commented 2 years ago

Hi Sonali,

The Classic API, used via the 'JSS' module, does not support paging of any kind.

The Jamf Pro API, used via the 'Jamf' module does support paging for Mobile Devices, however I haven't had time to do any real work on ruby-jss's Jamf module since the pandemic started, and Mobile Devices via the Jamf Pro API are not yet implemented.

BUT - you can still use both APIs together to work with all mobile devices in a paginated way!

You can use the lower-level methods of the Jamf::Connection object (Jamf Pro API), to GET paginated data directly from the 'v2/mobile-devices' resource endpoint, specifying the paging.

It will return JSON data that will be converted to a Ruby Hash. The hash has a :results key, which contains an Array of Hashes, each with summary data about a device, including its Jamf Pro id.

You can then use that to fetch the full JSS::MobileDevice object from the Classic API, and process it as needed.

Here is an example of how to do this with ruby-jss:

require 'jss'
require  'jamf'

# Classic API Connection:
JSS.api.connect server: 'my.server.host', port: 443, user: 'apiuser' pw: :prompt

# Jamf Pro API Connection:
Jamf.cnx.connect  server: 'my.server.host', port: 443, user: 'apiuser' pw: :prompt

# set up the pagination
page_size = 200
page_num = 0

#  Fetch the first page of device summariess
paginated_rsrc_path = "v2/mobile-devices?page=#{page_num}&page-size=#{page_size}"
devices = Jamf.cnx.get(paginated_rsrc_path)[:results]

# process the first page and fetch the next page, until there are no more pages
until devices.empty?

  puts
  puts "##   Processing page #{page_num} of #{devices.size} devices"

  # process the fetched device summaries
  devices.each do |dev_summary|

    # if needed, fetch the device object from the Classic API
    dev_object = JSS::MobileDevice.fetch id: dev_summary[:id]
    puts "Device '#{dev_object.name}' (#{dev_object.id}) running #{dev_object.os_type} #{dev_object.os_version}"

  end # devices each

  # increment the page number
  page_num += 1

  # fetch the next page
  paginated_rsrc_path = "v2/mobile-devices?page=#{page_num}&page-size=#{page_size}"
  devices = Jamf.cnx.get(paginated_rsrc_path)[:results]

end  # until devices empty?

I hope this helps!

I'll try to make some time to get the Jamf module updated soon.

Cheers, -Chris

marekluban commented 2 years ago

👋 Just sharing how we query mobile devices. This approach won't work if you're looking to get full device objects, but we use this to parse through important data points for reporting purposes...

We created an AdvancedMobileDeviceSearch with blank criteria to pull in all mobile devices. We chose this approach because of the ability to include/exclude attributes that you want in the response (through "display" in the Jamf GUI).

Then you can just simply call the AdvancedMobileDeviceSearch endpoint and subsequently parse the data however you want:

jamf_group_id_for_device_reporting = '93'
JSS::AdvancedMobileDeviceSearch.fetch(id: jamf_group_id_for_device_reporting)