pymobiledevice3 5.0.1__py3-none-any.whl → 5.0.2__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of pymobiledevice3 might be problematic. Click here for more details.

Files changed (143) hide show
  1. misc/plist_sniffer.py +15 -15
  2. misc/remotexpc_sniffer.py +29 -28
  3. pymobiledevice3/__main__.py +128 -102
  4. pymobiledevice3/_version.py +2 -2
  5. pymobiledevice3/bonjour.py +26 -49
  6. pymobiledevice3/ca.py +32 -24
  7. pymobiledevice3/cli/activation.py +7 -7
  8. pymobiledevice3/cli/afc.py +19 -19
  9. pymobiledevice3/cli/amfi.py +4 -4
  10. pymobiledevice3/cli/apps.py +51 -39
  11. pymobiledevice3/cli/backup.py +58 -32
  12. pymobiledevice3/cli/bonjour.py +25 -18
  13. pymobiledevice3/cli/cli_common.py +112 -81
  14. pymobiledevice3/cli/companion_proxy.py +4 -4
  15. pymobiledevice3/cli/completions.py +10 -10
  16. pymobiledevice3/cli/crash.py +37 -31
  17. pymobiledevice3/cli/developer.py +602 -520
  18. pymobiledevice3/cli/diagnostics.py +38 -33
  19. pymobiledevice3/cli/lockdown.py +79 -74
  20. pymobiledevice3/cli/mounter.py +85 -68
  21. pymobiledevice3/cli/notification.py +10 -10
  22. pymobiledevice3/cli/pcap.py +19 -14
  23. pymobiledevice3/cli/power_assertion.py +12 -10
  24. pymobiledevice3/cli/processes.py +10 -10
  25. pymobiledevice3/cli/profile.py +88 -77
  26. pymobiledevice3/cli/provision.py +17 -17
  27. pymobiledevice3/cli/remote.py +186 -110
  28. pymobiledevice3/cli/restore.py +43 -40
  29. pymobiledevice3/cli/springboard.py +30 -28
  30. pymobiledevice3/cli/syslog.py +85 -58
  31. pymobiledevice3/cli/usbmux.py +21 -20
  32. pymobiledevice3/cli/version.py +3 -2
  33. pymobiledevice3/cli/webinspector.py +157 -79
  34. pymobiledevice3/common.py +1 -1
  35. pymobiledevice3/exceptions.py +154 -60
  36. pymobiledevice3/irecv.py +49 -53
  37. pymobiledevice3/irecv_devices.py +1489 -492
  38. pymobiledevice3/lockdown.py +394 -241
  39. pymobiledevice3/lockdown_service_provider.py +5 -7
  40. pymobiledevice3/osu/os_utils.py +18 -9
  41. pymobiledevice3/osu/posix_util.py +28 -15
  42. pymobiledevice3/osu/win_util.py +14 -8
  43. pymobiledevice3/pair_records.py +19 -19
  44. pymobiledevice3/remote/common.py +4 -4
  45. pymobiledevice3/remote/core_device/app_service.py +94 -67
  46. pymobiledevice3/remote/core_device/core_device_service.py +17 -14
  47. pymobiledevice3/remote/core_device/device_info.py +5 -5
  48. pymobiledevice3/remote/core_device/diagnostics_service.py +10 -8
  49. pymobiledevice3/remote/core_device/file_service.py +47 -33
  50. pymobiledevice3/remote/remote_service_discovery.py +53 -35
  51. pymobiledevice3/remote/remotexpc.py +62 -41
  52. pymobiledevice3/remote/tunnel_service.py +371 -293
  53. pymobiledevice3/remote/utils.py +12 -11
  54. pymobiledevice3/remote/xpc_message.py +145 -125
  55. pymobiledevice3/resources/dsc_uuid_map.py +19 -19
  56. pymobiledevice3/resources/firmware_notifications.py +16 -16
  57. pymobiledevice3/restore/asr.py +27 -27
  58. pymobiledevice3/restore/base_restore.py +90 -47
  59. pymobiledevice3/restore/consts.py +87 -66
  60. pymobiledevice3/restore/device.py +11 -11
  61. pymobiledevice3/restore/fdr.py +46 -46
  62. pymobiledevice3/restore/ftab.py +19 -19
  63. pymobiledevice3/restore/img4.py +130 -133
  64. pymobiledevice3/restore/mbn.py +35 -54
  65. pymobiledevice3/restore/recovery.py +125 -135
  66. pymobiledevice3/restore/restore.py +524 -523
  67. pymobiledevice3/restore/restore_options.py +122 -115
  68. pymobiledevice3/restore/restored_client.py +25 -22
  69. pymobiledevice3/restore/tss.py +378 -270
  70. pymobiledevice3/service_connection.py +50 -46
  71. pymobiledevice3/services/accessibilityaudit.py +136 -126
  72. pymobiledevice3/services/afc.py +350 -291
  73. pymobiledevice3/services/amfi.py +21 -18
  74. pymobiledevice3/services/companion.py +23 -19
  75. pymobiledevice3/services/crash_reports.py +60 -46
  76. pymobiledevice3/services/debugserver_applist.py +3 -3
  77. pymobiledevice3/services/device_arbitration.py +8 -8
  78. pymobiledevice3/services/device_link.py +55 -47
  79. pymobiledevice3/services/diagnostics.py +971 -968
  80. pymobiledevice3/services/dtfetchsymbols.py +8 -8
  81. pymobiledevice3/services/dvt/dvt_secure_socket_proxy.py +4 -4
  82. pymobiledevice3/services/dvt/dvt_testmanaged_proxy.py +4 -4
  83. pymobiledevice3/services/dvt/instruments/activity_trace_tap.py +85 -74
  84. pymobiledevice3/services/dvt/instruments/application_listing.py +2 -3
  85. pymobiledevice3/services/dvt/instruments/condition_inducer.py +7 -6
  86. pymobiledevice3/services/dvt/instruments/core_profile_session_tap.py +442 -421
  87. pymobiledevice3/services/dvt/instruments/device_info.py +11 -11
  88. pymobiledevice3/services/dvt/instruments/energy_monitor.py +1 -1
  89. pymobiledevice3/services/dvt/instruments/graphics.py +1 -1
  90. pymobiledevice3/services/dvt/instruments/location_simulation.py +1 -1
  91. pymobiledevice3/services/dvt/instruments/location_simulation_base.py +10 -10
  92. pymobiledevice3/services/dvt/instruments/network_monitor.py +17 -17
  93. pymobiledevice3/services/dvt/instruments/notifications.py +1 -1
  94. pymobiledevice3/services/dvt/instruments/process_control.py +25 -10
  95. pymobiledevice3/services/dvt/instruments/screenshot.py +2 -2
  96. pymobiledevice3/services/dvt/instruments/sysmontap.py +15 -15
  97. pymobiledevice3/services/dvt/testmanaged/xcuitest.py +40 -50
  98. pymobiledevice3/services/file_relay.py +10 -10
  99. pymobiledevice3/services/heartbeat.py +8 -7
  100. pymobiledevice3/services/house_arrest.py +12 -15
  101. pymobiledevice3/services/installation_proxy.py +119 -100
  102. pymobiledevice3/services/lockdown_service.py +12 -5
  103. pymobiledevice3/services/misagent.py +22 -19
  104. pymobiledevice3/services/mobile_activation.py +84 -72
  105. pymobiledevice3/services/mobile_config.py +330 -301
  106. pymobiledevice3/services/mobile_image_mounter.py +137 -116
  107. pymobiledevice3/services/mobilebackup2.py +188 -150
  108. pymobiledevice3/services/notification_proxy.py +11 -11
  109. pymobiledevice3/services/os_trace.py +69 -51
  110. pymobiledevice3/services/pcapd.py +306 -306
  111. pymobiledevice3/services/power_assertion.py +10 -9
  112. pymobiledevice3/services/preboard.py +4 -4
  113. pymobiledevice3/services/remote_fetch_symbols.py +16 -14
  114. pymobiledevice3/services/remote_server.py +176 -146
  115. pymobiledevice3/services/restore_service.py +16 -16
  116. pymobiledevice3/services/screenshot.py +13 -10
  117. pymobiledevice3/services/simulate_location.py +7 -7
  118. pymobiledevice3/services/springboard.py +15 -15
  119. pymobiledevice3/services/syslog.py +5 -5
  120. pymobiledevice3/services/web_protocol/alert.py +3 -3
  121. pymobiledevice3/services/web_protocol/automation_session.py +180 -176
  122. pymobiledevice3/services/web_protocol/cdp_screencast.py +44 -36
  123. pymobiledevice3/services/web_protocol/cdp_server.py +19 -19
  124. pymobiledevice3/services/web_protocol/cdp_target.py +411 -373
  125. pymobiledevice3/services/web_protocol/driver.py +47 -45
  126. pymobiledevice3/services/web_protocol/element.py +74 -63
  127. pymobiledevice3/services/web_protocol/inspector_session.py +106 -102
  128. pymobiledevice3/services/web_protocol/selenium_api.py +2 -2
  129. pymobiledevice3/services/web_protocol/session_protocol.py +15 -10
  130. pymobiledevice3/services/web_protocol/switch_to.py +11 -12
  131. pymobiledevice3/services/webinspector.py +127 -116
  132. pymobiledevice3/tcp_forwarder.py +35 -22
  133. pymobiledevice3/tunneld/api.py +20 -15
  134. pymobiledevice3/tunneld/server.py +212 -133
  135. pymobiledevice3/usbmux.py +183 -138
  136. pymobiledevice3/utils.py +14 -11
  137. {pymobiledevice3-5.0.1.dist-info → pymobiledevice3-5.0.2.dist-info}/METADATA +1 -1
  138. pymobiledevice3-5.0.2.dist-info/RECORD +173 -0
  139. pymobiledevice3-5.0.1.dist-info/RECORD +0 -173
  140. {pymobiledevice3-5.0.1.dist-info → pymobiledevice3-5.0.2.dist-info}/WHEEL +0 -0
  141. {pymobiledevice3-5.0.1.dist-info → pymobiledevice3-5.0.2.dist-info}/entry_points.txt +0 -0
  142. {pymobiledevice3-5.0.1.dist-info → pymobiledevice3-5.0.2.dist-info}/licenses/LICENSE +0 -0
  143. {pymobiledevice3-5.0.1.dist-info → pymobiledevice3-5.0.2.dist-info}/top_level.txt +0 -0
