anycable 0.5.0 → 0.5.1

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 3f3531b822f2fe18921fabc66f1d440869aa70e7
4
- data.tar.gz: b346094927f772d9a65a3095c767eb12c448987f
2
+ SHA256:
3
+ metadata.gz: 190929557d66d3cb49e7dee5e8a87f841f8e6a248df55673faab9b09d4027d81
4
+ data.tar.gz: 0b703c1626163f1175664aeae26110214fdd3d819633291f390ec2401e985dee
5
5
  SHA512:
6
- metadata.gz: 85cdaf95181f6690f6cab6b0cc2b6692070a9e79f1c0dc80a78ca90de6f5778f9ca9e5381ac5d575f54251729f5d1e7f2fc58b76300b0959a7b1fefc80b4ec13
7
- data.tar.gz: 867646df97ba3723082377512ecf25bff6b68fbd7a3509fc7e794baa38a409c52a583bf9283a646276a906f3fcd9cf05c7d364b24b8009d9b6d1f2cb05211c96
6
+ metadata.gz: 17f2e03a750e60a1bc3f9022212cc7009c3ecf825bacf37552ceadbf1e195421281d5d9509495c8dfd1805948061c6f29406299e8cc51f9a1b4924549173bf30
7
+ data.tar.gz: 10032b73f09581d3bb9d9ebf844765d28fb5de1d80e970ea1ead176c67cf1c35fa93d9cd9f1d8f4f7d251ba92c03a9226b7ade4e6c9c83ed990364b3023153db
@@ -22,6 +22,9 @@ AllCops:
22
22
  Naming/AccessorMethodName:
23
23
  Enabled: false
24
24
 
25
+ Naming/UncommunicativeMethodParamName:
26
+ Enabled: false
27
+
25
28
  Style/PercentLiteralDelimiters:
26
29
  Enabled: false
27
30
 
@@ -45,6 +48,9 @@ Style/BlockDelimiters:
45
48
  Lint/AmbiguousRegexpLiteral:
46
49
  Enabled: false
47
50
 
51
+ Lint/MissingCopEnableDirective:
52
+ Enabled: false
53
+
48
54
  Metrics/MethodLength:
49
55
  Exclude:
50
56
  - 'spec/**/*.rb'
@@ -7,7 +7,7 @@ sudo: false
7
7
  notifications:
8
8
  email: false
9
9
 
10
- matrix:
11
- include:
12
- - rvm: 2.3.3
13
- - rvm: 2.4.0
10
+ rvm:
11
+ - 2.3.6
12
+ - 2.4.3
13
+ - 2.5.0
@@ -1,6 +1,12 @@
1
1
  # Change log
2
2
 
3
- ## 0.5.0 (master)
3
+ ## master
4
+
5
+ ## 0.5.1 (2018-06-13)
6
+
7
+ Minor fixes.
8
+
9
+ ## 0.5.0 (2017-10-21)
4
10
 
