instrumental_agent 0.13.1 → 0.13.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: d22dc8e7673c5701cf1cdc654ebd8b953eff28c7
4
- data.tar.gz: 53fa9eb53ace63abe3a243b3ce8397bf3d53f01f
3
+ metadata.gz: 6cde80ee21af0e7064fda51df68d72943ccb8879
4
+ data.tar.gz: 441003be93bf1ec0ec287f431726e5bf789b9266
5
5
  SHA512:
6
- metadata.gz: bc8ec3269967f078690443c315c0dfe1d450603855b2f9cb31a01f3625cb00642cb1e5975cfdc7b3ee25c04c9f4b5249f4c1d5b1aa8fc7e0fed5086fb5f9fc49
7
- data.tar.gz: 3c846c8a723c0c5e9b5c1998a78d330caad7a7b67e663ebb8a5abd21e8866348af0538ef14149b7bd897190930703e9e2c990cb5168caa9fa929941354f762ea
6
+ metadata.gz: 8ba42e1733a75ed3d1c879c7116d04e1cdfb0f042375b14601b7f32b5800eb2bcf2c6f7f8e60bd41729a627be0e8e5076593569042666f9b817d1425995c1342
7
+ data.tar.gz: f838d3a4dc8a9ab272350300776c3473ff586a072e71673f0db66d7de0364f1e85860cd99a64f0e76b3d461b27574816655e04ee8311cbcc76817078f7ecd034
data/.travis.yml CHANGED
@@ -1,3 +1,4 @@
1
+ sudo: false
1
2
  language: ruby
2
3
  rvm:
3
4
  - 1.8.7
@@ -6,5 +7,3 @@ rvm:
6
7
  - 2.0.0
7
8
  - jruby-18mode
8
9
  - jruby-19mode
9
- - rbx-18mode
10
- - rbx-19mode
data/CHANGELOG.md CHANGED
@@ -1,3 +1,6 @@
1
+ ### 0.13.2 [August 17, 2015]
2
+ * DNS resolution fixes to prevent fork'd child deadlocks
3
+
1
4
  ### 0.13.1 [August 3, 2015]
2
5
  * Revert encrypted support
3
6
 
data/Gemfile CHANGED
@@ -1,8 +1,8 @@
1
1
  source "https://rubygems.org"
2
2
 
3
3
  gemspec
4
-
5
- if RUBY_VERSION < "1.9"
4
+ ruby_engine = defined?(RUBY_ENGINE) && RUBY_ENGINE
5
+ if RUBY_VERSION < "1.9" && !%w{jruby rbx}.include?(ruby_engine)
6
6
  # Built and installed via ext/mkrf_conf.rb
7
7
  gem 'system_timer', '~> 1.2'
8
8
  end
data/Rakefile CHANGED
@@ -1,3 +1,4 @@
1
+ require 'bundler/setup'
1
2
  require 'bundler/gem_tasks'
2
3
  require 'rspec/core/rake_task'
3
4
 