@@ -17,25 +17,25 @@ def cli() -> None:
17
17
 
18
18
  @cli.group()
19
19
  def notification() -> None:
20
- """ Post/Observe notifications """
20
+ """Post/Observe notifications"""
21
21
  pass
22
22
 
23
23
 
24
24
  @notification.command(cls=Command)
25
- @click.argument('names', nargs=-1)
26
- @click.option('--insecure', is_flag=True, help='use the insecure relay meant for untrusted clients instead')
25
+ @click.argument("names", nargs=-1)
26
+ @click.option("--insecure", is_flag=True, help="use the insecure relay meant for untrusted clients instead")
27
27
  def post(service_provider: LockdownClient, names, insecure):
28
- """ API for notify_post(). """
28
+ """API for notify_post()."""
29
29
  service = NotificationProxyService(lockdown=service_provider, insecure=insecure)
30
30
  for name in names:
31
31
  service.notify_post(name)
32
32
 
33
33
 
34
34
  @notification.command(cls=Command)
35
- @click.argument('names', nargs=-1)
36
- @click.option('--insecure', is_flag=True, help='use the insecure relay meant for untrusted clients instead')
35
+ @click.argument("names", nargs=-1)
36
+ @click.option("--insecure", is_flag=True, help="use the insecure relay meant for untrusted clients instead")
37
37
  def observe(service_provider: LockdownClient, names, insecure):
