Skip to content

Commit e0d1fd1

Browse files
committed
Merge branch 'release/v0.6.0'
2 parents 094d6f4 + 41a6384 commit e0d1fd1

10 files changed

+372
-29
lines changed

.travis.yml

+9-5
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,17 @@
11
language: ruby
2+
#cache: bundler
23

34
before_install:
5+
# https://github.com/travis-ci/travis-ci/issues/8978
6+
- gem update --system
47
- gem update bundler
58
- bundle version
69

710
rvm:
8-
- "1.9.3"
9-
- "2.0.0"
10-
- "2.1"
11-
- "2.2"
11+
- 2.2
12+
- 2.3
13+
- 2.4
14+
- 2.5
1215
- ruby-head
1316
- jruby-19mode
1417

@@ -26,4 +29,5 @@ deploy:
2629
on:
2730
tags: true
2831
repo: "iphoting/ovpnmcgen.rb"
29-
ruby: 2.0.0
32+
ruby: 2.4.0
33+
branch: master

ChangeLog

+6
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
= 0.6.0 / 2018-01-27
2+
* Added support for `EvaluateConnection`, `Domains`, via `--domains`. It will include an `ActionParameters` dict containing `Domains`, and if `--domain-probe-url` is set, also contains `RequiredURLStringProbe`.
3+
* Added support for updated bundle identifier (VPNSubType) `net.openvpn.connect.app` (changed since OpenVPN Connect 1.2.x), via `--v12compat`.
4+
* Added support for `--cert` and `--key` for inline attachment of certificate and key, to workaround bug in OpenVPN Connect 1.2.5.
5+
* Added support for `vpn-on-demand: 0` key/value pair when `--no-vod` is set, so that OpenVPN Connect can control this profile.
6+
17
= 0.5.0 / 2015-02-22
28
* Specify multiple remotes with `--remotes "host2 1194 tcp","host3 1195 udp"` flag.
39

README.md

+63-9
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,16 @@ OpenVPN iOS Configuration Profile Utility
99

1010
Generates iOS configuration profiles (.mobileconfig) that configures OpenVPN for use with VPN-on-Demand that are not accessible through the Apple Configurator or the iPhone Configuration Utility.
1111