@@ -0,0 +1,69 @@
1
+ Certificate:
2
+ Data:
3
+ Version: 3 (0x2)
4
+ Serial Number: 903804111 (0x35def4cf)
5
+ Signature Algorithm: sha1WithRSAEncryption
6
+ Issuer: C=US, O=Equifax, OU=Equifax Secure Certificate Authority
7
+ Validity
8
+ Not Before: Aug 22 16:41:51 1998 GMT
9
+ Not After : Aug 22 16:41:51 2018 GMT
10
+ Subject: C=US, O=Equifax, OU=Equifax Secure Certificate Authority
11
+ Subject Public Key Info:
12
+ Public Key Algorithm: rsaEncryption
13
+ RSA Public Key: (1024 bit)
14
+ Modulus (1024 bit):
15
+ 00:c1:5d:b1:58:67:08:62:ee:a0:9a:2d:1f:08:6d:
16
+ 91:14:68:98:0a:1e:fe:da:04:6f:13:84:62:21:c3:
17
+ d1:7c:ce:9f:05:e0:b8:01:f0:4e:34:ec:e2:8a:95:
18
+ 04:64:ac:f1:6b:53:5f:05:b3:cb:67:80:bf:42:02:
19
+ 8e:fe:dd:01:09:ec:e1:00:14:4f:fc:fb:f0:0c:dd:
20
+ 43:ba:5b:2b:e1:1f:80:70:99:15:57:93:16:f1:0f:
21
+ 97:6a:b7:c2:68:23:1c:cc:4d:59:30:ac:51:1e:3b:
22
+ af:2b:d6:ee:63:45:7b:c5:d9:5f:50:d2:e3:50:0f:
23
+ 3a:88:e7:bf:14:fd:e0:c7:b9
24
+ Exponent: 65537 (0x10001)
25
+ X509v3 extensions:
26
+ X509v3 CRL Distribution Points:
27
+ DirName:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority/CN=CRL1
28
+
29
+ X509v3 Private Key Usage Period:
30
+ Not After: Aug 22 16:41:51 2018 GMT
31
+ X509v3 Key Usage:
32
+ Certificate Sign, CRL Sign
33
+ X509v3 Authority Key Identifier:
34
+ keyid:48:E6:68:F9:2B:D2:B2:95:D7:47:D8:23:20:10:4F:33:98:90:9F:D4
35
+
36
+ X509v3 Subject Key Identifier:
37
+ 48:E6:68:F9:2B:D2:B2:95:D7:47:D8:23:20:10:4F:33:98:90:9F:D4
38
+ X509v3 Basic Constraints:
39
+ CA:TRUE
40
+ 1.2.840.113533.7.65.0:
41
+ 0...V3.0c....
42
+ Signature Algorithm: sha1WithRSAEncryption
43
+ 58:ce:29:ea:fc:f7:de:b5:ce:02:b9:17:b5:85:d1:b9:e3:e0:
44
+ 95:cc:25:31:0d:00:a6:92:6e:7f:b6:92:63:9e:50:95:d1:9a:
45
+ 6f:e4:11:de:63:85:6e:98:ee:a8:ff:5a:c8:d3:55:b2:66:71:
46
+ 57:de:c0:21:eb:3d:2a:a7:23:49:01:04:86:42:7b:fc:ee:7f:
47
+ a2:16:52:b5:67:67:d3:40:db:3b:26:58:b2:28:77:3d:ae:14:
48
+ 77:61:d6:fa:2a:66:27:a0:0d:fa:a7:73:5c:ea:70:f1:94:21:
49
+ 65:44:5f:fa:fc:ef:29:68:a9:a2:87:79:ef:79:ef:4f:ac:07:
50
+ 77:38
51
+ -----BEGIN CERTIFICATE-----
52
+ MIIDIDCCAomgAwIBAgIENd70zzANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQGEwJV
53
+ UzEQMA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUgQ2Vy
54
+ dGlmaWNhdGUgQXV0aG9yaXR5MB4XDTk4MDgyMjE2NDE1MVoXDTE4MDgyMjE2NDE1
55
+ MVowTjELMAkGA1UEBhMCVVMxEDAOBgNVBAoTB0VxdWlmYXgxLTArBgNVBAsTJEVx
56
+ dWlmYXggU2VjdXJlIENlcnRpZmljYXRlIEF1dGhvcml0eTCBnzANBgkqhkiG9w0B
57
+ AQEFAAOBjQAwgYkCgYEAwV2xWGcIYu6gmi0fCG2RFGiYCh7+2gRvE4RiIcPRfM6f
58
+ BeC4AfBONOziipUEZKzxa1NfBbPLZ4C/QgKO/t0BCezhABRP/PvwDN1Dulsr4R+A
59
+ cJkVV5MW8Q+XarfCaCMczE1ZMKxRHjuvK9buY0V7xdlfUNLjUA86iOe/FP3gx7kC
60
+ AwEAAaOCAQkwggEFMHAGA1UdHwRpMGcwZaBjoGGkXzBdMQswCQYDVQQGEwJVUzEQ
61
+ MA4GA1UEChMHRXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUgQ2VydGlm
62
+ aWNhdGUgQXV0aG9yaXR5MQ0wCwYDVQQDEwRDUkwxMBoGA1UdEAQTMBGBDzIwMTgw
63
+ ODIyMTY0MTUxWjALBgNVHQ8EBAMCAQYwHwYDVR0jBBgwFoAUSOZo+SvSspXXR9gj
64
+ IBBPM5iQn9QwHQYDVR0OBBYEFEjmaPkr0rKV10fYIyAQTzOYkJ/UMAwGA1UdEwQF
65
+ MAMBAf8wGgYJKoZIhvZ9B0EABA0wCxsFVjMuMGMDAgbAMA0GCSqGSIb3DQEBBQUA
66
+ A4GBAFjOKer89961zgK5F7WF0bnj4JXMJTENAKaSbn+2kmOeUJXRmm/kEd5jhW6Y
67
+ 7qj/WsjTVbJmcVfewCHrPSqnI0kBBIZCe/zuf6IWUrVnZ9NA2zsmWLIodz2uFHdh
68
+ 1voqZiegDfqnc1zqcPGUIWVEX/r87yloqaKHee9570+sB3c4
69
+ -----END CERTIFICATE-----
@@ -0,0 +1,80 @@
1
+ Certificate:
2
+ Data:
3
+ Version: 3 (0x2)
4
+ Serial Number: 1227750 (0x12bbe6)
5
+ Signature Algorithm: sha1WithRSAEncryption
6
+ Issuer: C=US, O=Equifax, OU=Equifax Secure Certificate Authority
7
+ Validity
8
+ Not Before: May 21 04:00:00 2002 GMT
9
+ Not After : Aug 21 04:00:00 2018 GMT
10
+ Subject: C=US, O=GeoTrust Inc., CN=GeoTrust Global CA
11
+ Subject Public Key Info:
12
+ Public Key Algorithm: rsaEncryption
13
+ RSA Public Key: (2048 bit)
14
+ Modulus (2048 bit):
15
+ 00:da:cc:18:63:30:fd:f4:17:23:1a:56:7e:5b:df:
16
+ 3c:6c:38:e4:71:b7:78:91:d4:bc:a1:d8:4c:f8:a8:
17
+ 43:b6:03:e9:4d:21:07:08:88:da:58:2f:66:39:29:
18
+ bd:05:78:8b:9d:38:e8:05:b7:6a:7e:71:a4:e6:c4:
19
+ 60:a6:b0:ef:80:e4:89:28:0f:9e:25:d6:ed:83:f3:
20
+ ad:a6:91:c7:98:c9:42:18:35:14:9d:ad:98:46:92:
21
+ 2e:4f:ca:f1:87:43:c1:16:95:57:2d:50:ef:89:2d:
22
+ 80:7a:57:ad:f2:ee:5f:6b:d2:00:8d:b9:14:f8:14:
23
+ 15:35:d9:c0:46:a3:7b:72:c8:91:bf:c9:55:2b:cd:
24
+ d0:97:3e:9c:26:64:cc:df:ce:83:19:71:ca:4e:e6:
25
+ d4:d5:7b:a9:19:cd:55:de:c8:ec:d2:5e:38:53:e5:
26
+ 5c:4f:8c:2d:fe:50:23:36:fc:66:e6:cb:8e:a4:39:
27
+ 19:00:b7:95:02:39:91:0b:0e:fe:38:2e:d1:1d:05:
28
+ 9a:f6:4d:3e:6f:0f:07:1d:af:2c:1e:8f:60:39:e2:
29
+ fa:36:53:13:39:d4:5e:26:2b:db:3d:a8:14:bd:32:
30
+ eb:18:03:28:52:04:71:e5:ab:33:3d:e1:38:bb:07:
31
+ 36:84:62:9c:79:ea:16:30:f4:5f:c0:2b:e8:71:6b:
32
+ e4:f9
33
+ Exponent: 65537 (0x10001)
34
+ X509v3 extensions:
35
+ X509v3 Authority Key Identifier:
36
+ keyid:48:E6:68:F9:2B:D2:B2:95:D7:47:D8:23:20:10:4F:33:98:90:9F:D4
37
+
38
+ X509v3 Subject Key Identifier:
39
+ C0:7A:98:68:8D:89:FB:AB:05:64:0C:11:7D:AA:7D:65:B8:CA:CC:4E
40
+ X509v3 Basic Constraints: critical
41
+ CA:TRUE
42
+ X509v3 Key Usage: critical
43
+ Certificate Sign, CRL Sign
44
+ X509v3 CRL Distribution Points:
45
+ URI:http://crl.geotrust.com/crls/secureca.crl
46
+
47
+ X509v3 Certificate Policies:
48
+ Policy: X509v3 Any Policy
49
+ CPS: https://www.geotrust.com/resources/repository
50
+
51
+ Signature Algorithm: sha1WithRSAEncryption
52
+ 76:e1:12:6e:4e:4b:16:12:86:30:06:b2:81:08:cf:f0:08:c7:
53
+ c7:71:7e:66:ee:c2:ed:d4:3b:1f:ff:f0:f0:c8:4e:d6:43:38:
54
+ b0:b9:30:7d:18:d0:55:83:a2:6a:cb:36:11:9c:e8:48:66:a3:
55
+ 6d:7f:b8:13:d4:47:fe:8b:5a:5c:73:fc:ae:d9:1b:32:19:38:
56
+ ab:97:34:14:aa:96:d2:eb:a3:1c:14:08:49:b6:bb:e5:91:ef:
57
+ 83:36:eb:1d:56:6f:ca:da:bc:73:63:90:e4:7f:7b:3e:22:cb:
58
+ 3d:07:ed:5f:38:74:9c:e3:03:50:4e:a1:af:98:ee:61:f2:84:
59
+ 3f:12
60
+ -----BEGIN CERTIFICATE-----
61
+ MIIDfTCCAuagAwIBAgIDErvmMA0GCSqGSIb3DQEBBQUAME4xCzAJBgNVBAYTAlVT
62
+ MRAwDgYDVQQKEwdFcXVpZmF4MS0wKwYDVQQLEyRFcXVpZmF4IFNlY3VyZSBDZXJ0
63
+ aWZpY2F0ZSBBdXRob3JpdHkwHhcNMDIwNTIxMDQwMDAwWhcNMTgwODIxMDQwMDAw
64
+ WjBCMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEbMBkGA1UE
65
+ AxMSR2VvVHJ1c3QgR2xvYmFsIENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB
66
+ CgKCAQEA2swYYzD99BcjGlZ+W988bDjkcbd4kdS8odhM+KhDtgPpTSEHCIjaWC9m
67
+ OSm9BXiLnTjoBbdqfnGk5sRgprDvgOSJKA+eJdbtg/OtppHHmMlCGDUUna2YRpIu
68
+ T8rxh0PBFpVXLVDviS2Aelet8u5fa9IAjbkU+BQVNdnARqN7csiRv8lVK83Qlz6c
69
+ JmTM386DGXHKTubU1XupGc1V3sjs0l44U+VcT4wt/lAjNvxm5suOpDkZALeVAjmR
70
+ Cw7+OC7RHQWa9k0+bw8HHa8sHo9gOeL6NlMTOdReJivbPagUvTLrGAMoUgRx5asz
71
+ PeE4uwc2hGKceeoWMPRfwCvocWvk+QIDAQABo4HwMIHtMB8GA1UdIwQYMBaAFEjm
72
+ aPkr0rKV10fYIyAQTzOYkJ/UMB0GA1UdDgQWBBTAephojYn7qwVkDBF9qn1luMrM
73
+ TjAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBBjA6BgNVHR8EMzAxMC+g
74
+ LaArhilodHRwOi8vY3JsLmdlb3RydXN0LmNvbS9jcmxzL3NlY3VyZWNhLmNybDBO
75
+ BgNVHSAERzBFMEMGBFUdIAAwOzA5BggrBgEFBQcCARYtaHR0cHM6Ly93d3cuZ2Vv
76
+ dHJ1c3QuY29tL3Jlc291cmNlcy9yZXBvc2l0b3J5MA0GCSqGSIb3DQEBBQUAA4GB
77
+ AHbhEm5OSxYShjAGsoEIz/AIx8dxfmbuwu3UOx//8PDITtZDOLC5MH0Y0FWDomrL
78
+ NhGc6Ehmo21/uBPUR/6LWlxz/K7ZGzIZOKuXNBSqltLroxwUCEm2u+WR74M26x1W
79
+ b8ravHNjkOR/ez4iyz0H7V84dJzjA1BOoa+Y7mHyhD8S
80
+ -----END CERTIFICATE-----
@@ -0,0 +1,94 @@
1
+ Certificate:
2
+ Data:
3
+ Version: 3 (0x2)
4
+ Serial Number: 146039 (0x23a77)
5
+ Signature Algorithm: sha256WithRSAEncryption
6
+ Issuer: C=US, O=GeoTrust Inc., CN=GeoTrust Global CA
7
+ Validity
8
+ Not Before: Aug 29 21:39:32 2014 GMT
9
+ Not After : May 20 21:39:32 2022 GMT
10
+ Subject: C=US, O=GeoTrust Inc., CN=RapidSSL SHA256 CA - G3
11
+ Subject Public Key Info:
12
+ Public Key Algorithm: rsaEncryption
13
+ RSA Public Key: (2048 bit)
14
+ Modulus (2048 bit):
15
+ 00:af:54:9b:d9:58:5d:1e:2c:56:c6:d5:e8:7f:f4:
16
+ 7d:16:03:ff:d0:8b:5a:e4:8e:a7:dd:54:2e:d4:04:
17
+ c0:5d:98:9c:8d:90:0f:bc:10:65:5f:da:9a:d6:44:
18
+ 7c:c0:9f:b5:e9:4a:8c:0b:06:43:04:bb:f4:96:e2:
19
+ 26:f6:61:01:91:66:31:22:c3:34:34:5f:3f:3f:91:
20
+ 2f:44:5f:dc:c7:14:b6:03:9f:86:4b:0e:a3:ff:a0:
21
+ 80:02:83:c3:d3:1f:69:52:d6:9d:64:0f:c9:83:e7:
22
+ 1b:c4:70:ac:94:e7:c3:a4:6a:2c:bd:b8:9e:69:d8:
23
+ be:0a:8f:16:63:5a:68:71:80:7b:30:de:15:04:bf:
24
+ cc:d3:bf:3e:48:05:55:7a:b3:d7:10:0c:03:fc:9b:
25
+ fd:08:a7:8c:8c:db:a7:8e:f1:1e:63:dc:b3:01:2f:
26
+ 7f:af:57:c3:3c:48:a7:83:68:21:a7:2f:e7:a7:3f:
27
+ f0:b5:0c:fc:f5:84:d1:53:bc:0e:72:4f:60:0c:42:
28
+ b8:98:ad:19:88:57:d7:04:ec:87:bf:7e:87:4e:a3:
29
+ 21:f9:53:fd:36:98:48:8d:d6:f8:bb:48:f2:29:c8:
30
+ 64:d1:cc:54:48:53:8b:af:b7:65:1e:bf:29:33:29:
31
+ d9:29:60:48:f8:ff:91:bc:57:58:e5:35:2e:bb:69:
32
+ b6:59
33
+ Exponent: 65537 (0x10001)
34
+ X509v3 extensions:
35
+ X509v3 Authority Key Identifier:
36
+ keyid:C0:7A:98:68:8D:89:FB:AB:05:64:0C:11:7D:AA:7D:65:B8:CA:CC:4E
37
+
38
+ X509v3 Subject Key Identifier:
39
+ C3:9C:F3:FC:D3:46:08:34:BB:CE:46:7F:A0:7C:5B:F3:E2:08:CB:59
40
+ X509v3 Basic Constraints: critical
41
+ CA:TRUE, pathlen:0
42
+ X509v3 Key Usage: critical
43
+ Certificate Sign, CRL Sign
44
+ X509v3 CRL Distribution Points:
45
+ URI:http://g.symcb.com/crls/gtglobal.crl
46
+
47
+ Authority Information Access:
48
+ OCSP - URI:http://g.symcd.com
49
+
50
+ X509v3 Certificate Policies:
51
+ Policy: 2.16.840.1.113733.1.7.54
52
+ CPS: http://www.geotrust.com/resources/cps
53
+
54
+ Signature Algorithm: sha256WithRSAEncryption
55
+ a3:58:1e:c6:43:32:ac:ac:2f:93:78:b7:ea:ae:54:40:47:2d:
56
+ 7e:78:8d:50:f6:f8:66:ac:d6:4f:73:d6:44:ef:af:0b:cc:5b:
57
+ c1:f4:4f:9a:8f:49:7e:60:af:c2:27:c7:16:f1:fb:93:81:90:
58
+ a9:7c:ef:6f:7e:6e:45:94:16:84:bd:ec:49:f1:c4:0e:f4:af:
59
+ 04:59:83:87:0f:2c:3b:97:c3:5a:12:9b:7b:04:35:7b:a3:95:
60
+ 33:08:7b:93:71:22:42:b3:a9:d9:6f:4f:81:92:fc:07:b6:79:
61
+ bc:84:4a:9d:77:09:f1:c5:89:f2:f0:b4:9c:54:aa:12:7b:0d:
62
+ ba:4f:ef:93:19:ec:ef:7d:4e:61:a3:8e:76:9c:59:cf:8c:94:
63
+ b1:84:97:f7:1a:b9:07:b8:b2:c6:4f:13:79:db:bf:4f:51:1b:
64
+ 7f:69:0d:51:2a:c1:d6:15:ff:37:51:34:65:51:f4:1e:be:38:
65
+ 6a:ec:0e:ab:bf:3d:7b:39:05:7b:f4:f3:fb:1a:a1:d0:c8:7e:
66
+ 4e:64:8d:cd:8c:61:55:90:fe:3a:ca:5d:25:0f:f8:1d:a3:4a:
67
+ 74:56:4f:1a:55:40:70:75:25:a6:33:2e:ba:4b:a5:5d:53:9a:
68
+ 0d:30:e1:8d:5f:61:2c:af:cc:ef:b0:99:a1:80:ff:0b:f2:62:
69
+ 4c:70:26:98
70
+ -----BEGIN CERTIFICATE-----
71
+ MIIEJTCCAw2gAwIBAgIDAjp3MA0GCSqGSIb3DQEBCwUAMEIxCzAJBgNVBAYTAlVT
72
+ MRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i
73
+ YWwgQ0EwHhcNMTQwODI5MjEzOTMyWhcNMjIwNTIwMjEzOTMyWjBHMQswCQYDVQQG
74
+ EwJVUzEWMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEgMB4GA1UEAxMXUmFwaWRTU0wg
75
+ U0hBMjU2IENBIC0gRzMwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCv
76
+ VJvZWF0eLFbG1eh/9H0WA//Qi1rkjqfdVC7UBMBdmJyNkA+8EGVf2prWRHzAn7Xp
77
+ SowLBkMEu/SW4ib2YQGRZjEiwzQ0Xz8/kS9EX9zHFLYDn4ZLDqP/oIACg8PTH2lS
78
+ 1p1kD8mD5xvEcKyU58Okaiy9uJ5p2L4KjxZjWmhxgHsw3hUEv8zTvz5IBVV6s9cQ
79
+ DAP8m/0Ip4yM26eO8R5j3LMBL3+vV8M8SKeDaCGnL+enP/C1DPz1hNFTvA5yT2AM
80
+ QriYrRmIV9cE7Ie/fodOoyH5U/02mEiN1vi7SPIpyGTRzFRIU4uvt2UevykzKdkp
81
+ YEj4/5G8V1jlNS67abZZAgMBAAGjggEdMIIBGTAfBgNVHSMEGDAWgBTAephojYn7
82
+ qwVkDBF9qn1luMrMTjAdBgNVHQ4EFgQUw5zz/NNGCDS7zkZ/oHxb8+IIy1kwEgYD
83
+ VR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8EBAMCAQYwNQYDVR0fBC4wLDAqoCig
84
+ JoYkaHR0cDovL2cuc3ltY2IuY29tL2NybHMvZ3RnbG9iYWwuY3JsMC4GCCsGAQUF
85
+ BwEBBCIwIDAeBggrBgEFBQcwAYYSaHR0cDovL2cuc3ltY2QuY29tMEwGA1UdIARF
86
+ MEMwQQYKYIZIAYb4RQEHNjAzMDEGCCsGAQUFBwIBFiVodHRwOi8vd3d3Lmdlb3Ry
87
+ dXN0LmNvbS9yZXNvdXJjZXMvY3BzMA0GCSqGSIb3DQEBCwUAA4IBAQCjWB7GQzKs
88
+ rC+TeLfqrlRARy1+eI1Q9vhmrNZPc9ZE768LzFvB9E+aj0l+YK/CJ8cW8fuTgZCp
89
+ fO9vfm5FlBaEvexJ8cQO9K8EWYOHDyw7l8NaEpt7BDV7o5UzCHuTcSJCs6nZb0+B
90
+ kvwHtnm8hEqddwnxxYny8LScVKoSew26T++TGezvfU5ho452nFnPjJSxhJf3GrkH
91
+ uLLGTxN5279PURt/aQ1RKsHWFf83UTRlUfQevjhq7A6rvz17OQV79PP7GqHQyH5O
92
+ ZI3NjGFVkP46yl0lD/gdo0p0Vk8aVUBwdSWmMy66S6VdU5oNMOGNX2Esr8zvsJmh
93
+ gP8L8mJMcCaY
94
+ -----END CERTIFICATE-----
@@ -19,10 +19,4 @@ Gem::Specification.new do |s|
19
19
  s.add_development_dependency(%q<rake>, [">= 0"])