38
- """ API for notify_register_dispatch(). """
38
+ """API for notify_register_dispatch()."""
39
39
  service = NotificationProxyService(lockdown=service_provider, insecure=insecure)
40
40
  for name in names:
41
41
  service.notify_register_dispatch(name)
@@ -44,10 +44,10 @@ def observe(service_provider: LockdownClient, names, insecure):
44
44
  logger.info(event)
45
45
 
46
46
 
47
- @notification.command('observe-all', cls=Command)
48
- @click.option('--insecure', is_flag=True, help='use the insecure relay meant for untrusted clients instead')
47
+ @notification.command("observe-all", cls=Command)
48
+ @click.option("--insecure", is_flag=True, help="use the insecure relay meant for untrusted clients instead")
49
49
  def observe_all(service_provider: LockdownClient, insecure):
50
- """ attempt to observe all builtin firmware notifications. """
50
+ """attempt to observe all builtin firmware notifications."""
51
51
  service = NotificationProxyService(lockdown=service_provider, insecure=insecure)
52
52
  for notification in get_notifications():
53
53
  service.notify_register_dispatch(notification)
@@ -17,19 +17,19 @@ def cli() -> None:
17
17
  def print_packet_header(packet, color: bool) -> None:
18
18
  date = datetime.fromtimestamp(packet.seconds + (packet.microseconds / 1000000))