12+
---
13+
14+
**OpenVPN Connect (iOS) v1.2.x**:
15+
- Breaking changes: enable the `--v12compat` switch.
16+
- Bug/workaround: enable the `--cert` & `--key` switches as necessary.
17+
18+
Refer to [known issues](#known-issues) below for more details.
19+
20+
---
21+
1222
Although there are many possible VPN-on-Demand (VoD) triggers, this utility currently only implements `SSIDMatch`, `InterfaceTypeMatch`, and optionally `URLStringProbe`. For 'high' (default) security level, the following algorithm is executed upon network changes, in order:
1323

1424
- If wireless SSID matches any specified with `--trusted-ssids`, tear down the VPN connection and do not reconnect on demand.
@@ -47,18 +57,26 @@ Usage: ovpnmcgen.rb generate [options] <user> <device>
4757
-c, --config FILE Specify path to config file. [Default: .ovpnmcgen.rb.yml]
4858
--cafile FILE Path to OpenVPN CA file. (Required)
4959
--tafile FILE Path to TLS-Auth Key file.
60+
--cert FILE Path to Cert file.
61+
--key FILE Path to Private Key file.
5062
--host HOSTNAME Hostname of OpenVPN server. (Required)
5163
--proto PROTO OpenVPN server protocol. [Default: udp]
5264
-p, --port PORT OpenVPN server port. [Default: 1194]
53-
--p12file FILE Path to user PKCS#12 file. (Required)
65+
--p12file FILE Path to user PKCS#12 file.
5466
--p12pass PASSWORD Password to unlock PKCS#12 file.
55-
--[no-]vod Enable or Disable VPN-On-Demand. [Default: Enabled]
67+
--[no-]vod Enable or Disable VPN-On-Demand.
68+
When Disabled, sets `vpn-on-demand: 0`, so that OpenVPN Connect can control this profile. [Default: Enabled]
69+
--v12compat Enable OpenVPN Connect 1.2.x compatibility.
70+
When Enabled, use updated `VPNSubType: net.openvpn.connect.app`
71+
(changed since OpenVPN Connect 1.2.x). [Default: Disabled]
5672
--security-level LEVEL Security level of VPN-On-Demand Behaviour: paranoid, high, medium. [Default: high]
5773
--vpn-uuid UUID Override a VPN configuration payload UUID.
5874
--profile-uuid UUID Override a Profile UUID.
5975
--cert-uuid UUID Override a Certificate payload UUID.
6076
-t, --trusted-ssids SSIDS List of comma-separated trusted SSIDs.
6177
-u, --untrusted-ssids SSIDS List of comma-separated untrusted SSIDs.
78+
-d, --domains DOMAINS List of comma-separated domain names requiring VPN service.
79+
--domain-probe-url PROBE An HTTP(S) URL to probe, using a GET request. If no HTTP response code is received from the server, a VPN connection is established in response.
6280
--url-probe URL This URL must return HTTP status 200, without redirection, before the VPN service will try establishing.
6381
--remotes REMOTES List of comma-separated alternate remotes: "<host> <port> <proto>".
6482
--ovpnconfigfile FILE Path to OpenVPN client config file.
@@ -110,13 +128,25 @@ This feature can be enabled for statistical and maintenance-protection reasons.
110128

111129
By enabling this option, you will need to reliably and quickly respond with HTTP status code 200 at the URL string supplied.
112130

131+
### Domain Matching
132+
To require an iOS device to bring up the VPN when `example.com` is requested is not so easy, especially if it is has a publicly accessible DNS resolution.
133+
134+
Apple provides an `EvaluateConnection` and `ActionParameters` configuration options with the view that certain domains will have DNS resolution failures, and hence, require the VPN to be up. In most corporate cases with internal-facing hostnames, it works well. See the `--domains` option.
135+
136+
However, if there are certain sensitive public sites (or blocked sites) that you decide that a VPN should be brought up instead, you will need to additionally specify a `RequiredURLStringProbe` that returns a non-200 response. See the `--domain-probe-url` option.
137+
113138
## Examples
114139

115140
### Typical Usage
116-
$ ovpnmcgen.rb gen --trusted-ssids home --host vpn.example.com \
117-
--cafile path/to/ca.pem --tafile path/to/ta.key \
141+
$ ovpnmcgen.rb gen --v12compat \
142+
--trusted-ssids home \
143+
--host vpn.example.com \
144+
--cafile path/to/ca.pem \
145+
--tafile path/to/ta.key \
118146
--url-probe http://vpn.example.com/status \
119-
--p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad
147+
--p12file path/to/john-ipad.p12 \
148+
--p12pass p12passphrase \
149+
john ipad
120150

121151
Output:
122152

@@ -191,7 +221,7 @@ Output:
191221
<string>DEFAULT</string>
192222
</dict>
193223
<key>VPNSubType</key>
194-
<string>net.openvpn.OpenVPN-Connect.vpnplugin</string>
224+
<string>net.openvpn.connect.app</string>
195225
<key>VPNType</key>
196226
<string>VPN</string>
197227
<key>VendorConfig</key>
@@ -270,10 +300,16 @@ Output:
270300
```
271301

272302
### Extended Usage
273-
$ ovpnmcgen.rb gen --trusted-ssids home,school --untrusted-ssids virusnet \
274-
--host vpn.example.com --cafile path/to/ca.pem --tafile path/to/ta.key \
303+
$ ovpnmcgen.rb gen --v12compat \
304+
--trusted-ssids home,school \
305+
--untrusted-ssids virusnet \
306+
--host vpn.example.com \
307+
--cafile path/to/ca.pem \
308+
--tafile path/to/ta.key \
275309
--url-probe http://vpn.example.com/status \
276-
--p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad
310+
--p12file path/to/john-ipad.p12 \
311+
--p12pass p12passphrase \
312+
john ipad
277313

278314
Output similar to above:
279315

@@ -349,8 +385,26 @@ Output similar to above:
349385
-inkey path/to/john-ipad.key -in path/to/john-ipad.crt \
350386
-passout pass:p12passphrase -name [email protected]
351387

388+
### Using OpenSSL to convert from PKCS#12 (.p12) to Cert PEM file
389+
openssl pkcs12 -in path/to/john-ipad.p12 -out path/to/john-ipad-cert.crt \
390+
-nodes -nokeys
391+
392+
### Using OpenSSL to convert from PKCS#12 (.p12) to Key PEM file
393+
openssl pkcs12 -in path/to/john-ipad.p12 -out path/to/john-ipad-key.pem \
394+
-nodes -nocerts
395+
352396
## Known Issues
353397

398+
- OpenVPN Connect v1.2.5 breaking changes
399+
400+
*Diagnosis*: Certificates no longer found or VoD mobileconfig broken after OpenVPN Connect upgrade to v1.2.5.
401+
402+
The VPN switch in the Settings.app jumps rapidly from On to Off, status switches from Connecting... to Disconnected immediately. No logs produced within the OpernVPN Connect app log viewer.
403+
404+
This is caused by 1) a breaking change, where the `VPNSubType` has changed, and 2) a bug where the OpenVPN Connect is missing a keychain access entitlement from Apple.
405+
406+
*Solution + Workaround*: Enable the `--v12compat` switch to resolve (1), and use `--cert` and `--key` switches to workaround (2).
407+
354408
- "Not connected to Internet" error/behaviour when VPN should be established.
355409

356410
*Diagnosis*: Load any site in Safari. An error message "Safari cannot open the page because your iPhone is not connected to the Internet" will be presented.

Rakefile

+4
Original file line numberDiff line numberDiff line change
@@ -7,4 +7,8 @@ end
77
desc "Run cucumber tests"
88
task :test => :cucumber
99

10+
namespace :pre_commit do
11+
task :ci => [:test]
12+
end
13+
1014
task :default => :test

bin/ovpnmcgen.rb

+22-6
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
program :version, Ovpnmcgen::VERSION
88
program :description, Ovpnmcgen::SUMMARY
99
program :help, 'Usage', 'ovpnmcgen.rb <command> [options] <args...>'
10-
program :help_formatter, :compact
10+
program :help_formatter, Commander::HelpFormatter::Terminal
1111
default_command :help
1212
never_trace!
1313
global_option '-c', '--config FILE', 'Specify path to config file. [Default: .ovpnmcgen.rb.yml]'
@@ -16,23 +16,30 @@
1616
c.syntax = 'ovpnmcgen.rb generate [options] <user> <device>'
1717
c.summary = 'Generates iOS Configuration Profiles (.mobileconfig)'
1818
c.description = 'Generates iOS configuration profiles (.mobileconfig) that configures OpenVPN for use with VPN-on-Demand that are not accessible through the Apple Configurator or the iPhone Configuration Utility.'
19-
c.example 'Typical Usage', 'ovpnmcgen.rb gen --trusted-ssids home --host vpn.example.com --cafile path/to/ca.pem --tafile path/to/ta.key --p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad'
20-
c.example 'Extended Usage', 'ovpnmcgen.rb gen --trusted-ssids home,school --untrusted-ssids virusnet --host vpn.example.com --cafile path/to/ca.pem --tafile path/to/ta.key --p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad'
19+
c.example 'Typical Usage', 'ovpnmcgen.rb gen --v12compat --trusted-ssids home --host vpn.example.com --cafile path/to/ca.pem --tafile path/to/ta.key --p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad'
20+
c.example 'Extended Usage', 'ovpnmcgen.rb gen --v12compat --trusted-ssids home,school --untrusted-ssids virusnet --host vpn.example.com --cafile path/to/ca.pem --tafile path/to/ta.key --p12file path/to/john-ipad.p12 --p12pass p12passphrase john ipad'
2121
c.example 'Using OpenSSL to convert files into PKCS#12 (.p12)', 'openssl pkcs12 -export -out path/to/john-ipad.p12 -inkey path/to/john-ipad.key -in path/to/john-ipad.crt -passout pass:p12passphrase -name [email protected]'
22+
c.example 'Using OpenSSL to convert from PKCS#12 (.p12) to Cert PEM file', 'openssl pkcs12 -in path/to/john-ipad.p12 -out path/to/john-ipad-cert.crt -nodes -nokeys'
23+
c.example 'Using OpenSSL to convert from PKCS#12 (.p12) to Key PEM file', 'openssl pkcs12 -in path/to/john-ipad.p12 -out path/to/john-ipad-key.pem -nodes -nocerts'
2224
c.option '--cafile FILE', 'Path to OpenVPN CA file. (Required)'
2325
c.option '--tafile FILE', 'Path to TLS-Auth Key file.'
26+
c.option '--cert FILE', 'Path to Cert file.'
27+
c.option '--key FILE', 'Path to Private Key file.'
2428
c.option '--host HOSTNAME', 'Hostname of OpenVPN server. (Required)'
2529
c.option '--proto PROTO', 'OpenVPN server protocol. [Default: udp]'
2630
c.option '-p', '--port PORT', 'OpenVPN server port. [Default: 1194]'
2731
c.option '--p12file FILE', 'Path to user PKCS#12 file. (Required)'
2832
c.option '--p12pass PASSWORD', 'Password to unlock PKCS#12 file.'
29-
c.option '--[no-]vod', 'Enable or Disable VPN-On-Demand. [Default: Enabled]'
33+
c.option '--[no-]vod', 'Enable or Disable VPN-On-Demand. When Disabled, sets `vpn-on-demand: 0`, so that OpenVPN Connect can control this profile. [Default: Enabled]'
34+
c.option '--v12compat', 'Enable OpenVPN Connect 1.2.x compatibility. When Enabled, use updated `VPNSubType: net.openvpn.connect.app` (changed since OpenVPN Connect 1.2.x). [Default: Disabled]'
3035
c.option '--security-level LEVEL', 'Security level of VPN-On-Demand Behaviour: paranoid, high, medium. [Default: high]'
3136
c.option '--vpn-uuid UUID', 'Override a VPN configuration payload UUID.'
3237
c.option '--profile-uuid UUID', 'Override a Profile UUID.'
3338
c.option '--cert-uuid UUID', 'Override a Certificate payload UUID.'
3439
c.option '-t', '--trusted-ssids SSIDS', Array, 'List of comma-separated trusted SSIDs.'
3540
c.option '-u', '--untrusted-ssids SSIDS', Array, 'List of comma-separated untrusted SSIDs.'
41+
c.option '-d', '--domains DOMAINS', Array, 'List of comma-separated domain names requiring VPN service.'
42+
c.option '--domain-probe-url PROBE', String, 'An HTTP(S) URL to probe, using a GET request. If no HTTP response code is received from the server, a VPN connection is established in response.'
3643
c.option '--url-probe URL', 'This URL must return HTTP status 200, without redirection, before the VPN service will try establishing.'
3744
c.option '--remotes REMOTES', Array, 'List of comma-separated alternate remotes: "<host> <port> <proto>".'
3845
c.option '--ovpnconfigfile FILE', 'Path to OpenVPN client config file.'
@@ -50,7 +57,11 @@
5057

5158
raise ArgumentError.new "Host is required" unless options.host or config.host
5259
raise ArgumentError.new "cafile is required" unless options.cafile or config.cafile
53-
raise ArgumentError.new "PKCS#12 file is required" unless options.p12file or config.p12file
60+
61+
# A --p12file or (--cert and --key) needs to be provided. Shall not prevent user from specifying both.
62+
unless (options.p12file or config.p12file) or ((options.cert or config.cert) and (options.key or config.key))
63+
raise ArgumentError.new "PKCS#12 or cert & key file required"
64+
end
5465

5566
options.default :vod => case
5667
when config.vod == true || config.no_vod == false
@@ -69,7 +80,6 @@
6980
inputs = {
7081
:user => user,
7182
:device => device,
72-
:p12file => options.p12file || config.p12file,
7383
:p12pass => options.p12pass || config.p12pass,
7484
:cafile => options.cafile || config.cafile,
7585
:host => options.host || config.host,
@@ -84,9 +94,15 @@
8494
:security_level => options.security_level
8595
}
8696
inputs[:ovpnconfigfile] = options.ovpnconfigfile || config.ovpnconfigfile if options.ovpnconfigfile or config.ovpnconfigfile
97+
inputs[:p12file] = options.p12file || config.p12file if options.p12file or config.p12file
8798
inputs[:tafile] = options.tafile || config.tafile if options.tafile or config.tafile
99+
inputs[:cert] = options.cert || config.cert if options.cert or config.cert
100+
inputs[:key] = options.key || config.key if options.key or config.key
88101
inputs[:url_probe] = options.url_probe || config.url_probe if options.url_probe or config.url_probe
89102
inputs[:remotes] = options.remotes || config.remotes if options.remotes or config.remotes
103+
inputs[:domains] = options.domains || config.domains if options.domains or config.domains
104+
inputs[:domain_probe_url] = options.domain_probe_url || config.domain_probe_url if options.domain_probe_url or config.domain_probe_url
105+
inputs[:v12compat] = options.v12compat || config.v12compat if options.v12compat or config.v12compat
90106

91107
unless options.output
92108
puts Ovpnmcgen.generate(inputs)

config/pre_commit.yml

+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
---
2+
:checks_remove:
3+
- :common
4+
- :rails
5+
:checks_add:
6+
- :merge_conflict
7+
- :yaml
8+
:warnings_remove: []
9+
:warnings_add:
10+
- :tabs
11+
- :nb_space
12+
- :whitespace
13+
- :ci

0 commit comments

Comments
 (0)