20
20
  s.add_development_dependency(%q<rspec>, ["~> 2.0"])
21
21
  s.add_development_dependency(%q<fuubar>, [">= 0"])
22
- if RUBY_VERSION >= "1.9.2"
23
- s.add_development_dependency(%q<guard>, [">= 0"])
24
- s.add_development_dependency(%q<guard-rspec>, [">= 0"])
25
- s.add_development_dependency(%q<growl>, [">= 0"])
26
- s.add_development_dependency(%q<rb-fsevent>, [">= 0"])
27
- end
28
22
  end
@@ -1,22 +1,28 @@
1
1
  require 'instrumental/version'
2
2
  require 'instrumental/system_timer'
3
3
  require 'logger'
4
+ require 'openssl' rescue nil
5
+ require 'resolv'
4
6
  require 'thread'
5
7
  require 'socket'
6
8
 
7
9
 
8
10
  module Instrumental
9
11
  class Agent
10
- BACKOFF = 2.0
11
- MAX_RECONNECT_DELAY = 15
12
- MAX_BUFFER = 5000
13
- REPLY_TIMEOUT = 10
14
- CONNECT_TIMEOUT = 20
15
- EXIT_FLUSH_TIMEOUT = 5
16
- HOSTNAME = Socket.gethostbyname(Socket.gethostname).first rescue Socket.gethostname
12
+ BACKOFF = 2.0
13
+ CONNECT_TIMEOUT = 20
14
+ EXIT_FLUSH_TIMEOUT = 5
15
+ HOSTNAME = Socket.gethostbyname(Socket.gethostname).first rescue Socket.gethostname
16
+ MAX_BUFFER = 5000
17
+ MAX_RECONNECT_DELAY = 15
18
+ REPLY_TIMEOUT = 10
19
+ RESOLUTION_FAILURES_BEFORE_WAITING = 3
20
+ RESOLUTION_WAIT = 30
21
+ RESOLVE_TIMEOUT = 1
17
22
 