19
19
  data = (
20
- f'{date}: '
21
- f'Process {packet.comm} ({packet.pid}), '
22
- f'Interface: {packet.interface_name} ({packet.interface_type.name}), '
23
- f'Family: {packet.protocol_family.name}'
20
+ f"{date}: "
21
+ f"Process {packet.comm} ({packet.pid}), "
22
+ f"Interface: {packet.interface_name} ({packet.interface_type.name}), "
23
+ f"Family: {packet.protocol_family.name}"
24
24
  )
25
25
  if not color:
26
26
  print(data)
27
27
  else:
28
- print(highlight(data, lexers.HspecLexer(), formatters.Terminal256Formatter(style='native')), end='')
28
+ print(highlight(data, lexers.HspecLexer(), formatters.Terminal256Formatter(style="native")), end="")
29
29
 
30
30
 
31
31
  def print_packet(packet, color: Optional[bool] = None):
32
- """ Return the packet, so it can be chained in a generator """
32
+ """Return the packet, so it can be chained in a generator"""
33
33
  if color is None:
34
34
  color = user_requested_colored_output()
35
35
  print_packet_header(packet, color)
@@ -38,18 +38,23 @@ def print_packet(packet, color: Optional[bool] = None):
38
38
 
39
39
 
40
40
  @cli.command(cls=Command)
41
- @click.argument('out', type=click.File('wb'), required=False)
42
- @click.option('-c', '--count', type=click.INT, default=-1, help='Number of packets to sniff. Omit to endless sniff.')
43
- @click.option('--process', default=None, help='Process to filter. Omit for all.')
44
- @click.option('-i', '--interface', default=None, help='Interface name to filter. Omit for all.')
45
- def pcap(service_provider: LockdownServiceProvider, out: Optional[IO], count: int, process: Optional[str],
46
- interface: Optional[str]) -> None:
47
- """ Sniff device traffic """
41
+ @click.argument("out", type=click.File("wb"), required=False)
42
+ @click.option("-c", "--count", type=click.INT, default=-1, help="Number of packets to sniff. Omit to endless sniff.")
43
+ @click.option("--process", default=None, help="Process to filter. Omit for all.")
44
+ @click.option("-i", "--interface", default=None, help="Interface name to filter. Omit for all.")
45
+ def pcap(
46
+ service_provider: LockdownServiceProvider,
47
+ out: Optional[IO],
48
+ count: int,
49
+ process: Optional[str],
50
+ interface: Optional[str],
51
+ ) -> None:
52
+ """Sniff device traffic"""
48
53
  service = PcapdService(lockdown=service_provider)
49
54
  packets_generator = service.watch(packets_count=count, process=process, interface_name=interface)
50
55
 
51
56
  if out is not None:
52
- packets_generator_with_print = map(lambda p: print_packet(p), packets_generator)
57
+ packets_generator_with_print = (print_packet(p) for p in packets_generator)
53
58
  service.write_to_pcap(out, packets_generator_with_print)
54
59
  return
55
60
 
@@ -12,14 +12,16 @@ def cli() -> None:
12
12
  pass
13
13
 
14
14
 
15
- @cli.command('power-assertion', cls=Command)
16
- @click.argument('type', type=click.Choice(
17
- ['AMDPowerAssertionTypeWirelessSync', 'PreventUserIdleSystemSleep', 'PreventSystemSleep']))
18
- @click.argument('name')
19
- @click.argument('timeout', type=click.INT)
20
- @click.argument('details', required=False)
21
- def power_assertion(service_provider: LockdownServiceProvider, type, name, timeout, details) -> None:
22
- """ Create a power assertion """
23
- with PowerAssertionService(service_provider).create_power_assertion(type, name, timeout, details):
24
- print('> Hit Ctrl+C to exit')
15
+ @cli.command("power-assertion", cls=Command)
16
+ @click.argument(
17
+ "assertion_type",
18
+ type=click.Choice(["AMDPowerAssertionTypeWirelessSync", "PreventUserIdleSystemSleep", "PreventSystemSleep"]),
19
+ )
20
+ @click.argument("name")
21
+ @click.argument("timeout", type=click.INT)
22
+ @click.argument("details", required=False)
23
+ def power_assertion(service_provider: LockdownServiceProvider, assertion_type, name, timeout, details) -> None:
24
+ """Create a power assertion"""
25
+ with PowerAssertionService(service_provider).create_power_assertion(assertion_type, name, timeout, details):
26
+ print("> Hit Ctrl+C to exit")
25
27
  time.sleep(timeout)
@@ -16,22 +16,22 @@ def cli() -> None:
16
16
 
17
17
  @cli.group()