5
11
  - [#2](https://github.com/anycable/anycable/issues/2) Add support for [Redis Sentinel](https://redis.io/topics/sentinel). ([@accessd](https://github.com/accessd))
6
12
 
data/Gemfile CHANGED
@@ -5,6 +5,4 @@ local_gemfile = "#{File.dirname(__FILE__)}/Gemfile.local"
5
5
 
6
6
  if File.exist?(local_gemfile)
7
7
  eval(File.read(local_gemfile)) # rubocop:disable Lint/Eval
8
- else
9
- # ??
10
8
  end
data/README.md CHANGED
@@ -16,9 +16,21 @@ Rails plug-n-play integration has been extracted to [anycable-rails](https://git
16
16
 
17
17
  ## Requirements
18
18
 
19
- - Ruby ~> 2.3
19
+ - Ruby >= 2.3, <= 2.5
20
20
  - Redis (for brodcasting, [discuss other options](https://github.com/anycable/anycable/issues/2) with us!)
21
21
 
22
+ Or you can try to [build it from source](https://github.com/grpc/grpc/blob/master/INSTALL.md#build-from-source).
23
+
24
+ For MacOS there is also [the same problem](https://github.com/google/protobuf/issues/4098) with `google-protobuf` that can be solved
25
+ the following way:
26
+
27
+ ```ruby
28
+ # Gemfile
29
+ git 'https://github.com/google/protobuf' do
30
+ gem 'google-protobuf'
31
+ end
32
+ ```
33
+
22
34
  ## How It Works?
23
35
 
24
36
  ![](https://s3.amazonaws.com/anycable/Scheme.png)
@@ -29,7 +41,15 @@ Read our [Wiki](https://github.com/anycable/anycable/wiki) for more.
29
41
 
30
42
  - [AnyCable: Action Cable on steroids!](https://evilmartians.com/chronicles/anycable-actioncable-on-steroids)
31
43
 
32
- - [Connecting LiteCable to Hanami](http://gabrielmalakias.com.br/ruby/hanami/iot/2017/05/26/websockets-connecting-litecable-to-hanami.html)
44
+ - [Connecting LiteCable to Hanami](http://gabrielmalakias.com.br/ruby/hanami/iot/2017/05/26/websockets-connecting-litecable-to-hanami.html) by [@GabrielMalakias](https://github.com/GabrielMalakias)
45
+
46
+ - [From Action to Any](https://medium.com/@leshchuk/from-action-to-any-1e8d863dd4cf) by [@alekseyl](https://github.com/alekseyl)
47
+
48
+ ## Talks
49
+
50
+ - Wroc_Love.rb 2018 [slides](https://speakerdeck.com/palkan/wroc-love-dot-rb-2018-cables-cables-cables) and [video](https://www.youtube.com/watch?v=AUxFFOehiy0) (EN)
51
+
52
+ - RubyConfMY 2017 [slides](https://speakerdeck.com/palkan/rubyconf-malaysia-2017-anycable) and [video](https://www.youtube.com/watch?v=j5oFx525zNw) (EN)
33
53
 
34
54
  - RailsClub Moscow 2016 [slides](https://speakerdeck.com/palkan/railsclub-moscow-2016-anycable) and [video](https://www.youtube.com/watch?v=-k7GQKuBevY&list=PLiWUIs1hSNeOXZhotgDX7Y7qBsr24cu7o&index=4) (RU)
35
55
 
@@ -71,6 +91,7 @@ Performing Channel Actions | +
71
91
  Streaming | +
72
92
  [Custom stream callbacks](http://edgeapi.rubyonrails.org/classes/ActionCable/Channel/Streams.html) | -
73
93
  Broadcasting | +
94
+ Custom pubsub adapter | Only redis
74
95
 
75
96
  ## Build
76
97
 
@@ -91,5 +112,7 @@ make
91
112
 
92
113
  Bug reports and pull requests are welcome on GitHub at https://github.com/anycable/anycable.
93
114
 
115
+ Please, provide reproduction script (using [this template](https://github.com/anycable/anycable/blob/master/etc/bug_report_template.rb)) when submitting bugs if possible.
116
+
94
117
  ## License
95
118
  The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
@@ -26,7 +26,7 @@ Gem::Specification.new do |spec|
26
26
  spec.add_development_dependency "rake", ">= 10.0"
27
27
  spec.add_development_dependency "rack", "~> 2.0"
28
28
  spec.add_development_dependency "rspec", ">= 3.5"
29
- spec.add_development_dependency "rubocop", ">= 0.50"
29
+ spec.add_development_dependency "rubocop", "~> 0.57.1"
30
30
  spec.add_development_dependency "simplecov", ">= 0.3.8"
31
31
  spec.add_development_dependency "pry-byebug"
32
32
  end
@@ -3,17 +3,18 @@
3
3
  Code: https://github.com/palkan/websocket-shootout
4
4
  Client/Server instances: c3.4xlarge (16 vCPU, 30 GiB RAM).
5
5
 
6
+ Ruby: 2.3.4
7
+ Rails: 5.1.0
8
+
6
9
  The benchmark measures broadcasting RTT for 10k clients.
7
10
 
8
- **NOTE**: memory anc CPU usage was measured by looking at `htop` output.
11
+ **NOTE**: memory and CPU usage was measured by looking at `htop` output.
9
12
 
10
13
  ## Action Cable (8 workers)
11
14
 
12
15
  ```
13
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.
14
- 26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 10
15
- 00 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:333
16
- 4/cable --server-type=actioncable
16
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
17
+
17
18
  clients: 1000 95per-rtt: 700ms min-rtt: 2ms median-rtt: 264ms max-rtt: 854ms
18
19
  clients: 2000 95per-rtt: 1155ms min-rtt: 1ms median-rtt: 490ms max-rtt: 1358ms
19
20
  clients: 3000 95per-rtt: 1584ms min-rtt: 1ms median-rtt: 769ms max-rtt: 1644ms
@@ -24,7 +25,8 @@ clients: 7000 95per-rtt: 3907ms min-rtt: 1ms median-rtt: 1734ms m
24
25
  clients: 8000 95per-rtt: 4479ms min-rtt: 1ms median-rtt: 2137ms max-rtt: 5469ms
25
26
  clients: 9000 95per-rtt: 5734ms min-rtt: 1ms median-rtt: 2356ms max-rtt: 8234ms
26
27
  clients: 10000 95per-rtt: 5292ms min-rtt: 1ms median-rtt: 2784ms max-rtt: 6454ms
27
- 2017/02/12 09:18:45 Missing received broadcasts: expected 6600000, got 6572168
28
+
29
+ Missing received broadcasts: expected 6600000, got 6572168
28
30
  ```
29
31
 
30
32
  CPU: ~70%
@@ -34,10 +36,8 @@ MEM: ~ 4 GiB
34
36
  ## Action Cable (16 workers)
35
37
 
36
38
  ```
37
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.
38
- 26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 10
39
- 00 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:333
40
- 4/cable --server-type=actioncable
39
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
40
+
41
41
  clients: 1000 95per-rtt: 575ms min-rtt: 1ms median-rtt: 115ms max-rtt: 846ms
42
42
  clients: 2000 95per-rtt: 1144ms min-rtt: 1ms median-rtt: 250ms max-rtt: 1457ms
43
43
  clients: 3000 95per-rtt: 1274ms min-rtt: 1ms median-rtt: 439ms max-rtt: 1673ms
@@ -48,7 +48,8 @@ clients: 7000 95per-rtt: 3033ms min-rtt: 1ms median-rtt: 1008ms m
48
48
  clients: 8000 95per-rtt: 3275ms min-rtt: 1ms median-rtt: 1160ms max-rtt: 4268ms
49
49
  clients: 9000 95per-rtt: 4406ms min-rtt: 1ms median-rtt: 1342ms max-rtt: 5018ms
50
50
  clients: 10000 95per-rtt: 5414ms min-rtt: 1ms median-rtt: 1504ms max-rtt: 7039ms
51
- 2017/02/12 09:36:45 Missing received broadcasts: expected 6600000, got 6589644
51
+
52
+ Missing received broadcasts: expected 6600000, got 6589644
52
53
  ```
53
54
 
54
55
  CPU: ~80-100%
@@ -60,10 +61,8 @@ MEM: ~ 5 GiB
60
61
  About patch: https://github.com/rails/rails/issues/26999
61
62
 
62
63
  ```
63
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
64
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
65
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --serve
66
- r-type=actioncable
64
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
65
+
67
66
  clients: 1000 95per-rtt: 161ms min-rtt: 1ms median-rtt: 44ms max-rtt: 236ms
68
67
  clients: 2000 95per-rtt: 292ms min-rtt: 1ms median-rtt: 43ms max-rtt: 389ms
69
68
  clients: 3000 95per-rtt: 359ms min-rtt: 1ms median-rtt: 96ms max-rtt: 556ms
@@ -74,7 +73,8 @@ clients: 7000 95per-rtt: 717ms min-rtt: 1ms median-rtt: 95ms max
74
73
  clients: 8000 95per-rtt: 679ms min-rtt: 1ms median-rtt: 19ms max-rtt: 1089ms
75
74
  clients: 9000 95per-rtt: 561ms min-rtt: 1ms median-rtt: 25ms max-rtt: 938ms
76
75
  clients: 10000 95per-rtt: 1038ms min-rtt: 1ms median-rtt: 59ms max-rtt: 2197ms
77
- 2017/02/12 10:33:07 Missing received broadcasts: expected 6600000, got 5649743
76
+
77
+ Missing received broadcasts: expected 6600000, got 5649743
78
78
  ```
79
79
 
80
80
  CPU: ~70%
@@ -84,10 +84,8 @@ MEM: ~ 4 GiB
84
84
  ## ActionCable / Patched (16 workers)
85
85
 
86
86
  ```
87
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
88
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
89
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --serve
90
- r-type=actioncable
87
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
88
+
91
89
  clients: 1000 95per-rtt: 228ms min-rtt: 1ms median-rtt: 53ms max-rtt: 425ms
92
90
  clients: 2000 95per-rtt: 277ms min-rtt: 1ms median-rtt: 63ms max-rtt: 407ms
93
91
  clients: 3000 95per-rtt: 349ms min-rtt: 1ms median-rtt: 28ms max-rtt: 640ms
@@ -98,7 +96,8 @@ clients: 7000 95per-rtt: 466ms min-rtt: 1ms median-rtt: 90ms max
98
96
  clients: 8000 95per-rtt: 530ms min-rtt: 1ms median-rtt: 26ms max-rtt: 1225ms
99
97
  clients: 9000 95per-rtt: 459ms min-rtt: 1ms median-rtt: 39ms max-rtt: 622ms
100
98
  clients: 10000 95per-rtt: 477ms min-rtt: 1ms median-rtt: 71ms max-rtt: 632ms
101
- 2017/02/12 10:47:09 Missing received broadcasts: expected 6600000, got 5662008
99
+
100
+ Missing received broadcasts: expected 6600000, got 5662008
102
101
  ```
103
102
 
104
103
  CPU: ~80-100%
@@ -108,10 +107,8 @@ MEM: ~ 5 GiB
108
107
  ## Action Cable / AnyCable-Go
109
108
 
110
109
  ```
111
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
112
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
113
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --serve
114
- r-type=actioncable
110
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
111
+
115
112
  clients: 1000 95per-rtt: 172ms min-rtt: 2ms median-rtt: 9ms max-rtt: 220ms
116
113
  clients: 2000 95per-rtt: 228ms min-rtt: 2ms median-rtt: 16ms max-rtt: 498ms
117
114
  clients: 3000 95per-rtt: 367ms min-rtt: 2ms median-rtt: 14ms max-rtt: 798ms
@@ -122,7 +119,8 @@ clients: 7000 95per-rtt: 813ms min-rtt: 2ms median-rtt: 40ms max
122
119
  clients: 8000 95per-rtt: 657ms min-rtt: 2ms median-rtt: 39ms max-rtt: 2457ms
123
120
  clients: 9000 95per-rtt: 792ms min-rtt: 2ms median-rtt: 117ms max-rtt: 1557ms
124
121
  clients: 10000 95per-rtt: 727ms min-rtt: 2ms median-rtt: 66ms max-rtt: 3391ms
125
- 2017/02/12 09:24:35 Missing received broadcasts: expected 6600000, got 6588881
122
+
123
+ Missing received broadcasts: expected 6600000, got 6588881
126
124
  ```
127
125
 
128
126
  CPU: 15-25%
@@ -132,9 +130,8 @@ MEM: ~500 MiB
132
130
  ## JavaScript / uWS (clustered)
133
131
 
134
132
  ```
135
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
136
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
137
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334
133
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334
134
+
138
135
  clients: 1000 95per-rtt: 207ms min-rtt: 0ms median-rtt: 8ms max-rtt: 611ms
139
136
  clients: 2000 95per-rtt: 393ms min-rtt: 2ms median-rtt: 20ms max-rtt: 750ms
140
137
  clients: 3000 95per-rtt: 425ms min-rtt: 4ms median-rtt: 25ms max-rtt: 1196ms
@@ -145,7 +142,8 @@ clients: 7000 95per-rtt: 635ms min-rtt: 6ms median-rtt: 37ms max
145
142
  clients: 8000 95per-rtt: 782ms min-rtt: 5ms median-rtt: 142ms max-rtt: 1439ms
146
143
  clients: 9000 95per-rtt: 610ms min-rtt: 7ms median-rtt: 72ms max-rtt: 1552ms
147
144
  clients: 10000 95per-rtt: 1216ms min-rtt: 7ms median-rtt: 91ms max-rtt: 2195ms
148
- 2017/02/12 09:40:31 Missing received broadcasts: expected 6600000, got 6599571
145
+
146
+ Missing received broadcasts: expected 6600000, got 6599571
149
147
  ```
150
148
 
151
149
  CPU: 7-8%
@@ -155,9 +153,8 @@ MEM: ~400 MiB
155
153
  ## Go / WebSocket
156
154
 
157
155
  ```
158
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
159
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
160
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/json
156
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/json
157
+
161
158
  clients: 1000 95per-rtt: 27ms min-rtt: 7ms median-rtt: 16ms max-rtt: 44ms
162
159
  clients: 2000 95per-rtt: 193ms min-rtt: 12ms median-rtt: 28ms max-rtt: 235ms
163
160
  clients: 3000 95per-rtt: 231ms min-rtt: 15ms median-rtt: 35ms max-rtt: 433ms
@@ -168,7 +165,8 @@ clients: 7000 95per-rtt: 449ms min-rtt: 38ms median-rtt: 74ms max
168
165
  clients: 8000 95per-rtt: 539ms min-rtt: 43ms median-rtt: 89ms max-rtt: 1351ms
169
166
  clients: 9000 95per-rtt: 534ms min-rtt: 48ms median-rtt: 96ms max-rtt: 2978ms
170
167
  clients: 10000 95per-rtt: 414ms min-rtt: 57ms median-rtt: 123ms max-rtt: 3424ms
171
- 2017/02/12 09:49:29 Missing received broadcasts: expected 6600000, got 6593825
168
+
169
+ Missing received broadcasts: expected 6600000, got 6593825
172
170
  ```
173
171
 
174
172
  CPU: one core – ~80-100%, other cores – ~7-10%
@@ -178,9 +176,8 @@ MEM: ~400 MiB
178
176
  ## Erlang / Cowboy
179
177
 
180
178
  ```
181
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
182
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
183
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/ws/cable
179
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/ws/cable
180
+
184
181
  clients: 1000 95per-rtt: 204ms min-rtt: 2ms median-rtt: 11ms max-rtt: 585ms
185
182
  clients: 2000 95per-rtt: 219ms min-rtt: 3ms median-rtt: 20ms max-rtt: 620ms
186
183
  clients: 3000 95per-rtt: 348ms min-rtt: 6ms median-rtt: 19ms max-rtt: 1447ms
@@ -191,7 +188,8 @@ clients: 7000 95per-rtt: 542ms min-rtt: 13ms median-rtt: 76ms max
191
188
  clients: 8000 95per-rtt: 737ms min-rtt: 16ms median-rtt: 57ms max-rtt: 1527ms
192
189
  clients: 9000 95per-rtt: 634ms min-rtt: 17ms median-rtt: 74ms max-rtt: 1479ms
193
190
  clients: 10000 95per-rtt: 792ms min-rtt: 17ms median-rtt: 79ms max-rtt: 3805ms
194
- 2017/02/12 10:11:21 Missing received broadcasts: expected 6600000, got 6575292
191
+
192
+ Missing received broadcasts: expected 6600000, got 6575292
195
193
  ```
196
194
 
197
195
  cCPU: 20-30%
@@ -201,9 +199,8 @@ MEM: ~500 MiB
201
199
  ## Ruby / Plezi (1x8)
202
200
 
203
201
  ```
204
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
205
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
206
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
202
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
203
+
207
204
  clients: 1000 95per-rtt: 84ms min-rtt: 3ms median-rtt: 42ms max-rtt: 95ms
208
205
  clients: 2000 95per-rtt: 211ms min-rtt: 4ms median-rtt: 60ms max-rtt: 318ms
209
206
  clients: 3000 95per-rtt: 525ms min-rtt: 2ms median-rtt: 93ms max-rtt: 527ms
@@ -214,7 +211,8 @@ clients: 7000 95per-rtt: 1100ms min-rtt: 1ms median-rtt: 249ms ma
214
211
  clients: 8000 95per-rtt: 1094ms min-rtt: 7ms median-rtt: 298ms max-rtt: 1134ms
215
212
  clients: 9000 95per-rtt: 1265ms min-rtt: 1ms median-rtt: 342ms max-rtt: 1407ms
216
213
  clients: 10000 95per-rtt: 1523ms min-rtt: 2ms median-rtt: 388ms max-rtt: 1555ms
217
- 2017/02/12 10:18:07 Missing received broadcasts: expected 6600000, got 6599226
214
+
215
+ Missing received broadcasts: expected 6600000, got 6599226
218
216
  ```
219
217
 
220
218
  CPU: ~10-15% (only 1/2 of cores affected)
@@ -224,9 +222,8 @@ MEM: ~300 MiB
224
222
  ## Ruby / Plezi (8x8)
225
223
 
226
224
  ```
227
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
228
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
229
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
225
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
226
+
230
227
  clients: 1000 95per-rtt: 46ms min-rtt: 1ms median-rtt: 8ms max-rtt: 115ms
231
228
  clients: 2000 95per-rtt: 152ms min-rtt: 1ms median-rtt: 17ms max-rtt: 241ms
232
229
  clients: 3000 95per-rtt: 207ms min-rtt: 1ms median-rtt: 26ms max-rtt: 254ms
@@ -237,7 +234,8 @@ clients: 7000 95per-rtt: 210ms min-rtt: 1ms median-rtt: 59ms max
237
234
  clients: 8000 95per-rtt: 498ms min-rtt: 2ms median-rtt: 58ms max-rtt: 749ms
238
235
  clients: 9000 95per-rtt: 651ms min-rtt: 2ms median-rtt: 52ms max-rtt: 766ms
239
236
  clients: 10000 95per-rtt: 796ms min-rtt: 1ms median-rtt: 90ms max-rtt: 800ms
240
- 2017/02/12 10:14:31 Missing received broadcasts: expected 6600000, got 2736158
237
+
238
+ Missing received broadcasts: expected 6600000, got 2736158
241
239
  ```
242
240
 
243
241
  CPU: ~10%
@@ -253,9 +251,8 @@ EM shows great results but only for the first run (`em-websocket` bug?).
253
251
  First run:
254
252
 
255
253
  ```
256
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
257
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
258
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
254
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
255
+
259
256
  clients: 1000 95per-rtt: 24ms min-rtt: 5ms median-rtt: 20ms max-rtt: 30ms
260
257
  clients: 2000 95per-rtt: 61ms min-rtt: 13ms median-rtt: 42ms max-rtt: 73ms
261
258
  clients: 3000 95per-rtt: 84ms min-rtt: 18ms median-rtt: 68ms max-rtt: 109ms
@@ -266,15 +263,15 @@ clients: 7000 95per-rtt: 308ms min-rtt: 43ms median-rtt: 190ms max
266
263
  clients: 8000 95per-rtt: 383ms min-rtt: 52ms median-rtt: 218ms max-rtt: 458ms
267
264
  clients: 9000 95per-rtt: 401ms min-rtt: 50ms median-rtt: 218ms max-rtt: 550ms
268
265
  clients: 10000 95per-rtt: 429ms min-rtt: 60ms median-rtt: 246ms max-rtt: 530ms
269
- 2017/02/12 10:22:39 Missing received broadcasts: expected 6600000, got 6599593
266
+
267
+ Missing received broadcasts: expected 6600000, got 6599593
270
268
  ```
271
269
 
272
270
  Second run:
273
271
 
274
272
  ```
275
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
276
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
277
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
273
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
274
+
278
275
  clients: 1000 95per-rtt: 246ms min-rtt: 47ms median-rtt: 197ms max-rtt: 287ms
279
276
  clients: 2000 95per-rtt: 296ms min-rtt: 63ms median-rtt: 229ms max-rtt: 400ms
280
277
  clients: 3000 95per-rtt: 325ms min-rtt: 184ms median-rtt: 261ms max-rtt: 335ms
@@ -290,9 +287,8 @@ clients: 10000 95per-rtt: 813ms min-rtt: 101ms median-rtt: 448ms max
290
287
  Third run:
291
288
 
292
289
  ```
293
- deplo@ip-172-31-26-145:/webapps/anycable_bench$ bin/websocket-bench broadcast -l 172.31.26.14
294
- 5 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --paylo
295
- ad-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
290
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/
291
+
296
292
  clients: 1000 95per-rtt: 522ms min-rtt: 115ms median-rtt: 414ms max-rtt: 719ms
297
293
  clients: 2000 95per-rtt: 558ms min-rtt: 119ms median-rtt: 444ms max-rtt: 763ms
298
294
  clients: 3000 95per-rtt: 499ms min-rtt: 127ms median-rtt: 489ms max-rtt: 833ms
@@ -303,7 +299,8 @@ clients: 7000 95per-rtt: 960ms min-rtt: 130ms median-rtt: 571ms max
303
299
  clients: 8000 95per-rtt: 1038ms min-rtt: 145ms median-rtt: 592ms max-rtt: 1179ms
304
300
  clients: 9000 95per-rtt: 1110ms min-rtt: 140ms median-rtt: 625ms max-rtt: 1405ms
305
301
  clients: 10000 95per-rtt: 1176ms min-rtt: 163ms median-rtt: 649ms max-rtt: 1633ms
306
- 2017/02/12 10:28:08 Missing received broadcasts: expected 6600000, got 6599123
302
+
303
+ Missing received broadcasts: expected 6600000, got 6599123
307
304
  ```
308
305
 
309
306
  CPU: one core is totally f**ked up
@@ -0,0 +1,192 @@
1
+ # WebSocket Shootout Benchmark (2018-03-04)
2
+
3
+ Code: https://github.com/palkan/websocket-shootout
4
+ Client/Server instances: c3.2xlarge (8 vCPU, 15 GiB RAM).
5
+
6
+ Ruby: 2.5.0
7
+ Rails: 5.1.4
8
+
9
+ The benchmark measures broadcasting RTT for 10k clients.
10
+
11
+ **NOTE**: memory and peak CPU usage was measured by looking at `htop` output; avg CPU usage is a 1 minute LA.
12
+
13
+ ## Action Cable (8 workers)
14
+
15
+ Command:
16
+
17
+ ```sh
18
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
19
+
20
+ clients: 1000 95per-rtt: 847ms min-rtt: 1ms median-rtt: 174ms max-rtt: 930ms
21
+ clients: 2000 95per-rtt: 1611ms min-rtt: 1ms median-rtt: 387ms max-rtt: 1768ms
22
+ clients: 3000 95per-rtt: 2107ms min-rtt: 1ms median-rtt: 644ms max-rtt: 2601ms
23
+ clients: 4000 95per-rtt: 2504ms min-rtt: 1ms median-rtt: 899ms max-rtt: 3118ms
24
+ clients: 5000 95per-rtt: 3452ms min-rtt: 1ms median-rtt: 1070ms max-rtt: 4487ms
25
+ clients: 6000 95per-rtt: 4044ms min-rtt: 1ms median-rtt: 1261ms max-rtt: 5018ms
26
+ clients: 7000 95per-rtt: 3207ms min-rtt: 1ms median-rtt: 1647ms max-rtt: 3958ms
27
+ clients: 8000 95per-rtt: 4115ms min-rtt: 1ms median-rtt: 1957ms max-rtt: 5059ms
28
+ clients: 9000 95per-rtt: 4306ms min-rtt: 1ms median-rtt: 2273ms max-rtt: 7160ms
29
+ clients: 10000 95per-rtt: 5147ms min-rtt: 1ms median-rtt: 2462ms max-rtt: 6734ms
30
+
31
+ Missing received broadcasts: expected 6600000, got 6554972
32
+ ```
33
+
34
+ CPU (peak): ~100%
35
+ CPU (avg): ~30%
36
+
37
+ MEM: ~1.7 GiB
38
+
39
+
40
+ ## AnyCable-Go 0.5.4
41
+
42
+ ```
43
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
44
+
45
+ clients: 1000 95per-rtt: 61ms min-rtt: 2ms median-rtt: 18ms max-rtt: 178ms
46
+ clients: 2000 95per-rtt: 214ms min-rtt: 2ms median-rtt: 26ms max-rtt: 568ms
47
+ clients: 3000 95per-rtt: 275ms min-rtt: 2ms median-rtt: 32ms max-rtt: 645ms
48
+ clients: 4000 95per-rtt: 430ms min-rtt: 2ms median-rtt: 40ms max-rtt: 1463ms
49
+ clients: 5000 95per-rtt: 352ms min-rtt: 3ms median-rtt: 61ms max-rtt: 1017ms
50
+ clients: 6000 95per-rtt: 619ms min-rtt: 3ms median-rtt: 60ms max-rtt: 1630ms
51
+ clients: 7000 95per-rtt: 623ms min-rtt: 2ms median-rtt: 74ms max-rtt: 3099ms
52
+ clients: 8000 95per-rtt: 846ms min-rtt: 2ms median-rtt: 89ms max-rtt: 3165ms
53
+ clients: 9000 95per-rtt: 642ms min-rtt: 2ms median-rtt: 110ms max-rtt: 981ms
54
+ clients: 10000 95per-rtt: 1019ms min-rtt: 2ms median-rtt: 114ms max-rtt: 4759ms
55
+
56
+ Missing received broadcasts: expected 6600000, got 6580959
57
+ ```
58
+
59
+ CPU (peak): ~40%
60
+ CPU (avg): ~3%
61
+
62
+ MEM: ~500 MiB
63
+
64
+ ## AnyCable-Go 0.6.0-preview1
65
+
66
+ ```
67
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 --origin http://0.0.0.0 ws://172.31.22.121:3334/cable --server-type=actioncable
68
+
69
+ clients: 1000 95per-rtt: 64ms min-rtt: 2ms median-rtt: 15ms max-rtt: 191ms
70
+ clients: 2000 95per-rtt: 188ms min-rtt: 2ms median-rtt: 27ms max-rtt: 325ms
71
+ clients: 3000 95per-rtt: 218ms min-rtt: 2ms median-rtt: 36ms max-rtt: 854ms
72
+ clients: 4000 95per-rtt: 483ms min-rtt: 2ms median-rtt: 37ms max-rtt: 2353ms
73
+ clients: 5000 95per-rtt: 388ms min-rtt: 2ms median-rtt: 63ms max-rtt: 659ms
74
+ clients: 6000 95per-rtt: 500ms min-rtt: 2ms median-rtt: 59ms max-rtt: 1430ms
75
+ clients: 7000 95per-rtt: 692ms min-rtt: 2ms median-rtt: 85ms max-rtt: 1333ms
76
+ clients: 8000 95per-rtt: 591ms min-rtt: 2ms median-rtt: 90ms max-rtt: 2499ms
77
+ clients: 9000 95per-rtt: 959ms min-rtt: 2ms median-rtt: 90ms max-rtt: 5961ms
78
+ clients: 10000 95per-rtt: 674ms min-rtt: 2ms median-rtt: 106ms max-rtt: 2543ms
79
+
80
+ Missing received broadcasts: expected 6600000, got 6599507
81
+ ```
82
+
83
+ CPU (peak): ~40%
84
+ CPU (avg): ~3%
85
+
86
+ MEM: ~450 MiB
87
+
88
+ ## Plezi (0.15.0) + Iodine (0.4.16) (8 workers)
89
+
90
+ ```
91
+ bin/websocket-bench broadcast -l 172.31.26.145 -l 172.31.26.146 -l 172.31.26.147 --concurrent 4 --sample-size 100 --step-size 1000 --payload-padding 200 --total-steps 10 ws://172.31.22.121:3334/cable
92
+
93
+ clients: 1000 95per-rtt: 48ms min-rtt: 1ms median-rtt: 18ms max-rtt: 208ms
94
+ clients: 2000 95per-rtt: 236ms min-rtt: 0ms median-rtt: 24ms max-rtt: 612ms
95
+ clients: 3000 95per-rtt: 224ms min-rtt: 0ms median-rtt: 38ms max-rtt: 662ms
96
+ clients: 4000 95per-rtt: 402ms min-rtt: 0ms median-rtt: 39ms max-rtt: 3071ms
97
+ clients: 5000 95per-rtt: 392ms min-rtt: 1ms median-rtt: 47ms max-rtt: 1850ms
98
+ clients: 6000 95per-rtt: 582ms min-rtt: 1ms median-rtt: 64ms max-rtt: 1825ms
99
+ clients: 7000 95per-rtt: 393ms min-rtt: 1ms median-rtt: 92ms max-rtt: 729ms
100
+ clients: 8000 95per-rtt: 1181ms min-rtt: 1ms median-rtt: 42ms max-rtt: 5782ms
101
+ clients: 9000 95per-rtt: 676ms min-rtt: 1ms median-rtt: 107ms max-rtt: 2220ms
102
+ clients: 10000 95per-rtt: 603ms min-rtt: 1ms median-rtt: 131ms max-rtt: 5703ms
103
+
104
+ Missing received broadcasts: expected 6600000, got 6586987
105
+ ```
106
+
107
+ CPU (peak): ~50%
108
+ CPU (avg): ~5%
109
+
110
+ MEM: ~700 MiB
111
+
112
+ *NOTE*: Plezi app is not a Rails app, thus its memory is less than in Rails examples.
113
+
114
+ # More Stress
115
+
116
+ Peak connections: 20k.
117
+ Concurrency: 8.
118
+
119
+ ## Plezi (0.15.0) + Iodine (0.4.16)
120
+
121
+ CPU (peak): ~90%
122
+ CPU (avg): ~6%
123
+ Mem: ~1100MB
124
+
125
+
126
+ ```
127
+ clients: 1000 95per-rtt: 216ms min-rtt: 1ms median-rtt: 17ms max-rtt: 364ms
128
+ clients: 2000 95per-rtt: 446ms min-rtt: 0ms median-rtt: 24ms max-rtt: 738ms
129
+ clients: 3000 95per-rtt: 348ms min-rtt: 0ms median-rtt: 46ms max-rtt: 925ms
130
+ clients: 4000 95per-rtt: 654ms min-rtt: 2ms median-rtt: 65ms max-rtt: 1175ms
131
+ clients: 5000 95per-rtt: 590ms min-rtt: 0ms median-rtt: 67ms max-rtt: 1842ms
132
+ clients: 6000 95per-rtt: 469ms min-rtt: 1ms median-rtt: 121ms max-rtt: 1098ms
133
+ clients: 7000 95per-rtt: 705ms min-rtt: 1ms median-rtt: 121ms max-rtt: 1617ms
134
+ clients: 8000 95per-rtt: 1090ms min-rtt: 1ms median-rtt: 159ms max-rtt: 3253ms
135
+ clients: 9000 95per-rtt: 869ms min-rtt: 1ms median-rtt: 163ms max-rtt: 3945ms
136
+ clients: 10000 95per-rtt: 1171ms min-rtt: 1ms median-rtt: 247ms max-rtt: 2326ms
137
+ clients: 11000 95per-rtt: 1634ms min-rtt: 1ms median-rtt: 191ms max-rtt: 4383ms
138
+ clients: 12000 95per-rtt: 1138ms min-rtt: 2ms median-rtt: 283ms max-rtt: 8319ms
139
+ clients: 13000 95per-rtt: 1234ms min-rtt: 1ms median-rtt: 306ms max-rtt: 5429ms
140
+ clients: 14000 95per-rtt: 947ms min-rtt: 1ms median-rtt: 346ms max-rtt: 7804ms
141
+ clients: 15000 95per-rtt: 1716ms min-rtt: 1ms median-rtt: 344ms max-rtt: 7372ms
142
+ clients: 16000 95per-rtt: 1999ms min-rtt: 1ms median-rtt: 364ms max-rtt: 3047ms
143
+ clients: 17000 95per-rtt: 1729ms min-rtt: 1ms median-rtt: 410ms max-rtt: 7231ms
144
+ clients: 18000 95per-rtt: 1455ms min-rtt: 1ms median-rtt: 442ms max-rtt: 4725ms
145
+ clients: 19000 95per-rtt: 2006ms min-rtt: 1ms median-rtt: 456ms max-rtt: 3811ms
146
+ clients: 20000 95per-rtt: 2923ms min-rtt: 1ms median-rtt: 378ms max-rtt: 11954ms
147
+
148
+ Missing received broadcasts: expected 23100000, got 23089387
149
+ ```
150
+
151
+ ## Anycable-Go 0.6.0-preview1
152
+
153
+ CPU (peak): ~60%
154
+ CPU (avg): ~4%
155
+ Mem: ~1000MB
156
+
157
+ ```
158
+ clients: 1000 95per-rtt: 173ms min-rtt: 2ms median-rtt: 21ms max-rtt: 617ms
159
+ clients: 2000 95per-rtt: 311ms min-rtt: 2ms median-rtt: 39ms max-rtt: 594ms
160
+ clients: 3000 95per-rtt: 386ms min-rtt: 3ms median-rtt: 91ms max-rtt: 592ms
161
+ clients: 4000 95per-rtt: 539ms min-rtt: 2ms median-rtt: 93ms max-rtt: 973ms
162
+ clients: 5000 95per-rtt: 534ms min-rtt: 2ms median-rtt: 128ms max-rtt: 1486ms
163
+ clients: 6000 95per-rtt: 1092ms min-rtt: 2ms median-rtt: 110ms max-rtt: 3073ms
164
+ clients: 7000 95per-rtt: 726ms min-rtt: 3ms median-rtt: 185ms max-rtt: 1116ms
165
+ clients: 8000 95per-rtt: 1078ms min-rtt: 2ms median-rtt: 174ms max-rtt: 3296ms
166
+ clients: 9000 95per-rtt: 1401ms min-rtt: 8ms median-rtt: 195ms max-rtt: 6838ms
167
+ clients: 10000 95per-rtt: 1157ms min-rtt: 3ms median-rtt: 282ms max-rtt: 3446ms
168
+ clients: 11000 95per-rtt: 1804ms min-rtt: 4ms median-rtt: 271ms max-rtt: 5640ms
169
+ clients: 12000 95per-rtt: 1339ms min-rtt: 2ms median-rtt: 344ms max-rtt: 2251ms
170
+ clients: 13000 95per-rtt: 1638ms min-rtt: 3ms median-rtt: 336ms max-rtt: 3341ms
171
+ clients: 14000 95per-rtt: 1811ms min-rtt: 3ms median-rtt: 339ms max-rtt: 2079ms
172
+ clients: 15000 95per-rtt: 1407ms min-rtt: 2ms median-rtt: 435ms max-rtt: 6666ms
173
+ clients: 16000 95per-rtt: 2796ms min-rtt: 2ms median-rtt: 398ms max-rtt: 4769ms
174
+ clients: 17000 95per-rtt: 2494ms min-rtt: 6ms median-rtt: 338ms max-rtt: 36085ms
175
+ clients: 18000 95per-rtt: 2844ms min-rtt: 2ms median-rtt: 374ms max-rtt: 7384ms
176
+ clients: 19000 95per-rtt: 4010ms min-rtt: 17ms median-rtt: 370ms max-rtt: 5504ms
177
+ clients: 20000 95per-rtt: 2819ms min-rtt: 2ms median-rtt: 470ms max-rtt: 8598ms
178
+
179
+ Missing received broadcasts: expected 23100000, got 23065521
180
+ ```
181
+
182
+ # Idle Connections Benchmark
183
+
184
+ Connection 20k idle clients at 200 connections per second rate; measuring final memory usage.
185
+
186
+ Using [cable_bench](https://github.com/palkan/cable_bench).
187
+
188
+ **Action Cable (8 workers)**: ~1500 MB
189
+
190
+ **Anycable-Go 0.6.0-preview1**: ~700 MB
191
+
192
+ **Plezi (0.15.0) + Iodine (0.4.16)**: ~800 MB (a lot of connection timeout errors and "The connection was lost" errors).
@@ -0,0 +1,57 @@
1
+ # AnyCable RPC benchmarks
2
+
3
+ AnyCable RPC server benchmarks.
4
+
5
+ The benchmark is pretty simple:
6
+ - Create N concurrent _clients_ (authenticate and subscribe to `BenchmarkChannel` within the RPC app)
7
+ - Every client starts performing an action (`echo`) in a loop
8
+ - Every call is collected (request time)
9
+ - Wait for the specified amount of seconds and aggragate the results.
10
+
11
+ Measuring **requests per seconds**.
12
+
13
+ **NOTE:** this benchmark shows performance characteristics for both _clients_ and the server.
14
+ The purpose of this benchmark is to measure the thoughout of RPC connection between AnyCable services.
15
+
16
+ **NOTE 2:** "Noop RPC" is just a gRPC handling doing nothing except from responding with success result.
17
+
18
+ Sources:
19
+ - [Golang](https://github.com/anycable/anycable-go/blob/chore/benchmarking/cmd/rpc-bench/main.go)
20
+ - [Erlang](https://github.com/anycable/simple-cable-app/tree/master/benchmarks)
21
+
22
+ ## Erlang single connection
23
+
24
+ RPC type \ Number of clients | 1 | 10 | 50
25
+ --------------------------------|------|------|----
26
+ AnyCable RPC | 100 | 110 | 130
27
+ Noop RPC | 100 | 115 | 125
28
+
29
+ Erlang client definitely has problems(
30
+
31
+ Looks like HTTP2 streaming is working in _blocking mode_.
32
+
33
+ Requires investigation.
34
+
35
+ ## Erlycable connection pool (5-50)
36
+
37
+ RPC type \ Number of clients | 1 | 10 | 50
38
+ --------------------------------|------|------|----
39
+ AnyCable RPC | 100 | 800 | 1700
40
+ Noop RPC | 100 | 900 | 2700
41
+
42
+ ## Golang single connection
43
+
44
+ RPC type \ Number of clients | 1 | 10 | 50
45
+ --------------------------------|------|------|----
46
+ AnyCable RPC | 1600 | 2200 | 2400
47
+ Noop RPC with connection object building\* | 2200 | 3500 | 4000
48
+ Noop RPC | 3000 | 4600 | 5500
49
+
50
+ \* Only build Action Cable connection object without performing an action.
51
+
52
+ ## Golang connection pool (5-50)
53
+
54
+ RPC type \ Number of clients | 1 | 10 | 50
55
+ --------------------------------|------|------|----
56
+ AnyCable RPC | 1400 | 1500 | 1700
57
+ Noop RPC | 2100 | 3200 | 4000
@@ -10,7 +10,7 @@
10
10
 
11
11
  - Update `hosts` file and playbooks with required information (IPs, etc)
12
12
 
13
- - Prepare the _client_ instance: `ansible-playbook --extra-vars="prepare=True" benchmark.yml`
13
+ - Prepare the _client_ instance: `ansible-playbook --tags prepare benchmark.yml`
14
14
 
15
15
  ### Running benchmarks
16
16
 
@@ -5,17 +5,19 @@
5
5
  remote_user: ubuntu
6
6
  gather_facts: False
7
7
  vars:
8
- server_host: '172.31.22.14'
8
+ server_host: '172.31.17.82'
9
9
  hostname: ws-bench-client
10
- local_ips: ['172.31.21.241', '172.31.21.242', '172.31.21.243', '172.31.21.244']
11
- local_ips_str: '-l 172.31.21.241 -l 172.31.21.242 -l 172.31.21.243 -l 172.31.21.244'
12
- steps: 10
10
+ local_ips: ['172.31.17.191', '172.31.17.192', '172.31.17.193', '172.31.17.194']
11
+ local_ips_str: '-l 172.31.17.191 -l 172.31.17.192 -l 172.31.17.193 -l 172.31.17.194'
12
+ steps: 20
13
13
  step_size: 1000
14
- sample_size: 40
14
+ sample_size: 100
15
+ concurrency: 8
16
+ payload_size: 200
15
17
  prepare: False
16
18
  tasks:
17
19
  - name: Prepare the machine
18
- when: prepare
20
+ tags: prepare
19
21
  block:
20
22
  - hostname:
21
23
  name: "{{ hostname }}"
@@ -25,16 +27,41 @@
25
27
  state: present
26
28
  - shell: ip addr add {{ item }}/20 dev eth0
27
29
  with_items: "{{ local_ips }}"
30
+
31
+ - name: Print Action Cable command
32
+ debug: msg="bin/websocket-bench broadcast {{ local_ips_str }} --concurrent {{ concurrency }} --sample-size {{ sample_size }} --step-size {{ step_size }} --payload-padding {{ payload_size }} --total-steps {{ steps }} --origin http://0.0.0.0 ws://{{ server_host }}:3334/cable --server-type=actioncable"
33
+ tags: action_cable
34
+
28
35
  - name: Action Cable benchmark
29
36
  become_user: deplo
30
- shell: bin/websocket-bench broadcast {{ local_ips_str }} --concurrent 4 --sample-size {{ sample_size }} --step-size {{ step_size }} --payload-padding 200 --total-steps {{ steps }} --origin http://0.0.0.0 ws://{{ server_host }}:3334/cable --server-type=actioncable
37
+ shell: bin/websocket-bench broadcast {{ local_ips_str }} --concurrent {{ concurrency }} --sample-size {{ sample_size }} --step-size {{ step_size }} --payload-padding {{ payload_size }} --total-steps {{ steps }} --origin http://0.0.0.0 ws://{{ server_host }}:3334/cable --server-type=actioncable
31
38
  register: bench
32
39
  tags: action_cable
33
40
  args:
34
41
  chdir: /webapps/anycable_bench
35
42
  ignore_errors: yes
36
43
 
37
- - name: Benchmark results
44
+ - name: Print Plezi command
45
+ debug: msg="bin/websocket-bench broadcast {{ local_ips_str }} --concurrent {{ concurrency }} --sample-size {{ sample_size }} --step-size {{ step_size }} --payload-padding {{ payload_size }} --total-steps {{ steps }} ws://{{ server_host }}:3334/cable"
46
+ tags: plezi
47
+
48
+ - name: Plezi benchmark
49
+ become_user: deplo
50
+ shell: bin/websocket-bench broadcast {{ local_ips_str }} --concurrent {{ concurrency }} --sample-size {{ sample_size }} --step-size {{ step_size }} --payload-padding {{ payload_size }} --total-steps {{ steps }} ws://{{ server_host }}:3334/cable
51
+ register: bench
52
+ tags: plezi
53
+ args:
54
+ chdir: /webapps/anycable_bench
55
+ ignore_errors: yes
56
+
57
+ - name: Benchmark results (stdout)
38
58
  debug: var=bench.stdout_lines
39
59
  tags:
40
60
  - action_cable
61
+ - plezi
62
+
63
+ - name: Benchmark results (stderr)
64
+ debug: var=bench.stderr_lines
65
+ tags:
66
+ - action_cable
67
+ - plezi
@@ -1,5 +1,5 @@
1
1
  [benchmark]
2
- ec2-52-208-189-15.eu-west-1.compute.amazonaws.com ansible_ssh_private_key_file=/Users/palkan/.ssh/macos-dev
2
+ ec2-52-19-57-142.eu-west-1.compute.amazonaws.com ansible_ssh_private_key_file=/Users/palkan/.ssh/macos-dev
3
3
 
4
4
  [servers]
5
- ec2-52-211-15-119.eu-west-1.compute.amazonaws.com ansible_ssh_private_key_file=/Users/palkan/.ssh/macos-dev
5
+ ec2-34-252-33-102.eu-west-1.compute.amazonaws.com ansible_ssh_private_key_file=/Users/palkan/.ssh/macos-dev
@@ -5,25 +5,32 @@
5
5
  remote_user: ubuntu
6
6
  gather_facts: False
7
7
  vars:
8
- rails_webc: 8
8
+ web_concurrency: 8
9
9
  tasks:
10
10
  - name: Kill servers
11
11
  shell: pid=$(lsof -i:{{item}} -t); kill -TERM $pid || kill -KILL $pid
12
12
  tags:
13
13
  - action_cable
14
14
  - anycable
15
+ - plezi
15
16
  with_items:
16
17
  - "3334"
17
18
  ignore_errors: true
18
19
  - name: Run Action Cable
19
20
  become_user: deplo
20
21
  tags: action_cable
21
- shell: WEB_CONCURRENCY={{ rails_webc }} bundle exec rails s -p 3334 -e production
22
+ shell: WEB_CONCURRENCY={{ web_concurrency }} bundle exec rails s -p 3334 -e production
22
23
  args:
23
24
  chdir: /webapps/anycable_bench/ruby/action-cable-server
24
25
  - name: Run Anycable Go
25
26
  become_user: deplo
26
27
  tags: anycable
27
- shell: bundle exec anycable
28
+ shell: ANYCABLE_GO_BIN="anycable-go-0.6.0" ANYCABLE_PORT="3334" bundle exec bin/anycable
28
29
  args:
29
- chdir: /webapps/anycable_bench/ruby/action-cable-server/bin
30
+ chdir: /webapps/anycable_bench/ruby/action-cable-server
31
+ - name: Run Iodine/Plezi
32
+ become_user: deplo
33
+ tags: plezi
34
+ shell: iodine -p 3334
35
+ args:
36
+ chdir: /webapps/anycable_bench/ruby/plezi-iodine
@@ -0,0 +1,76 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler/inline"
4
+
5
+ # This reproduction script is based on `anyt` gem
6
+ # (https://github.com/anycable/anyt).
7
+ #
8
+ # See more test examples here:
9
+ # https://github.com/anycable/anyt/tree/master/lib/anyt/tests
10
+
11
+ gemfile(true) do
12
+ source "https://rubygems.org"
13
+
14
+ gem "anyt"
15
+ end
16
+
17
+ require "anyt"
18
+ require "anyt/cli"
19
+ require "anycable-rails"
20
+
21
+ # WebSocket server url
22
+ ENV['ANYT_TARGET_URL'] ||= "ws://localhost:8080/cable"
23
+
24
+ # Command to launch WebSocket server.
25
+ # Comment this line if you want to run WebSocket server manually
26
+ ENV['ANYT_COMMAND'] ||= "anycable-go"
27
+
28
+ ActionCable.server.config.logger = Rails.logger = Anycable.logger
29
+
30
+ # Test scenario
31
+ feature "issue_xyz" do
32
+ # This block defines an anonymous channel to test against
33
+ channel do
34
+ # def subscribed
35
+ # stream_from "a"
36
+ # end
37
+ #
38
+ # def perform(data)
39
+ # # ...
40
+ # end
41
+ end
42
+
43
+ # You can use minitest/spec features here
44
+ before do
45
+ # `channel` contains identifier of the anonymous channel defined above
46
+ subscribe_request = { command: "subscribe", identifier: { channel: channel }.to_json }
47
+
48
+ # `client` represents a websocket client connected to a server
49
+ client.send(subscribe_request)
50
+
51
+ ack = {
52
+ "identifier" => { channel: channel }.to_json, "type" => "confirm_subscription"
53
+ }
54
+
55
+ # `receive` method returns the first message from the incoming messages queue;
56
+ # waits 5s when no messages available
57
+ assert_equal ack, client.receive
58
+ end
59
+
60
+ # describe you bug scenario here
61
+ scenario %{
62
+ Should work
63
+ } do
64
+ # ...
65
+ end
66
+ end
67
+
68
+ # Required setup/teardown
69
+ begin
70
+ Anyt::RPC.start
71
+ Anyt::Command.run if Anyt.config.command
72
+ Anyt::Tests.run
73
+ ensure
74
+ Anyt::Command.stop if Anyt.config.command
75
+ Anyt::RPC.stop
76
+ end
@@ -47,7 +47,8 @@ module Anycable
47
47
  @pubsub ||= PubSub.new
48
48
  end
49
49
 
50
- # Broadcast message to the channel
50
+ # Raw broadcast message to the channel, sends only string!
51
+ # To send hash or object use ActionCable.server.broadcast instead!
51
52
  def broadcast(channel, payload)
52
53
  pubsub.broadcast(channel, payload)
53
54
  end
@@ -15,7 +15,7 @@ module Anycable
15
15
 
16
16
  # Handle connection request from WebSocket server
17
17
  def connect(request, _unused_call)
18
- logger.debug("RPC Connect: #{request}")
18
+ logger.debug("RPC Connect: #{request.inspect}")
19
19
 
20
20
  socket = build_socket(env: rack_env(request))
21
21
 
@@ -35,7 +35,7 @@ module Anycable
35
35
  end
36
36
 
37
37
  def disconnect(request, _unused_call)
38
- logger.debug("RPC Disonnect: #{request}")
38
+ logger.debug("RPC Disconnect: #{request.inspect}")
39
39
 
40
40
  socket = build_socket(env: rack_env(request))
41
41
 
@@ -53,7 +53,7 @@ module Anycable
53
53
  end
54
54
 
55
55
  def command(message, _unused_call)
56
- logger.debug("RPC Command: #{message}")
56
+ logger.debug("RPC Command: #{message.inspect}")
57
57
 
58
58
  socket = build_socket
59
59
 
@@ -96,7 +96,7 @@ module Anycable
96
96
  end
97
97
 
98
98
  def build_socket(**options)
99
- Anycable::Socket.new(**options)
99
+ Anycable::Socket.new(options)
100
100
  end
101
101
 
102
102
  def build_headers(headers)
@@ -14,6 +14,7 @@ module Anycable
14
14
  @grpc_server ||= build_server
15
15
 
16
16
  Anycable.logger.info "RPC server is listening on #{Anycable.config.rpc_host}"
17
+ Anycable.logger.info "Broadcasting Redis channel: #{Anycable.config.redis_channel}"
17
18
  grpc_server.run_till_terminated
18
19
  end
19
20
 
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Anycable
4
- VERSION = "0.5.0"
4
+ VERSION = "0.5.1"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: anycable
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.0
4
+ version: 0.5.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - palkan
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-10-21 00:00:00.000000000 Z
11
+ date: 2018-06-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: anyway_config
@@ -118,16 +118,16 @@ dependencies:
118
118
  name: rubocop
119
119
  requirement: !ruby/object:Gem::Requirement
120
120
  requirements:
121
- - - ">="
121
+ - - "~>"
122
122
  - !ruby/object:Gem::Version
123
- version: '0.50'
123
+ version: 0.57.1
124
124
  type: :development
125
125
  prerelease: false
126
126
  version_requirements: !ruby/object:Gem::Requirement
127
127
  requirements:
128
- - - ">="
128
+ - - "~>"
129
129
  - !ruby/object:Gem::Version
130
- version: '0.50'
130
+ version: 0.57.1
131
131
  - !ruby/object:Gem::Dependency
132
132
  name: simplecov
133
133
  requirement: !ruby/object:Gem::Requirement
@@ -187,6 +187,8 @@ files:
187
187
  - assets/evlms.png
188
188
  - benchmarks/.gitignore
189
189
  - benchmarks/2017-02-12.md
190
+ - benchmarks/2018-03-04.md
191
+ - benchmarks/2018-05-27-rpc-bench.md
190
192
  - benchmarks/HowTo.md
191
193
  - benchmarks/ansible.cfg
192
194
  - benchmarks/benchmark.yml
@@ -195,6 +197,7 @@ files:
195
197
  - bin/console
196
198
  - bin/setup
197
199
  - circle.yml
200
+ - etc/bug_report_template.rb
198
201
  - lib/anycable.rb
199
202
  - lib/anycable/config.rb
200
203
  - lib/anycable/handler/exceptions_handling.rb
@@ -226,7 +229,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
226
229
  version: '0'
227
230
  requirements: []
228
231
  rubyforge_project:
229
- rubygems_version: 2.6.13
232
+ rubygems_version: 2.7.6
230
233
  signing_key:
231
234
  specification_version: 4
232
235
  summary: Polyglot replacement for ActionCable server