18
- attr_accessor :host, :port, :synchronous, :queue
19
- attr_reader :connection, :enabled
23
+
24
+ attr_accessor :host, :port, :synchronous, :queue, :dns_resolutions, :last_connect_at
25
+ attr_reader :connection, :enabled, :secure
20
26
 
21
27
  def self.logger=(l)
22
28
  @logger = l
@@ -42,17 +48,35 @@ module Instrumental
42
48
 
43
49
  # defaults
44
50
  # host: collector.instrumentalapp.com
45
- # port: 8000
51
+ # port: 8001
46
52
  # enabled: true
47
53
  # synchronous: false
54
+ # secure: true
55
+ # verify: true
48
56
  @api_key = api_key
49
57
  @host, @port = options[:collector].to_s.split(':')
50
58
  @host ||= 'collector.instrumentalapp.com'
51
- @port = (@port || 8000).to_i
59
+ requested_secure = options[:secure] == true
60
+ desired_secure = options[:secure].nil? ? allows_secure? : !!options[:secure]
61
+ if !allows_secure? && desired_secure
62
+ logger.warn "Cannot connect to Instrumental via encrypted transport, SSL not available"
63
+ if requested_secure
64
+ options[:enabled] = false
65
+ logger.error "You requested secure protocol to connect to Instrumental, but it is not available on this system (OpenSSL is not defined). Connecting to Instrumental has been disabled."
66
+ end
67
+ desired_secure = false
68
+ end
69
+ @secure = desired_secure
70
+ @verify_cert = options[:verify_cert].nil? ? true : !!options[:verify_cert]
71
+ default_port = @secure ? 8001 : 8000
72
+ @port = (@port || default_port).to_i
52
73
  @enabled = options.has_key?(:enabled) ? !!options[:enabled] : true