18
18
  def processes() -> None:
19
- """ View process list using diagnosticsd API """
19
+ """View process list using diagnosticsd API"""
20
20
  pass
21
21
 
22
22
 
23
- @processes.command('ps', cls=Command)
23
+ @processes.command("ps", cls=Command)
24
24
  def processes_ps(service_provider: LockdownClient):
25
- """ show process list """
26
- print_json(OsTraceService(lockdown=service_provider).get_pid_list().get('Payload'))
25
+ """show process list"""
26
+ print_json(OsTraceService(lockdown=service_provider).get_pid_list().get("Payload"))
27
27
 
28
28
 
29
- @processes.command('pgrep', cls=Command)
30
- @click.argument('expression')
29
+ @processes.command("pgrep", cls=Command)
30
+ @click.argument("expression")
31
31
  def processes_pgrep(service_provider: LockdownClient, expression):
32
- """ try to match processes pid by given expression (like pgrep) """
33
- processes_list = OsTraceService(lockdown=service_provider).get_pid_list().get('Payload')
32
+ """try to match processes pid by given expression (like pgrep)"""
33
+ processes_list = OsTraceService(lockdown=service_provider).get_pid_list().get("Payload")
34
34
  for pid, process_info in processes_list.items():
35
- process_name = process_info.get('ProcessName')
35
+ process_name = process_info.get("ProcessName")
36
36
  if expression in process_name:
37
- logger.info(f'{pid} {process_name}')
37
+ logger.info(f"{pid} {process_name}")
@@ -21,21 +21,21 @@ def cli() -> None:
21
21
  pass
22
22
 
23
23
 
24
- @cli.group('profile')
24
+ @cli.group("profile")
25
25
  def profile_group() -> None:
26
- """ Managed installed profiles or install SSL certificates """
26
+ """Managed installed profiles or install SSL certificates"""
27
27
  pass
28
28
 
29
29
 
30
- @profile_group.command('list', cls=Command)
30
+ @profile_group.command("list", cls=Command)
31
31
  def profile_list(service_provider: LockdownClient):
32
- """ List installed profiles """
32
+ """List installed profiles"""
33
33
  print_json(MobileConfigService(lockdown=service_provider).get_profile_list())
34
34
 
35
35
 
36
- @profile_group.command('install', cls=Command)
37
- @click.option('--keybag', type=click.Path(file_okay=True, dir_okay=False, exists=True))
38
- @click.argument('profiles', nargs=-1, type=click.File('rb'))
36
+ @profile_group.command("install", cls=Command)
37
+ @click.option("--keybag", type=click.Path(file_okay=True, dir_okay=False, exists=True))
38
+ @click.argument("profiles", nargs=-1, type=click.File("rb"))
39
39
  def profile_install(service_provider: LockdownServiceProvider, keybag: Optional[str], profiles: list[IO]) -> None:
40
40
  """
41
41
  Install given profiles
@@ -44,101 +44,108 @@ def profile_install(service_provider: LockdownServiceProvider, keybag: Optional[
44
44
  """
45
45
  service = MobileConfigService(lockdown=service_provider)
46
46
  for profile in profiles:
47
- logger.info(f'installing {profile.name}')
47
+ logger.info(f"installing {profile.name}")
48
48
  if keybag is not None:
49
49
  service.install_profile_silent(Path(keybag), profile.read())
50
50
  else:
51
51
  service.install_profile(profile.read())
52
52
 
53
53
 
54
- @profile_group.command('cloud-configuration', cls=Command)
55
- @click.argument('config', type=click.File('rb'), required=False)
54
+ @profile_group.command("cloud-configuration", cls=Command)
55
+ @click.argument("config", type=click.File("rb"), required=False)
56
56
  def profile_cloud_configuration(service_provider: LockdownServiceProvider, config: Optional[IO]) -> None:
57
- """ Get/Set cloud configuration """
57
+ """Get/Set cloud configuration"""
58
58
  if not config:
59
59
  print_json(MobileConfigService(lockdown=service_provider).get_cloud_configuration())
60
60
  else:
61
61
  config_json = plistlib.load(config)
62
- logger.info(f'applying cloud configuration {config_json}')
62
+ logger.info(f"applying cloud configuration {config_json}")
63
63
  MobileConfigService(lockdown=service_provider).set_cloud_configuration(config_json)
64
- logger.info('applied cloud configuration')
64
+ logger.info("applied cloud configuration")
65
65
 
66
66
 
