simctl 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +2 -0
- data/.travis.yml +8 -0
- data/Gemfile +3 -0
- data/Gemfile.lock +22 -0
- data/LICENSE +20 -0
- data/README.md +144 -0
- data/Rakefile +13 -0
- data/lib/simctl.rb +27 -0
- data/lib/simctl/command.rb +18 -0
- data/lib/simctl/command/boot.rb +14 -0
- data/lib/simctl/command/create.rb +18 -0
- data/lib/simctl/command/delete.rb +14 -0
- data/lib/simctl/command/erase.rb +16 -0
- data/lib/simctl/command/list.rb +59 -0
- data/lib/simctl/command/shutdown.rb +14 -0
- data/lib/simctl/device.rb +27 -0
- data/lib/simctl/device_type.rb +7 -0
- data/lib/simctl/executor.rb +28 -0
- data/lib/simctl/list.rb +20 -0
- data/lib/simctl/object.rb +9 -0
- data/lib/simctl/runtime.rb +7 -0
- data/lib/simctl/version.rb +3 -0
- data/simctl.gemspec +24 -0
- data/test/simctl/command/crud_test.rb +55 -0
- data/test/simctl/command/list_test.rb +47 -0
- data/test/test_helper.rb +5 -0
- metadata +116 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 0bb277e12e4ce8fc175ae3aa9e2f6409df2f9452
|
4
|
+
data.tar.gz: 21f532425ac401ea95dde484af341f2f4d8231db
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 8d0400e3c768b6f7dac83a7c4cc7195daa71eca447630410c753c4e19016f29878ef1e59de51dda28eb2e7e89ffa01bf4602167cbbd1ff2352326656e736b766
|
7
|
+
data.tar.gz: ac9fd2b3fed5f8652dc3fbf2d1cde044fb98f0e6cebe36a83e8f91847c1f8e17f5a6c98e9e04234243ffb1db158f9957831df4b57aaf5fb2efc64593e6ef041c
|
data/.gitignore
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/Gemfile.lock
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
PATH
|
2
|
+
remote: .
|
3
|
+
specs:
|
4
|
+
simctl (0.1.0)
|
5
|
+
|
6
|
+
GEM
|
7
|
+
remote: https://rubygems.org/
|
8
|
+
specs:
|
9
|
+
maxitest (1.5.4)
|
10
|
+
minitest (>= 5.0.0, < 5.9.0)
|
11
|
+
minitest (5.8.3)
|
12
|
+
rake (10.4.2)
|
13
|
+
shoulda-context (1.2.1)
|
14
|
+
|
15
|
+
PLATFORMS
|
16
|
+
ruby
|
17
|
+
|
18
|
+
DEPENDENCIES
|
19
|
+
maxitest
|
20
|
+
rake
|
21
|
+
shoulda-context
|
22
|
+
simctl!
|
data/LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2015 Johannes Plunien
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy of
|
6
|
+
this software and associated documentation files (the "Software"), to deal in
|
7
|
+
the Software without restriction, including without limitation the rights to
|
8
|
+
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
|
9
|
+
the Software, and to permit persons to whom the Software is furnished to do so,
|
10
|
+
subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
13
|
+
copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
|
17
|
+
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
|
18
|
+
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
|
19
|
+
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
20
|
+
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,144 @@
|
|
1
|
+
# simctl
|
2
|
+
|
3
|
+
[![Build Status](https://travis-ci.org/plu/simctl.svg?branch=master)](https://travis-ci.org/plu/simctl)
|
4
|
+
|
5
|
+
Ruby interface to xcrun simctl.
|
6
|
+
|
7
|
+
## Installation
|
8
|
+
|
9
|
+
Via [bundler](http://getbundler.com)
|
10
|
+
|
11
|
+
```sh
|
12
|
+
# in your Gemfile
|
13
|
+
gem 'simctl'
|
14
|
+
```
|
15
|
+
|
16
|
+
## Usage
|
17
|
+
|
18
|
+
### boot_device
|
19
|
+
|
20
|
+
```ruby
|
21
|
+
device = SimCtl.device(name: 'my iphone 5', state: 'Shutdown')
|
22
|
+
SimCtl.boot_device(device)
|
23
|
+
|
24
|
+
# or:
|
25
|
+
|
26
|
+
SimCtl.device(name: 'my iphone 5', state: 'Shutdown').boot!
|
27
|
+
```
|
28
|
+
|
29
|
+
### create_device
|
30
|
+
|
31
|
+
```ruby
|
32
|
+
SimCtl.create_device 'my iphone 5', SimCtl.devicetype(name: 'iPhone 5'), SimCtl.runtime(name: 'iOS 9.2')
|
33
|
+
|
34
|
+
#<SimCtl::Device:0x007fbce48afd88 @state="Creating", @availability="(available)", @name="my iphone 5", @udid="6F7269E0-6375-4B72-8451-F2728BF6DA82", @os="iOS 9.2">
|
35
|
+
```
|
36
|
+
|
37
|
+
### delete_device
|
38
|
+
|
39
|
+
```ruby
|
40
|
+
device = SimCtl.device(name: 'my iphone 5', state: 'Booted')
|
41
|
+
SimCtl.delete_device(device)
|
42
|
+
|
43
|
+
# or:
|
44
|
+
|
45
|
+
SimCtl.device(name: 'my iphone 5', state: 'Booted').delete!
|
46
|
+
```
|
47
|
+
|
48
|
+
### devicetype
|
49
|
+
|
50
|
+
```ruby
|
51
|
+
SimCtl.devicetype(name: 'iPhone 5')
|
52
|
+
|
53
|
+
#<SimCtl::DeviceType:0x007fd90dd9f2e0 @name="iPhone 5", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-5">
|
54
|
+
```
|
55
|
+
|
56
|
+
### device
|
57
|
+
|
58
|
+
```ruby
|
59
|
+
SimCtl.device(name: 'my iphone 5', state: 'Booted')
|
60
|
+
|
61
|
+
#<SimCtl::Device:0x007fd90dcce910 @state="Booted", @availability="(available)", @name="my iphone 5", @udid="6F7269E0-6375-4B72-8451-F2728BF6DA82", @os="iOS 9.2">
|
62
|
+
```
|
63
|
+
|
64
|
+
### erase_device
|
65
|
+
|
66
|
+
```ruby
|
67
|
+
device = SimCtl.device(name: 'my iphone 5', state: 'Booted')
|
68
|
+
SimCtl.erase_device(device)
|
69
|
+
|
70
|
+
# or:
|
71
|
+
|
72
|
+
SimCtl.device(name: 'my iphone 5', state: 'Booted').erase!
|
73
|
+
```
|
74
|
+
|
75
|
+
### list_devices
|
76
|
+
|
77
|
+
```ruby
|
78
|
+
SimCtl.list_devices.each do |device|
|
79
|
+
puts device.inspect
|
80
|
+
end
|
81
|
+
|
82
|
+
#<SimCtl::Device:0x007fd90dd06f90 @state="Booted", @availability="(available)", @name="iPhone 5", @udid="25AC234A-EB91-46EF-9BCB-B7405813EF93", @os="iOS 9.2">
|
83
|
+
#<SimCtl::Device:0x007fd90dd06e00 @state="Shutdown", @availability="(available)", @name="iPhone 5", @udid="CEFEDED6-94C0-4B6B-8ABC-B855C49F06B0", @os="iOS 9.2">
|
84
|
+
```
|
85
|
+
|
86
|
+
### list_devicetypes
|
87
|
+
|
88
|
+
```ruby
|
89
|
+
SimCtl.list_devicetypes.each do |devicetype|
|
90
|
+
puts devicetype.inspect
|
91
|
+
end
|
92
|
+
|
93
|
+
#<SimCtl::DeviceType:0x007fbce48f5270 @name="iPhone 4s", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-4s">
|
94
|
+
#<SimCtl::DeviceType:0x007fbce48f51f8 @name="iPhone 5", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-5">
|
95
|
+
#<SimCtl::DeviceType:0x007fbce48f5180 @name="iPhone 5s", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-5s">
|
96
|
+
#<SimCtl::DeviceType:0x007fbce48f5108 @name="iPhone 6", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-6">
|
97
|
+
#<SimCtl::DeviceType:0x007fbce48f5090 @name="iPhone 6 Plus", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-6-Plus">
|
98
|
+
#<SimCtl::DeviceType:0x007fbce48f5018 @name="iPhone 6s", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-6s">
|
99
|
+
#<SimCtl::DeviceType:0x007fbce48f4fa0 @name="iPhone 6s Plus", @identifier="com.apple.CoreSimulator.SimDeviceType.iPhone-6s-Plus">
|
100
|
+
#<SimCtl::DeviceType:0x007fbce48f4f28 @name="iPad 2", @identifier="com.apple.CoreSimulator.SimDeviceType.iPad-2">
|
101
|
+
#<SimCtl::DeviceType:0x007fbce48f4eb0 @name="iPad Retina", @identifier="com.apple.CoreSimulator.SimDeviceType.iPad-Retina">
|
102
|
+
#<SimCtl::DeviceType:0x007fbce48f4e38 @name="iPad Air", @identifier="com.apple.CoreSimulator.SimDeviceType.iPad-Air">
|
103
|
+
#<SimCtl::DeviceType:0x007fbce48f4dc0 @name="iPad Air 2", @identifier="com.apple.CoreSimulator.SimDeviceType.iPad-Air-2">
|
104
|
+
#<SimCtl::DeviceType:0x007fbce48f4d48 @name="iPad Pro", @identifier="com.apple.CoreSimulator.SimDeviceType.iPad-Pro">
|
105
|
+
#<SimCtl::DeviceType:0x007fbce48f4cd0 @name="Apple TV 1080p", @identifier="com.apple.CoreSimulator.SimDeviceType.Apple-TV-1080p">
|
106
|
+
#<SimCtl::DeviceType:0x007fbce48f4c58 @name="Apple Watch - 38mm", @identifier="com.apple.CoreSimulator.SimDeviceType.Apple-Watch-38mm">
|
107
|
+
#<SimCtl::DeviceType:0x007fbce48f4be0 @name="Apple Watch - 42mm", @identifier="com.apple.CoreSimulator.SimDeviceType.Apple-Watch-42mm">
|
108
|
+
```
|
109
|
+
|
110
|
+
### list_runtimes
|
111
|
+
|
112
|
+
```ruby
|
113
|
+
SimCtl.list_runtimes.each do |runtime|
|
114
|
+
puts runtime.inspect
|
115
|
+
end
|
116
|
+
|
117
|
+
#<SimCtl::Runtime:0x007fbce48cd6d0 @buildversion="12B411", @availability="(available)", @name="iOS 8.1", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-8-1", @version="8.1">
|
118
|
+
#<SimCtl::Runtime:0x007fbce48cd5e0 @buildversion="12D508", @availability="(available)", @name="iOS 8.2", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-8-2", @version="8.2">
|
119
|
+
#<SimCtl::Runtime:0x007fbce48cd4f0 @buildversion="12F70", @availability="(available)", @name="iOS 8.3", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-8-3", @version="8.3">
|
120
|
+
#<SimCtl::Runtime:0x007fbce48cd400 @buildversion="12H141", @availability="(available)", @name="iOS 8.4", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-8-4", @version="8.4">
|
121
|
+
#<SimCtl::Runtime:0x007fbce48cd310 @buildversion="13A344", @availability="(available)", @name="iOS 9.0", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-9-0", @version="9.0">
|
122
|
+
#<SimCtl::Runtime:0x007fbce48cd220 @buildversion="13C75", @availability="(available)", @name="iOS 9.2", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-9-2", @version="9.2">
|
123
|
+
#<SimCtl::Runtime:0x007fbce48cd130 @buildversion="13U78", @availability="(available)", @name="tvOS 9.1", @identifier="com.apple.CoreSimulator.SimRuntime.tvOS-9-1", @version="9.1">
|
124
|
+
#<SimCtl::Runtime:0x007fbce48cd040 @buildversion="13S660", @availability="(available)", @name="watchOS 2.1", @identifier="com.apple.CoreSimulator.SimRuntime.watchOS-2-1", @version="2.1">
|
125
|
+
```
|
126
|
+
|
127
|
+
### runtime
|
128
|
+
|
129
|
+
```ruby
|
130
|
+
SimCtl.runtime(name: 'iOS 9.2')
|
131
|
+
|
132
|
+
#<SimCtl::Runtime:0x007fd90dd2da28 @buildversion="13C75", @availability="(available)", @name="iOS 9.2", @identifier="com.apple.CoreSimulator.SimRuntime.iOS-9-2", @version="9.2">
|
133
|
+
```
|
134
|
+
|
135
|
+
### shutdown_device
|
136
|
+
|
137
|
+
```ruby
|
138
|
+
device = SimCtl.device(name: 'my iphone 5', state: 'Booted')
|
139
|
+
SimCtl.shutdown_device(device)
|
140
|
+
|
141
|
+
# or:
|
142
|
+
|
143
|
+
SimCtl.device(name: 'my iphone 5', state: 'Booted').shutdown!
|
144
|
+
```
|
data/Rakefile
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
#!/usr/bin/env rake
|
2
|
+
require 'bundler/gem_tasks'
|
3
|
+
require 'rake/testtask'
|
4
|
+
|
5
|
+
desc 'Execute simctl tests'
|
6
|
+
Rake::TestTask.new(:test) do |t|
|
7
|
+
t.libs << 'lib' << 'test'
|
8
|
+
t.pattern = 'test/**/*_test.rb'
|
9
|
+
t.verbose = true
|
10
|
+
end
|
11
|
+
|
12
|
+
desc 'Default: Execute simctl tests'
|
13
|
+
task default: :test
|
data/lib/simctl.rb
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
require 'simctl/command'
|
2
|
+
require 'simctl/device'
|
3
|
+
require 'simctl/device_type'
|
4
|
+
require 'simctl/list'
|
5
|
+
require 'simctl/runtime'
|
6
|
+
|
7
|
+
module SimCtl
|
8
|
+
class << self
|
9
|
+
def command
|
10
|
+
return @command if defined?(@command)
|
11
|
+
@command = SimCtl::Command.new
|
12
|
+
end
|
13
|
+
|
14
|
+
private
|
15
|
+
|
16
|
+
def respond_to_missing?(method_name, include_private=false)
|
17
|
+
command.respond_to?(method_name, include_private)
|
18
|
+
end
|
19
|
+
|
20
|
+
def method_missing(method_name, *args, &block)
|
21
|
+
if command.respond_to?(method_name)
|
22
|
+
return command.send(method_name, *args, &block)
|
23
|
+
end
|
24
|
+
super
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'simctl/command/boot'
|
2
|
+
require 'simctl/command/create'
|
3
|
+
require 'simctl/command/delete'
|
4
|
+
require 'simctl/command/erase'
|
5
|
+
require 'simctl/command/list'
|
6
|
+
require 'simctl/command/shutdown'
|
7
|
+
require 'simctl/executor'
|
8
|
+
|
9
|
+
module SimCtl
|
10
|
+
class Command
|
11
|
+
include SimCtl::Command::Boot
|
12
|
+
include SimCtl::Command::Create
|
13
|
+
include SimCtl::Command::Delete
|
14
|
+
include SimCtl::Command::Erase
|
15
|
+
include SimCtl::Command::List
|
16
|
+
include SimCtl::Command::Shutdown
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module Boot
|
4
|
+
COMMAND = %w[xcrun simctl boot]
|
5
|
+
|
6
|
+
# Boots a device
|
7
|
+
#
|
8
|
+
# @param device [SimCtl::Device] the device to boot
|
9
|
+
def boot_device(device)
|
10
|
+
Executor.execute([COMMAND, device.udid])
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module Create
|
4
|
+
COMMAND = %w[xcrun simctl create]
|
5
|
+
|
6
|
+
# Creates a device
|
7
|
+
#
|
8
|
+
# @param name [String] name of the new device
|
9
|
+
# @param device_type [SimCtl::DeviceTYpe] device type of the new device
|
10
|
+
# @param runtime [SimCtl::Runtime] runtime of the new device
|
11
|
+
def create_device(name, device_type, runtime)
|
12
|
+
Executor.execute([COMMAND, "'#{name}'", device_type.identifier, runtime.identifier]) do |identifier|
|
13
|
+
device(udid: identifier)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module Delete
|
4
|
+
COMMAND = %w[xcrun simctl delete]
|
5
|
+
|
6
|
+
# Delete a device
|
7
|
+
#
|
8
|
+
# @param device [SimCtl::Device] the device to delete
|
9
|
+
def delete_device(device)
|
10
|
+
Executor.execute([COMMAND, device.udid])
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module Erase
|
4
|
+
COMMAND = %w[xcrun simctl erase]
|
5
|
+
|
6
|
+
# Erase a device
|
7
|
+
#
|
8
|
+
# @param device [SimCtl::Device] the device to erase
|
9
|
+
def erase_device(device)
|
10
|
+
Executor.execute([COMMAND, device.udid])
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
|
@@ -0,0 +1,59 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module List
|
4
|
+
COMMAND = %w[xcrun simctl list -j]
|
5
|
+
|
6
|
+
# Find a device
|
7
|
+
#
|
8
|
+
# @param filter [Hash] the filter
|
9
|
+
# @return [SimCtl::Device, nil] the device matching the given filter
|
10
|
+
def device(filter)
|
11
|
+
list_devices.where(filter).first
|
12
|
+
end
|
13
|
+
|
14
|
+
# Find a device type
|
15
|
+
#
|
16
|
+
# @param filter [Hash] the filter
|
17
|
+
# @return [SimCtl::DeviceType, nil] the device type matching the given filter
|
18
|
+
def devicetype(filter)
|
19
|
+
list_devicetypes.where(filter).first
|
20
|
+
end
|
21
|
+
|
22
|
+
# List all devices
|
23
|
+
#
|
24
|
+
# @return [SimCtl::List] a list of SimCtl::Device objects
|
25
|
+
def list_devices
|
26
|
+
Executor.execute([COMMAND, 'devices']) do |json|
|
27
|
+
SimCtl::List.new(json['devices'].map {|os, devices| devices.map {|device| Device.new(device.merge(os: os))}}.flatten)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
# List all device types
|
32
|
+
#
|
33
|
+
# @return [SimCtl::List] a list of SimCtl::DeviceType objects
|
34
|
+
def list_devicetypes
|
35
|
+
Executor.execute([COMMAND, 'devicetypes']) do |json|
|
36
|
+
SimCtl::List.new(json['devicetypes'].map {|devicetype| DeviceType.new(devicetype)})
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
# List all runtimes
|
41
|
+
#
|
42
|
+
# @return [SimCtl::List] a list of SimCtl::Runtime objects
|
43
|
+
def list_runtimes
|
44
|
+
Executor.execute([COMMAND, 'runtimes']) do |json|
|
45
|
+
SimCtl::List.new(json['runtimes'].map {|runtime| Runtime.new(runtime)})
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
# Find a runtime
|
50
|
+
#
|
51
|
+
# @param filter [Hash] the filter
|
52
|
+
# @return [SimCtl::Runtime, nil] the runtime matching the given filter
|
53
|
+
def runtime(filter)
|
54
|
+
list_runtimes.where(filter).first
|
55
|
+
end
|
56
|
+
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class Command
|
3
|
+
module Shutdown
|
4
|
+
COMMAND = %w[xcrun simctl shutdown]
|
5
|
+
|
6
|
+
# Shutdown a device
|
7
|
+
#
|
8
|
+
# @param device [SimCtl::Device] the device to shutdown
|
9
|
+
def shutdown_device(device)
|
10
|
+
Executor.execute([COMMAND, device.udid])
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require 'simctl/object'
|
2
|
+
|
3
|
+
module SimCtl
|
4
|
+
class Device < Object
|
5
|
+
attr_reader :availability, :name, :os, :state, :udid
|
6
|
+
|
7
|
+
# Boot the device
|
8
|
+
def boot!
|
9
|
+
SimCtl.boot_device(self)
|
10
|
+
end
|
11
|
+
|
12
|
+
# Delete the device
|
13
|
+
def delete!
|
14
|
+
SimCtl.delete_device(self)
|
15
|
+
end
|
16
|
+
|
17
|
+
# Erase the device
|
18
|
+
def erase!
|
19
|
+
SimCtl.erase_device(self)
|
20
|
+
end
|
21
|
+
|
22
|
+
# Shutdown the device
|
23
|
+
def shutdown!
|
24
|
+
SimCtl.shutdown_device(self)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'json'
|
2
|
+
require 'open3'
|
3
|
+
|
4
|
+
module SimCtl
|
5
|
+
class Executor
|
6
|
+
class << self
|
7
|
+
def execute(command)
|
8
|
+
command = command.flatten.join(' ')
|
9
|
+
Open3.popen2e(command) do |_, io, result|
|
10
|
+
output = io.read
|
11
|
+
raise StandardError.new(output) if result.value.to_i > 0
|
12
|
+
return unless block_given?
|
13
|
+
if looks_like_json?(output)
|
14
|
+
yield JSON.parse(output)
|
15
|
+
else
|
16
|
+
yield output.chomp
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
private
|
22
|
+
|
23
|
+
def looks_like_json?(output)
|
24
|
+
output.start_with?('[') || output.start_with?('{')
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
data/lib/simctl/list.rb
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
module SimCtl
|
2
|
+
class List < Array
|
3
|
+
# Filters an array of objects by a given hash. The keys of
|
4
|
+
# the hash must be methods implemented by the objects. The
|
5
|
+
# values of the hash are compared to the values the object
|
6
|
+
# returns when calling the methods.
|
7
|
+
#
|
8
|
+
# @param filter [Hash] the filters that should be applied
|
9
|
+
# @return [Array] the filtered array.
|
10
|
+
def where(filter)
|
11
|
+
select do |item|
|
12
|
+
matches = true
|
13
|
+
filter.each do |key, value|
|
14
|
+
matches &= item.send(key) == value
|
15
|
+
end
|
16
|
+
matches
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
data/simctl.gemspec
ADDED
@@ -0,0 +1,24 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$LOAD_PATH.unshift File.expand_path('../lib', __FILE__)
|
3
|
+
require 'simctl/version'
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = 'simctl'
|
7
|
+
s.version = SimCtl::VERSION
|
8
|
+
s.summary = 'Ruby interface to xcrun simctl'
|
9
|
+
s.description = 'Ruby interface to xcrun simctl'
|
10
|
+
|
11
|
+
s.authors = ['Johannes Plunien']
|
12
|
+
s.email = %w(plu@pqpq.de)
|
13
|
+
s.homepage = 'https://github.com/plu/simctl'
|
14
|
+
s.licenses = ['MIT']
|
15
|
+
|
16
|
+
s.files = `git ls-files`.split("\n")
|
17
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
18
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map { |f| File.basename(f) }
|
19
|
+
s.require_paths = ['lib']
|
20
|
+
|
21
|
+
s.add_development_dependency 'rake'
|
22
|
+
s.add_development_dependency 'maxitest'
|
23
|
+
s.add_development_dependency 'shoulda-context'
|
24
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
require 'securerandom'
|
2
|
+
require 'test_helper'
|
3
|
+
require 'timeout'
|
4
|
+
|
5
|
+
class SimCtl::Command::CRUDTest < Minitest::Test
|
6
|
+
def setup
|
7
|
+
@devicetype = SimCtl.list_devicetypes.select {|devicetype| devicetype.name =~ %r[iPhone]}.first
|
8
|
+
@runtime = SimCtl.list_runtimes.select {|runtime| runtime.name =~ %r[iOS.*9]}.first
|
9
|
+
@device = SimCtl.create_device SecureRandom.hex, @devicetype, @runtime
|
10
|
+
wait_for {|device| device.state != 'Creating'}
|
11
|
+
end
|
12
|
+
|
13
|
+
def teardown
|
14
|
+
device = SimCtl.device(udid: @device.udid)
|
15
|
+
SimCtl.delete_device device if device
|
16
|
+
end
|
17
|
+
|
18
|
+
def wait_for
|
19
|
+
Timeout::timeout(30) do
|
20
|
+
loop do
|
21
|
+
device = SimCtl.device(udid: @device.udid)
|
22
|
+
break if yield device
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
should 'find the device created in setup' do
|
28
|
+
device = SimCtl.device(udid: @device.udid)
|
29
|
+
assert_kind_of SimCtl::Device, device
|
30
|
+
assert device.availability != nil
|
31
|
+
assert device.name != nil
|
32
|
+
assert device.os != nil
|
33
|
+
assert device.state != nil
|
34
|
+
assert device.udid != nil
|
35
|
+
end
|
36
|
+
|
37
|
+
should 'erase the device created in setup' do
|
38
|
+
device = SimCtl.device(udid: @device.udid)
|
39
|
+
SimCtl.erase_device device
|
40
|
+
end
|
41
|
+
|
42
|
+
should 'boot/shutdown the device created in setup' do
|
43
|
+
device = SimCtl.device(udid: @device.udid)
|
44
|
+
SimCtl.boot_device device
|
45
|
+
wait_for {|device| device.state == 'Booted'}
|
46
|
+
SimCtl.shutdown_device device
|
47
|
+
wait_for {|device| device.state == 'Shutdown'}
|
48
|
+
end
|
49
|
+
|
50
|
+
should 'delete the device created in setup' do
|
51
|
+
device = SimCtl.device(udid: @device.udid)
|
52
|
+
SimCtl.delete_device device
|
53
|
+
assert_nil SimCtl.device(udid: @device.udid)
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
require 'test_helper'
|
2
|
+
|
3
|
+
class SimCtl::Command::ListTest < Minitest::Test
|
4
|
+
context 'list_devicetypes' do
|
5
|
+
should 'contain some devicetypes' do
|
6
|
+
assert SimCtl.list_devicetypes.count > 0
|
7
|
+
end
|
8
|
+
|
9
|
+
should 'be a SimCtl::DeviceType object' do
|
10
|
+
assert_kind_of SimCtl::DeviceType, SimCtl.list_devicetypes.first
|
11
|
+
end
|
12
|
+
|
13
|
+
should 'parse identifier property' do
|
14
|
+
assert SimCtl.list_devicetypes.first.identifier != nil
|
15
|
+
end
|
16
|
+
|
17
|
+
should 'parse name property' do
|
18
|
+
assert SimCtl.list_devicetypes.first.name != nil
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
context 'list_runtimes' do
|
23
|
+
should 'contain some runtimes' do
|
24
|
+
assert SimCtl.list_runtimes.count > 0
|
25
|
+
end
|
26
|
+
|
27
|
+
should 'be a SimCtl::Runtime object' do
|
28
|
+
assert_kind_of SimCtl::Runtime, SimCtl.list_runtimes.first
|
29
|
+
end
|
30
|
+
|
31
|
+
should 'parse availability property' do
|
32
|
+
assert SimCtl.list_runtimes.first.availability != nil
|
33
|
+
end
|
34
|
+
|
35
|
+
should 'parse buildversion property' do
|
36
|
+
assert SimCtl.list_runtimes.first.buildversion != nil
|
37
|
+
end
|
38
|
+
|
39
|
+
should 'parse identifier property' do
|
40
|
+
assert SimCtl.list_runtimes.first.identifier != nil
|
41
|
+
end
|
42
|
+
|
43
|
+
should 'parse name property' do
|
44
|
+
assert SimCtl.list_runtimes.first.name != nil
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
data/test/test_helper.rb
ADDED
metadata
ADDED
@@ -0,0 +1,116 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: simctl
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Johannes Plunien
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2015-12-24 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: rake
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ">="
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '0'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - ">="
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '0'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: maxitest
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: shoulda-context
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
description: Ruby interface to xcrun simctl
|
56
|
+
email:
|
57
|
+
- plu@pqpq.de
|
58
|
+
executables: []
|
59
|
+
extensions: []
|
60
|
+
extra_rdoc_files: []
|
61
|
+
files:
|
62
|
+
- ".gitignore"
|
63
|
+
- ".travis.yml"
|
64
|
+
- Gemfile
|
65
|
+
- Gemfile.lock
|
66
|
+
- LICENSE
|
67
|
+
- README.md
|
68
|
+
- Rakefile
|
69
|
+
- lib/simctl.rb
|
70
|
+
- lib/simctl/command.rb
|
71
|
+
- lib/simctl/command/boot.rb
|
72
|
+
- lib/simctl/command/create.rb
|
73
|
+
- lib/simctl/command/delete.rb
|
74
|
+
- lib/simctl/command/erase.rb
|
75
|
+
- lib/simctl/command/list.rb
|
76
|
+
- lib/simctl/command/shutdown.rb
|
77
|
+
- lib/simctl/device.rb
|
78
|
+
- lib/simctl/device_type.rb
|
79
|
+
- lib/simctl/executor.rb
|
80
|
+
- lib/simctl/list.rb
|
81
|
+
- lib/simctl/object.rb
|
82
|
+
- lib/simctl/runtime.rb
|
83
|
+
- lib/simctl/version.rb
|
84
|
+
- simctl.gemspec
|
85
|
+
- test/simctl/command/crud_test.rb
|
86
|
+
- test/simctl/command/list_test.rb
|
87
|
+
- test/test_helper.rb
|
88
|
+
homepage: https://github.com/plu/simctl
|
89
|
+
licenses:
|
90
|
+
- MIT
|
91
|
+
metadata: {}
|
92
|
+
post_install_message:
|
93
|
+
rdoc_options: []
|
94
|
+
require_paths:
|
95
|
+
- lib
|
96
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
97
|
+
requirements:
|
98
|
+
- - ">="
|
99
|
+
- !ruby/object:Gem::Version
|
100
|
+
version: '0'
|
101
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
102
|
+
requirements:
|
103
|
+
- - ">="
|
104
|
+
- !ruby/object:Gem::Version
|
105
|
+
version: '0'
|
106
|
+
requirements: []
|
107
|
+
rubyforge_project:
|
108
|
+
rubygems_version: 2.4.6
|
109
|
+
signing_key:
|
110
|
+
specification_version: 4
|
111
|
+
summary: Ruby interface to xcrun simctl
|
112
|
+
test_files:
|
113
|
+
- test/simctl/command/crud_test.rb
|
114
|
+
- test/simctl/command/list_test.rb
|
115
|
+
- test/test_helper.rb
|
116
|
+
has_rdoc:
|