53
74
  @synchronous = !!options[:synchronous]
54
75
  @pid = Process.pid
55
76
  @allow_reconnect = true
77
+ @certs = certificates
78
+ @dns_resolutions = 0
79
+ @last_connect_at = 0
56
80
 
57
81
  setup_cleanup_at_exit if @enabled
58
82
  end
@@ -179,6 +203,9 @@ module Instrumental
179
203
  @thread.kill
180
204
  @thread = nil
181
205
  end
206
+ if @queue
207
+ @queue.clear
208
+ end
182
209
  end
183
210
 
184
211
  # Called when a process is exiting to give it some extra time to
@@ -239,22 +266,29 @@ module Instrumental
239
266
  logger.error "Exception occurred: #{e.message}\n#{e.backtrace.join("\n")}"
240
267
  end
241
268
 
242
- def ipv4_address_for_host(host, port)
243
- addresses = Socket.getaddrinfo(host, port, 'AF_INET')
244
- if (result = addresses.first)
245
- _, _, _, address, _ = result
246
- address
247
- else
248
- raise Exception.new("Couldn't get address information for host #{host}")
269
+ def ipv4_address_for_host(host, port, moment_to_connect = Time.now.to_i)
270
+ self.dns_resolutions = dns_resolutions + 1
271
+ time_since_last_connect = moment_to_connect - last_connect_at
272
+ if dns_resolutions < RESOLUTION_FAILURES_BEFORE_WAITING || time_since_last_connect >= RESOLUTION_WAIT
273
+ self.last_connect_at = moment_to_connect
274
+ with_timeout(RESOLVE_TIMEOUT) do
275
+ address = Resolv.getaddresses(host).select { |address| address =~ Resolv::IPv4::Regex }.first
276
+ self.dns_resolutions = 0
277
+ address
278
+ end
249
279
  end