67
- @profile_group.command('store', cls=Command)
68
- @click.argument('profiles', nargs=-1, type=click.File('rb'))
67
+ @profile_group.command("store", cls=Command)
68
+ @click.argument("profiles", nargs=-1, type=click.File("rb"))
69
69
  def profile_store(service_provider: LockdownServiceProvider, profiles: list[IO]) -> None:
70
- """ Store a profile """
70
+ """Store a profile"""
71
71
  service = MobileConfigService(lockdown=service_provider)
72
72
  for profile in profiles:
73
- logger.info(f'storing {profile.name}')
73
+ logger.info(f"storing {profile.name}")
74
74
  service.store_profile(profile.read())
75
75
 
76
76
 
77
- @profile_group.command('remove', cls=Command)
78
- @click.argument('name')
77
+ @profile_group.command("remove", cls=Command)
78
+ @click.argument("name")
79
79
  def profile_remove(service_provider: LockdownServiceProvider, name: str) -> None:
80
- """ Remove a profile by its name """
80
+ """Remove a profile by its name"""
81
81
  MobileConfigService(lockdown=service_provider).remove_profile(name)
82
82
 
83
83
 
84
- @profile_group.command('set-wifi-power', cls=Command)
85
- @click.argument('state', type=click.Choice(['on', 'off']), required=False)
84
+ @profile_group.command("set-wifi-power", cls=Command)
85
+ @click.argument("state", type=click.Choice(["on", "off"]), required=False)
86
86
  def profile_set_wifi_power(service_provider: LockdownServiceProvider, state: str) -> None:
87
- """ change Wi-Fi power state """
88
- MobileConfigService(lockdown=service_provider).set_wifi_power_state(state == 'on')
89
-
90
-
91
- @profile_group.command('erase-device', cls=Command)
92
- @click.option('--preserve-data-plan/--no-preserve-data-plan', default=True,
93
- help='Preserves eSIM / data plan after erase')
94
- @click.option('--disallow-proximity-setup/--no-disallow-proximity-setup', default=False,
95
- help='Disallows to setup the erased device from nearby devices')
96
- def profile_erase_device(service_provider: LockdownServiceProvider, preserve_data_plan: bool,
97
- disallow_proximity_setup: bool) -> None:
98
- """ Erase device """
99
- logger.info(f'Erasing device with preserve_data_plan: {preserve_data_plan}, '
100
- f'disallow_proximity_setup: {disallow_proximity_setup}')
87
+ """change Wi-Fi power state"""
88
+ MobileConfigService(lockdown=service_provider).set_wifi_power_state(state == "on")
89
+
90
+
91
+ @profile_group.command("erase-device", cls=Command)
92
+ @click.option(
93
+ "--preserve-data-plan/--no-preserve-data-plan", default=True, help="Preserves eSIM / data plan after erase"
94
+ )
95
+ @click.option(
96
+ "--disallow-proximity-setup/--no-disallow-proximity-setup",
97
+ default=False,
98
+ help="Disallows to setup the erased device from nearby devices",
99
+ )
100
+ def profile_erase_device(
101
+ service_provider: LockdownServiceProvider, preserve_data_plan: bool, disallow_proximity_setup: bool
102
+ ) -> None:
103
+ """Erase device"""
104
+ logger.info(
105
+ f"Erasing device with preserve_data_plan: {preserve_data_plan}, "
106
+ f"disallow_proximity_setup: {disallow_proximity_setup}"
107
+ )
101
108
  MobileConfigService(lockdown=service_provider).erase_device(preserve_data_plan, disallow_proximity_setup)
102
- logger.info('Erased device')
109
+ logger.info("Erased device")
103
110
 
104
111
 
105
- @profile_group.command('create-keybag')
106
- @click.argument('keybag', type=click.Path(file_okay=True, dir_okay=False, exists=False))
107
- @click.argument('organization')
112
+ @profile_group.command("create-keybag")
113
+ @click.argument("keybag", type=click.Path(file_okay=True, dir_okay=False, exists=False))
114
+ @click.argument("organization")
108
115
  def profile_create_keybag(keybag: str, organization: str) -> None:
109
- """ Create keybag storing certificate and private key """
116
+ """Create keybag storing certificate and private key"""
110
117
  create_keybag_file(Path(keybag), organization)
111
118
 
112
119
 