280
+ rescue Exception => e
281
+ logger.warn "Couldn't resolve address for #{host}:#{port}"
282
+ report_exception(e)
283
+ nil
250
284
  end
251
285
 
252
286
  def send_command(cmd, *args)
253
287
  cmd = "%s %s\n" % [cmd, args.collect { |a| a.to_s }.join(" ")]
254
288
  if enabled?
255
- start_connection_worker if !running?
256
289
 
257
- if @queue.size < MAX_BUFFER
290
+ start_connection_worker if !running?
291
+ if @queue && @queue.size < MAX_BUFFER
258
292
  @queue_full_warning = false
259
293
  logger.debug "Queueing: #{cmd.chomp}"
260
294
  queue_message(cmd, { :synchronous => @synchronous })
@@ -291,10 +325,41 @@ module Instrumental
291
325
  message
292
326
  end
293
327
 
328
+ def wait_exceptions
329
+ classes = [Errno::EAGAIN]
330
+ if defined?(IO::EAGAINWaitReadable)
331
+ classes << IO::EAGAINWaitReadable
332
+ end
333
+ if defined?(IO::EWOULDBLOCKWaitReadable)
334
+ classes << IO::EWOULDBLOCKWaitReadable
335
+ end
336
+ if defined?(IO::WaitReadable)
337
+ classes << IO::WaitReadable
338
+ end
339
+ classes
340
+ end
341
+
342
+
294
343
  def test_connection
295
344
  begin
296
- @socket.read_nonblock(1)
297
- rescue Errno::EAGAIN
345
+ # In the case where the socket is an OpenSSL::SSL::SSLSocket,
346
+ # on Ruby 1.8.6, 1.8.7 or 1.9.1, read_nonblock does not exist,
347
+ # and so the case of testing socket liveliness via a nonblocking
348
+ # read that catches a wait condition won't work.
349
+ #
350
+ # We grab the SSL socket's underlying IO object and perform the
351
+ # non blocking read there in order to ensure the socket is still
352
+ # valid
353
+ if @socket.respond_to?(:read_nonblock)
354
+ @socket.read_nonblock(1)
355
+ elsif @socket.respond_to?(:io)
356
+ # The SSL Socket may send down additional data at close time,
357
+ # so we perform two nonblocking reads, one to pull any pending
358
+ # data on the socket, and the second to actually perform the connection
359
+ # liveliness test
360
+ @socket.io.read_nonblock(1024) && @socket.io.read_nonblock(1024)
361
+ end
362
+ rescue *wait_exceptions
298
363
  # noop
299
364
  end
300
365
  end
@@ -302,13 +367,17 @@ module Instrumental
302
367
  def start_connection_worker
303
368
  if enabled?
304
369
  disconnect
305
- @pid = Process.pid
306
- @queue = Queue.new
307
- @sync_mutex = Mutex.new
308
- @failures = 0
309
- logger.info "Starting thread"
310
- @thread = Thread.new do
311
- run_worker_loop
370
+ @queue ||= Queue.new
371
+ address = ipv4_address_for_host(@host, @port)
372
+ if address
373
+ @pid = Process.pid
374
+ @sync_mutex = Mutex.new
375
+ @failures = 0
376
+ @sockaddr_in = Socket.pack_sockaddr_in(@port, address)
377
+ logger.info "Starting thread"
378
+ @thread = Thread.new do
379
+ run_worker_loop
380
+ end
312
381
  end
313
382
  end
314
383
  end
@@ -323,15 +392,30 @@ module Instrumental
323
392
  end
324
393
  end
325
394
 