113
- @profile_group.command('supervise', cls=Command)
114
- @click.argument('organization')
115
- @click.option('--keybag', type=click.Path(file_okay=True, dir_okay=False, exists=True))
120
+ @profile_group.command("supervise", cls=Command)
121
+ @click.argument("organization")
122
+ @click.option("--keybag", type=click.Path(file_okay=True, dir_okay=False, exists=True))
116
123
  def profile_supervise(service_provider: LockdownServiceProvider, organization: str, keybag: Optional[str]) -> None:
117
- """ Supervise device """
118
- if MobileActivationService(service_provider).state == 'Unactivated':
119
- logger.info('Activating device')
124
+ """Supervise device"""
125
+ if MobileActivationService(service_provider).state == "Unactivated":
126
+ logger.info("Activating device")
120
127
  MobileActivationService(service_provider).activate()
121
- logger.info('Device has been successfully activated')
122
- logger.info('Supervising device')
128
+ logger.info("Device has been successfully activated")
129
+ logger.info("Supervising device")
123
130
  if keybag is None:
124
131
  with tempfile.TemporaryDirectory() as temp_dir:
125
- keybag = Path(temp_dir) / 'keybag'
132
+ keybag = Path(temp_dir) / "keybag"
126
133
  create_keybag_file(keybag, organization)
127
134
  MobileConfigService(lockdown=service_provider).supervise(organization, keybag)
128
135
  else:
129
136
  MobileConfigService(lockdown=service_provider).supervise(organization, Path(keybag))
130
137
 
131
- logger.info('Device has been successfully supervised')
138
+ logger.info("Device has been successfully supervised")
132
139
 
133
140
 