326
-
395
+ def open_socket(sockaddr_in, secure, verify_cert)
396
+ sock = Socket.new(Socket::PF_INET, Socket::SOCK_STREAM, 0)
397
+ sock.connect(sockaddr_in)
398
+ if secure
399
+ context = OpenSSL::SSL::SSLContext.new
400
+ if verify_cert
401
+ context.set_params(:verify_mode => OpenSSL::SSL::VERIFY_PEER | OpenSSL::SSL::VERIFY_FAIL_IF_NO_PEER_CERT)
402
+ else
403
+ context.set_params(:verify_mode => OpenSSL::SSL::VERIFY_NONE)
404
+ end
405
+ ssl_socket = OpenSSL::SSL::SSLSocket.new(sock, context)
406
+ ssl_socket.sync_close = true
407
+ ssl_socket.connect
408
+ sock = ssl_socket
409
+ end
410
+ sock
411
+ end
327
412
 
328
413
  def run_worker_loop
329
414
  command_and_args = nil
330
415
  command_options = nil
331
416
  logger.info "connecting to collector"
332
- @socket = Socket.new(Socket::PF_INET, Socket::SOCK_STREAM, 0)
333
417
  with_timeout(CONNECT_TIMEOUT) do
334
- @socket.connect Socket.pack_sockaddr_in(port, ipv4_address_for_host(host, port))
418
+ @socket = open_socket(@sockaddr_in, @secure, @verify_cert)
335
419
  end
336
420
  logger.info "connected to collector at #{host}:#{port}"
337
421
  hello_options = {
@@ -347,37 +431,46 @@ module Instrumental
347
431
  @failures = 0
348
432
  loop do
349
433
  command_and_args, command_options = @queue.pop
350
- sync_resource = command_options && command_options[:sync_resource]
351
- test_connection
352
- case command_and_args
353
- when 'exit'
354
- logger.info "Exiting, #{@queue.size} commands remain"
355
- return true
356
- when 'flush'
357
- release_resource = true
358
- else
359
- logger.debug "Sending: #{command_and_args.chomp}"
360
- @socket.puts command_and_args
361
- end
362
- command_and_args = nil
363
- command_options = nil
364
- if sync_resource
365
- @sync_mutex.synchronize do
366
- sync_resource.signal
434
+ if command_and_args
435
+ sync_resource = command_options && command_options[:sync_resource]
436
+ test_connection
437
+ case command_and_args
438
+ when 'exit'
439
+ logger.info "Exiting, #{@queue.size} commands remain"
440
+ return true
441
+ when 'flush'
442
+ release_resource = true
443
+ else
444
+ logger.debug "Sending: #{command_and_args.chomp}"
445
+ @socket.puts command_and_args
446
+ end
447
+ command_and_args = nil
448
+ command_options = nil
449
+ if sync_resource
450
+ @sync_mutex.synchronize do
451
+ sync_resource.signal
452
+ end
367
453
  end
368
454
  end
369
455
  end
370
456
  rescue Exception => err
371
- if err.is_a?(EOFError)
457
+ allow_reconnect = @allow_reconnect
458
+ case err
459
+ when EOFError
372
460
  # nop
373
- elsif err.is_a?(Errno::ECONNREFUSED)
374
- logger.error "unable to connect to Instrumental."
461
+ when Errno::ECONNREFUSED, Errno::EHOSTUNREACH, Errno::EADDRINUSE
462
+ # If the connection has been refused by Instrumental
463
+ # or we cannot reach the server
464
+ # or the connection state of this socket is in a race
465
+ logger.error "unable to connect to Instrumental, hanging up with #{@queue.size} messages remaining"
466
+ allow_reconnect = false
375
467
  else
376
468
  report_exception(err)
377
469
  end
378
- if @allow_reconnect == false ||
470
+ if allow_reconnect == false ||
379
471
  (command_options && command_options[:allow_reconnect] == false)
380
472
  logger.info "Not trying to reconnect"
473
+ @failures = 0
381
474
  return
382
475
  end
383
476
  if command_and_args
@@ -401,14 +494,20 @@ module Instrumental
401
494
  end
402
495
 
403
496
  def running?
404
- !@thread.nil? && @pid == Process.pid
497
+ !@thread.nil? && @pid == Process.pid && @thread.alive?
498
+ end
499
+
500
+ def flush_socket(socket)
501
+ socket.flush
405
502
  end
406
503
 
407
504
  def disconnect
408
505
  if connected?
409
506
  logger.info "Disconnecting..."
410
507
  begin
411
- with_timeout(EXIT_FLUSH_TIMEOUT) { @socket.flush }
508
+ with_timeout(EXIT_FLUSH_TIMEOUT) do
509
+ flush_socket(@socket)
510
+ end
412
511
  rescue Timeout::Error
413
512
  logger.info "Timed out flushing socket..."
414
513
  end
@@ -417,6 +516,21 @@ module Instrumental
417
516
  @socket = nil
418
517
  end
419
518
 
519
+ def allows_secure?
520
+ defined?(OpenSSL)
521
+ end
522
+
523
+ def certificates
524
+ if allows_secure?
525
+ base_dir = File.expand_path(File.join(File.dirname(__FILE__), "..", ".."))
526
+ %w{equifax geotrust rapidssl}.map do |name|
527
+ OpenSSL::X509::Certificate.new(File.open(File.join(base_dir, "certs", "#{name}.ca.pem")))
528
+ end
529
+ else
530
+ []
531
+ end
532
+ end
533
+
420
534
  end
421
535
 
422
536
  end