134
- @profile_group.command('install-wifi-profile', cls=Command)
135
- @click.argument('encryption_type')
136
- @click.argument('ssid')
137
- @click.argument('password')
138
- @click.option('--keybag', type=click.Path(file_okay=True, dir_okay=False, exists=True))
139
- def profile_install_wifi_profile(service_provider: LockdownServiceProvider, encryption_type: str, ssid: str,
140
- password: str,
141
- keybag: Optional[str]) -> None:
141
+ @profile_group.command("install-wifi-profile", cls=Command)
142
+ @click.argument("encryption_type")
143
+ @click.argument("ssid")
144
+ @click.argument("password")
145
+ @click.option("--keybag", type=click.Path(file_okay=True, dir_okay=False, exists=True))
146
+ def profile_install_wifi_profile(
147
+ service_provider: LockdownServiceProvider, encryption_type: str, ssid: str, password: str, keybag: Optional[str]
148
+ ) -> None:
142
149
  """
143
150
  Install Wi-Fi profile
144
151
 
@@ -147,34 +154,38 @@ def profile_install_wifi_profile(service_provider: LockdownServiceProvider, encr
147
154
  if keybag is not None:
148
155
  keybag = Path(keybag)
149
156
  MobileConfigService(lockdown=service_provider).install_wifi_profile(
150
- encryption_type=encryption_type, ssid=ssid, password=password, keybag_file=keybag)
151
-
152
-
153
- @profile_group.command('install-http-proxy', cls=Command)
154
- @click.argument('server')
155
- @click.argument('port', type=click.IntRange(1, 65535))
156
- @click.option('--keybag', type=click.Path(file_okay=True, dir_okay=False, exists=True))
157
- def profile_install_http_proxy(service_provider: LockdownServiceProvider, server: str, port: int,
158
- keybag: Optional[str]) -> None:
159
- """ Install HTTP Proxy profile """
157
+ encryption_type=encryption_type, ssid=ssid, password=password, keybag_file=keybag
158
+ )
159
+
160
+
161
+ @profile_group.command("install-http-proxy", cls=Command)
162
+ @click.argument("server")
163
+ @click.argument("port", type=click.IntRange(1, 65535))
164
+ @click.option("--keybag", type=click.Path(file_okay=True, dir_okay=False, exists=True))
165
+ def profile_install_http_proxy(
166
+ service_provider: LockdownServiceProvider, server: str, port: int, keybag: Optional[str]
167
+ ) -> None:
168
+ """Install HTTP Proxy profile"""
160
169
  if keybag is not None:
161
170
  keybag = Path(keybag)
162
171
  MobileConfigService(lockdown=service_provider).install_http_proxy(server, port, keybag_file=keybag)
163
172
 
164
173
 
165
- @profile_group.command('remove-http-proxy', cls=Command)
174
+ @profile_group.command("remove-http-proxy", cls=Command)
166
175
  def profile_remove_http_proxy(service_provider: LockdownServiceProvider) -> None:
167
- """ Remove HTTP Proxy profile that was previously installed using pymobiledevice3 """
176
+ """Remove HTTP Proxy profile that was previously installed using pymobiledevice3"""
168
177
  MobileConfigService(lockdown=service_provider).remove_http_proxy()
169
178
 
170
179
 
171
- @profile_group.command('install-restrictions-profile', cls=Command)
172
- @click.option('--keybag', type=click.Path(file_okay=True, dir_okay=False, exists=True))
173
- @click.option('--enforced-software-update-delay', type=click.IntRange(0, 90), default=0)
180
+ @profile_group.command("install-restrictions-profile", cls=Command)
181
+ @click.option("--keybag", type=click.Path(file_okay=True, dir_okay=False, exists=True))
182
+ @click.option("--enforced-software-update-delay", type=click.IntRange(0, 90), default=0)
174
183
  def profile_install_restrictions_profile(
175
- service_provider: LockdownServiceProvider, keybag: Optional[str], enforced_software_update_delay: int) -> None:
176
- """ Install restrictions profile (can be used for delayed OTA) """
184
+ service_provider: LockdownServiceProvider, keybag: Optional[str], enforced_software_update_delay: int
185
+ ) -> None:
186
+ """Install restrictions profile (can be used for delayed OTA)"""
177
187
  if keybag is not None:
178
188
  keybag = Path(keybag)
179
189
  MobileConfigService(lockdown=service_provider).install_restrictions_profile(
180
- enforced_software_update_delay=enforced_software_update_delay, keybag_file=keybag)
190
+ enforced_software_update_delay=enforced_software_update_delay, keybag_file=keybag
191
+ )
@@ -17,42 +17,42 @@ def cli() -> None:
17
17
 
18
18
  @cli.group()
19
19
  def provision() -> None:
20
- """ Manage installed provision profiles """
20
+ """Manage installed provision profiles"""
21
21
  pass
22
22
 
23
23
 
24
- @provision.command('install', cls=Command)
25
- @click.argument('profile', type=click.File('rb'))
24
+ @provision.command("install", cls=Command)
25
+ @click.argument("profile", type=click.File("rb"))
26
26
  def provision_install(service_provider: LockdownClient, profile):
27
- """ install a provision profile (.mobileprovision file) """
27
+ """install a provision profile (.mobileprovision file)"""
28
28
  MisagentService(lockdown=service_provider).install(profile)
29
29
 
30
30
 
31
- @provision.command('remove', cls=Command)
32
- @click.argument('profile_id')
31
+ @provision.command("remove", cls=Command)
32
+ @click.argument("profile_id")
33
33
  def provision_remove(service_provider: LockdownClient, profile_id):
34
- """ remove a provision profile """
34
+ """remove a provision profile"""
35
35
  MisagentService(lockdown=service_provider).remove(profile_id)
36
36
 
37
37
 
38
- @provision.command('clear', cls=Command)
38
+ @provision.command("clear", cls=Command)
39
39
  def provision_clear(service_provider: LockdownClient):
40
- """ remove all provision profiles """
40
+ """remove all provision profiles"""
41
41
  for profile in MisagentService(lockdown=service_provider).copy_all():
42
- MisagentService(lockdown=service_provider).remove(profile.plist['UUID'])
42
+ MisagentService(lockdown=service_provider).remove(profile.plist["UUID"])
43
43
 
44
44
 
45
- @provision.command('list', cls=Command)
45
+ @provision.command("list", cls=Command)
46
46
  def provision_list(service_provider: LockdownClient):
47
- """ list installed provision profiles """
47
+ """list installed provision profiles"""
48
48
  print_json([p.plist for p in MisagentService(lockdown=service_provider).copy_all()])
49
49
 
50
50
 
51
- @provision.command('dump', cls=Command)
52
- @click.argument('out', type=click.Path(file_okay=False, dir_okay=True, exists=True))
51
+ @provision.command("dump", cls=Command)
52
+ @click.argument("out", type=click.Path(file_okay=False, dir_okay=True, exists=True))
53
53
  def provision_dump(service_provider: LockdownClient, out):
54
- """ dump installed provision profiles to specified location """
54
+ """dump installed provision profiles to specified location"""
55
55
  for profile in MisagentService(lockdown=service_provider).copy_all():
56
- filename = f'{profile.plist["UUID"]}.mobileprovision'
57
- logger.info(f'downloading {filename}')
56
+ filename = f"{profile.plist['UUID']}.mobileprovision"
57
+ logger.info(f"downloading {filename}")
58
58
  (Path(out) / filename).write_bytes(profile.buf)