opal 0.11.0.rc1 → 0.11.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (493) hide show
  1. checksums.yaml +4 -4
  2. data/.jshintrc +1 -1
  3. data/.travis.yml +14 -2
  4. data/CHANGELOG.md +30 -5
  5. data/HACKING.md +2 -2
  6. data/README.md +4 -5
  7. data/appveyor.yml +3 -4
  8. data/bin +1 -0
  9. data/docs/headless_chrome.md +105 -0
  10. data/docs/rspec.md +2 -19
  11. data/{bin → exe}/opal +0 -0
  12. data/{bin → exe}/opal-build +0 -0
  13. data/{bin → exe}/opal-mspec +0 -0
  14. data/{bin → exe}/opal-repl +0 -0
  15. data/lib/opal.rb +1 -0
  16. data/lib/opal/ast/builder.rb +0 -4
  17. data/lib/opal/builder.rb +69 -15
  18. data/lib/opal/builder_processors.rb +8 -7
  19. data/lib/opal/cli.rb +1 -1
  20. data/lib/opal/cli_options.rb +1 -1
  21. data/lib/opal/cli_runners.rb +1 -1
  22. data/lib/opal/cli_runners/applescript.rb +0 -1
  23. data/lib/opal/cli_runners/chrome.js +135 -0
  24. data/lib/opal/cli_runners/chrome.rb +100 -0
  25. data/lib/opal/cli_runners/nashorn.rb +0 -1
  26. data/lib/opal/cli_runners/node_modules/.bin/chrome-remote-interface +1 -0
  27. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/LICENSE +18 -0
  28. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/README.md +843 -0
  29. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/bin/client.js +326 -0
  30. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/chrome-remote-interface.js +11 -0
  31. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/index.js +39 -0
  32. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/api.js +84 -0
  33. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/chrome.js +289 -0
  34. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/defaults.js +4 -0
  35. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/devtools.js +245 -0
  36. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/external-request.js +23 -0
  37. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/protocol.json +13303 -0
  38. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/lib/websocket-wrapper.js +32 -0
  39. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/package.json +128 -0
  40. data/lib/opal/cli_runners/node_modules/chrome-remote-interface/webpack.config.js +55 -0
  41. data/lib/opal/cli_runners/node_modules/commander/Readme.md +195 -0
  42. data/lib/opal/cli_runners/node_modules/commander/index.js +851 -0
  43. data/lib/opal/cli_runners/node_modules/commander/package.json +92 -0
  44. data/lib/opal/cli_runners/node_modules/ultron/LICENSE +22 -0
  45. data/lib/opal/cli_runners/node_modules/ultron/index.js +138 -0
  46. data/lib/opal/cli_runners/node_modules/ultron/package.json +112 -0
  47. data/lib/opal/cli_runners/node_modules/ws/LICENSE +21 -0
  48. data/lib/opal/cli_runners/node_modules/ws/README.md +259 -0
  49. data/lib/opal/cli_runners/node_modules/ws/SECURITY.md +33 -0
  50. data/lib/opal/cli_runners/node_modules/ws/index.js +15 -0
  51. data/lib/opal/cli_runners/node_modules/ws/lib/BufferUtil.fallback.js +56 -0
  52. data/lib/opal/cli_runners/node_modules/ws/lib/BufferUtil.js +15 -0
  53. data/lib/opal/cli_runners/node_modules/ws/lib/ErrorCodes.js +28 -0
  54. data/lib/opal/cli_runners/node_modules/ws/lib/EventTarget.js +158 -0
  55. data/lib/opal/cli_runners/node_modules/ws/lib/Extensions.js +69 -0
  56. data/lib/opal/cli_runners/node_modules/ws/lib/PerMessageDeflate.js +339 -0
  57. data/lib/opal/cli_runners/node_modules/ws/lib/Receiver.js +520 -0
  58. data/lib/opal/cli_runners/node_modules/ws/lib/Sender.js +438 -0
  59. data/lib/opal/cli_runners/node_modules/ws/lib/Validation.fallback.js +9 -0
  60. data/lib/opal/cli_runners/node_modules/ws/lib/Validation.js +17 -0
  61. data/lib/opal/cli_runners/node_modules/ws/lib/WebSocket.js +705 -0
  62. data/lib/opal/cli_runners/node_modules/ws/lib/WebSocketServer.js +336 -0
  63. data/lib/opal/cli_runners/node_modules/ws/package.json +122 -0
  64. data/lib/opal/cli_runners/nodejs.rb +0 -1
  65. data/lib/opal/cli_runners/package.json +5 -0
  66. data/lib/opal/cli_runners/server.rb +0 -1
  67. data/lib/opal/compiler.rb +8 -18
  68. data/lib/opal/deprecations.rb +1 -1
  69. data/lib/opal/eof_content.rb +36 -0
  70. data/lib/opal/nodes.rb +0 -1
  71. data/lib/opal/nodes/args/kwarg.rb +8 -6
  72. data/lib/opal/nodes/args/kwoptarg.rb +12 -6
  73. data/lib/opal/nodes/call.rb +3 -2
  74. data/lib/opal/nodes/call_special.rb +10 -1
  75. data/lib/opal/nodes/definitions.rb +5 -3
  76. data/lib/opal/nodes/helpers.rb +4 -8
  77. data/lib/opal/nodes/literal.rb +13 -1
  78. data/lib/opal/nodes/logic.rb +19 -32
  79. data/lib/opal/nodes/node_with_args.rb +1 -1
  80. data/lib/opal/nodes/scope.rb +1 -0
  81. data/lib/opal/nodes/super.rb +0 -4
  82. data/lib/opal/nodes/variables.rb +11 -0
  83. data/lib/opal/parser.rb +24 -19
  84. data/lib/opal/path_reader.rb +17 -4
  85. data/lib/opal/rewriter.rb +5 -1
  86. data/lib/opal/rewriters/base.rb +37 -34
  87. data/lib/opal/rewriters/binary_operator_assignment.rb +0 -3
  88. data/lib/opal/rewriters/for_rewriter.rb +93 -0
  89. data/lib/opal/rewriters/hashes/key_duplicates_rewriter.rb +58 -0
  90. data/lib/opal/rewriters/js_reserved_words.rb +5 -8
  91. data/lib/opal/rewriters/logical_operator_assignment.rb +0 -1
  92. data/lib/opal/simple_server.rb +1 -0
  93. data/lib/opal/util.rb +1 -1
  94. data/lib/opal/version.rb +1 -1
  95. data/opal.gemspec +32 -30
  96. data/opal/corelib/array.rb +53 -30
  97. data/opal/corelib/boolean.rb +11 -3
  98. data/opal/corelib/comparable.rb +16 -0
  99. data/opal/corelib/constants.rb +3 -3
  100. data/opal/corelib/enumerable.rb +48 -1
  101. data/opal/corelib/file.rb +54 -11
  102. data/opal/corelib/hash.rb +98 -0
  103. data/opal/corelib/io.rb +2 -2
  104. data/opal/corelib/kernel.rb +28 -11
  105. data/opal/corelib/marshal/read_buffer.rb +288 -150
  106. data/opal/corelib/marshal/write_buffer.rb +27 -2
  107. data/opal/corelib/nil.rb +11 -3
  108. data/opal/corelib/number.rb +90 -20
  109. data/opal/corelib/numeric.rb +3 -3
  110. data/opal/corelib/random.rb +1 -1
  111. data/opal/corelib/range.rb +22 -22
  112. data/opal/corelib/regexp.rb +45 -4
  113. data/opal/corelib/runtime.js +25 -9
  114. data/opal/corelib/string.rb +1 -1
  115. data/opal/corelib/string/encoding.rb +21 -29
  116. data/opal/corelib/string/inheritance.rb +1 -1
  117. data/opal/corelib/struct.rb +0 -5
  118. data/opal/corelib/time.rb +1 -1
  119. data/stdlib/buffer/array.rb +4 -2
  120. data/stdlib/date.rb +46 -12
  121. data/stdlib/headless_chrome.rb +11 -0
  122. data/stdlib/nodejs/file.rb +36 -11
  123. data/stdlib/nodejs/io.rb +8 -0
  124. data/stdlib/nodejs/stacktrace.rb +116 -100
  125. data/stdlib/opal-builder.rb +1 -0
  126. data/stdlib/opal-platform.rb +6 -6
  127. data/stdlib/opal/platform.rb +2 -2
  128. data/stdlib/rbconfig.rb +1 -1
  129. data/stdlib/securerandom.rb +1 -1
  130. data/tasks/testing.rake +58 -26
  131. data/tasks/testing/opal_rspec_smoketest.Gemfile +5 -12
  132. metadata +64 -733
  133. data/lib/opal/cli_runners/phantom.js +0 -69
  134. data/lib/opal/cli_runners/phantomjs.rb +0 -29
  135. data/lib/opal/hike_path_finder.rb +0 -19
  136. data/lib/opal/nodes/for.rb +0 -75
  137. data/spec/README.md +0 -10
  138. data/spec/filters/bugs/array.rb +0 -16
  139. data/spec/filters/bugs/basicobject.rb +0 -13
  140. data/spec/filters/bugs/bigdecimal.rb +0 -146
  141. data/spec/filters/bugs/class.rb +0 -11
  142. data/spec/filters/bugs/comparable.rb +0 -5
  143. data/spec/filters/bugs/complex.rb +0 -3
  144. data/spec/filters/bugs/date.rb +0 -94
  145. data/spec/filters/bugs/enumerable.rb +0 -43
  146. data/spec/filters/bugs/enumerator.rb +0 -40
  147. data/spec/filters/bugs/exception.rb +0 -72
  148. data/spec/filters/bugs/file.rb +0 -8
  149. data/spec/filters/bugs/float.rb +0 -39
  150. data/spec/filters/bugs/hash.rb +0 -15
  151. data/spec/filters/bugs/inheritance.rb +0 -5
  152. data/spec/filters/bugs/integer.rb +0 -30
  153. data/spec/filters/bugs/io.rb +0 -8
  154. data/spec/filters/bugs/kernel.rb +0 -168
  155. data/spec/filters/bugs/language.rb +0 -190
  156. data/spec/filters/bugs/marshal.rb +0 -41
  157. data/spec/filters/bugs/method.rb +0 -60
  158. data/spec/filters/bugs/module.rb +0 -158
  159. data/spec/filters/bugs/numeric.rb +0 -8
  160. data/spec/filters/bugs/pathname.rb +0 -7
  161. data/spec/filters/bugs/proc.rb +0 -37
  162. data/spec/filters/bugs/random.rb +0 -7
  163. data/spec/filters/bugs/range.rb +0 -36
  164. data/spec/filters/bugs/rational.rb +0 -4
  165. data/spec/filters/bugs/regexp.rb +0 -158
  166. data/spec/filters/bugs/set.rb +0 -41
  167. data/spec/filters/bugs/singleton.rb +0 -6
  168. data/spec/filters/bugs/string.rb +0 -98
  169. data/spec/filters/bugs/stringscanner.rb +0 -71
  170. data/spec/filters/bugs/struct.rb +0 -4
  171. data/spec/filters/bugs/time.rb +0 -35
  172. data/spec/filters/bugs/unboundmethod.rb +0 -17
  173. data/spec/filters/unsupported/array.rb +0 -167
  174. data/spec/filters/unsupported/basicobject.rb +0 -14
  175. data/spec/filters/unsupported/bignum.rb +0 -55
  176. data/spec/filters/unsupported/class.rb +0 -4
  177. data/spec/filters/unsupported/delegator.rb +0 -5
  178. data/spec/filters/unsupported/enumerable.rb +0 -11
  179. data/spec/filters/unsupported/enumerator.rb +0 -13
  180. data/spec/filters/unsupported/file.rb +0 -4
  181. data/spec/filters/unsupported/fixnum.rb +0 -14
  182. data/spec/filters/unsupported/float.rb +0 -46
  183. data/spec/filters/unsupported/freeze.rb +0 -75
  184. data/spec/filters/unsupported/hash.rb +0 -43
  185. data/spec/filters/unsupported/integer.rb +0 -3
  186. data/spec/filters/unsupported/kernel.rb +0 -32
  187. data/spec/filters/unsupported/language.rb +0 -22
  188. data/spec/filters/unsupported/marshal.rb +0 -46
  189. data/spec/filters/unsupported/matchdata.rb +0 -33
  190. data/spec/filters/unsupported/math.rb +0 -3
  191. data/spec/filters/unsupported/pathname.rb +0 -3
  192. data/spec/filters/unsupported/privacy.rb +0 -279
  193. data/spec/filters/unsupported/proc.rb +0 -3
  194. data/spec/filters/unsupported/random.rb +0 -4
  195. data/spec/filters/unsupported/range.rb +0 -7
  196. data/spec/filters/unsupported/regexp.rb +0 -69
  197. data/spec/filters/unsupported/set.rb +0 -4
  198. data/spec/filters/unsupported/singleton.rb +0 -6
  199. data/spec/filters/unsupported/string.rb +0 -546
  200. data/spec/filters/unsupported/struct.rb +0 -6
  201. data/spec/filters/unsupported/symbol.rb +0 -20
  202. data/spec/filters/unsupported/taint.rb +0 -30
  203. data/spec/filters/unsupported/thread.rb +0 -7
  204. data/spec/filters/unsupported/time.rb +0 -202
  205. data/spec/lib/builder_processors_spec.rb +0 -27
  206. data/spec/lib/builder_spec.rb +0 -89
  207. data/spec/lib/cli_runners/phantomjs_spec.rb +0 -39
  208. data/spec/lib/cli_spec.rb +0 -240
  209. data/spec/lib/compiler/call_spec.rb +0 -732
  210. data/spec/lib/compiler_spec.rb +0 -294
  211. data/spec/lib/config_spec.rb +0 -110
  212. data/spec/lib/dependency_resolver_spec.rb +0 -40
  213. data/spec/lib/deprecations_spec.rb +0 -16
  214. data/spec/lib/fixtures/complex_sprockets.js.rb.erb +0 -4
  215. data/spec/lib/fixtures/file_with_directives.js +0 -2
  216. data/spec/lib/fixtures/jst_file.js.jst +0 -1
  217. data/spec/lib/fixtures/no_requires.rb +0 -1
  218. data/spec/lib/fixtures/opal_file.rb +0 -2
  219. data/spec/lib/fixtures/require_tree_test.rb +0 -3
  220. data/spec/lib/fixtures/required_file.js +0 -1
  221. data/spec/lib/fixtures/required_tree_test/required_file1.rb +0 -1
  222. data/spec/lib/fixtures/required_tree_test/required_file2.rb +0 -1
  223. data/spec/lib/fixtures/requires.rb +0 -7
  224. data/spec/lib/fixtures/source_location_test.rb +0 -7
  225. data/spec/lib/fixtures/source_map.rb +0 -1
  226. data/spec/lib/fixtures/source_map/subfolder/other_file.rb +0 -1
  227. data/spec/lib/fixtures/sprockets_file.js.rb +0 -3
  228. data/spec/lib/fixtures/sprockets_require_tree_test.rb +0 -3
  229. data/spec/lib/hike_path_finder_spec.rb +0 -23
  230. data/spec/lib/path_reader_spec.rb +0 -36
  231. data/spec/lib/paths_spec.rb +0 -18
  232. data/spec/lib/rewriters/binary_operator_assignment_spec.rb +0 -151
  233. data/spec/lib/rewriters/block_to_iter_spec.rb +0 -28
  234. data/spec/lib/rewriters/dot_js_syntax_spec.rb +0 -108
  235. data/spec/lib/rewriters/explicit_writer_return_spec.rb +0 -186
  236. data/spec/lib/rewriters/js_reserved_words_spec.rb +0 -116
  237. data/spec/lib/rewriters/logical_operator_assignment_spec.rb +0 -202
  238. data/spec/lib/rewriters/opal_engine_check_spec.rb +0 -82
  239. data/spec/lib/rewriters/rubyspec/filters_rewriter_spec.rb +0 -53
  240. data/spec/lib/shared/path_finder_shared.rb +0 -19
  241. data/spec/lib/shared/path_reader_shared.rb +0 -31
  242. data/spec/lib/simple_server_spec.rb +0 -54
  243. data/spec/lib/spec_helper.rb +0 -100
  244. data/spec/mspec-opal/formatters.rb +0 -236
  245. data/spec/mspec-opal/runner.rb +0 -173
  246. data/spec/opal/compiler/irb_spec.rb +0 -44
  247. data/spec/opal/core/arity_spec.rb +0 -142
  248. data/spec/opal/core/array/intersection_spec.rb +0 -38
  249. data/spec/opal/core/array/minus_spec.rb +0 -38
  250. data/spec/opal/core/array/select_spec.rb +0 -14
  251. data/spec/opal/core/array/set_range_to_array_spec.rb +0 -7
  252. data/spec/opal/core/array/union_spec.rb +0 -38
  253. data/spec/opal/core/array/uniq_spec.rb +0 -49
  254. data/spec/opal/core/date_spec.rb +0 -191
  255. data/spec/opal/core/enumerable/all_break_spec.rb +0 -5
  256. data/spec/opal/core/enumerable/any_break_spec.rb +0 -5
  257. data/spec/opal/core/enumerable/collect_break_spec.rb +0 -13
  258. data/spec/opal/core/enumerable/count_break_spec.rb +0 -5
  259. data/spec/opal/core/enumerable/detect_break_spec.rb +0 -5
  260. data/spec/opal/core/enumerable/drop_while_break_spec.rb +0 -5
  261. data/spec/opal/core/enumerable/each_slice_break.rb +0 -6
  262. data/spec/opal/core/enumerable/each_with_index_break_spec.rb +0 -5
  263. data/spec/opal/core/enumerable/each_with_object_break_spec.rb +0 -5
  264. data/spec/opal/core/enumerable/find_all_break_spec.rb +0 -5
  265. data/spec/opal/core/enumerable/find_index_break_spec.rb +0 -5
  266. data/spec/opal/core/enumerable/grep_break_spec.rb +0 -5
  267. data/spec/opal/core/enumerable/max_break_spec.rb +0 -5
  268. data/spec/opal/core/enumerable/max_by_break_spec.rb +0 -5
  269. data/spec/opal/core/enumerable/min_break_spec.rb +0 -5
  270. data/spec/opal/core/enumerable/min_by_break_spec.rb +0 -5
  271. data/spec/opal/core/enumerable/none_break_spec.rb +0 -5
  272. data/spec/opal/core/enumerable/one_break_spec.rb +0 -5
  273. data/spec/opal/core/enumerable/reduce_break_spec.rb +0 -5
  274. data/spec/opal/core/enumerable/take_while_break_spec.rb +0 -5
  275. data/spec/opal/core/enumerator/with_index_spec.rb +0 -6
  276. data/spec/opal/core/exception_spec.rb +0 -30
  277. data/spec/opal/core/fixtures/class.rb +0 -124
  278. data/spec/opal/core/fixtures/class_variables.rb +0 -0
  279. data/spec/opal/core/fixtures/constants.rb +0 -33
  280. data/spec/opal/core/fixtures/require_tree_files/file 1.rb +0 -1
  281. data/spec/opal/core/fixtures/require_tree_files/file 2.rb +0 -1
  282. data/spec/opal/core/fixtures/require_tree_files/file 3.rb +0 -1
  283. data/spec/opal/core/fixtures/require_tree_files/file 4.rb +0 -1
  284. data/spec/opal/core/fixtures/require_tree_files/file 5.rb +0 -1
  285. data/spec/opal/core/fixtures/require_tree_files/nested/nested 1.rb +0 -1
  286. data/spec/opal/core/fixtures/require_tree_files/nested/nested 2.rb +0 -1
  287. data/spec/opal/core/fixtures/require_tree_files/other/other 1.rb +0 -1
  288. data/spec/opal/core/fixtures/require_tree_with_dot/file 1.rb +0 -1
  289. data/spec/opal/core/fixtures/require_tree_with_dot/file 2.rb +0 -1
  290. data/spec/opal/core/fixtures/require_tree_with_dot/file 3.rb +0 -1
  291. data/spec/opal/core/fixtures/require_tree_with_dot/index.rb +0 -3
  292. data/spec/opal/core/hash/has_value_spec.rb +0 -13
  293. data/spec/opal/core/hash/internals_spec.rb +0 -332
  294. data/spec/opal/core/helpers_spec.rb +0 -14
  295. data/spec/opal/core/kernel/Array_spec.rb +0 -10
  296. data/spec/opal/core/kernel/at_exit_spec.rb +0 -70
  297. data/spec/opal/core/kernel/block_given_spec.rb +0 -30
  298. data/spec/opal/core/kernel/class_spec.rb +0 -6
  299. data/spec/opal/core/kernel/define_singleton_method_spec.rb +0 -21
  300. data/spec/opal/core/kernel/equal_value_spec.rb +0 -12
  301. data/spec/opal/core/kernel/extend_spec.rb +0 -21
  302. data/spec/opal/core/kernel/format_spec.rb +0 -122
  303. data/spec/opal/core/kernel/freeze_spec.rb +0 -15
  304. data/spec/opal/core/kernel/instance_eval_spec.rb +0 -28
  305. data/spec/opal/core/kernel/instance_variable_defined_spec.rb +0 -15
  306. data/spec/opal/core/kernel/instance_variable_get_spec.rb +0 -14
  307. data/spec/opal/core/kernel/instance_variable_set_spec.rb +0 -10
  308. data/spec/opal/core/kernel/instance_variables_spec.rb +0 -110
  309. data/spec/opal/core/kernel/loop_spec.rb +0 -23
  310. data/spec/opal/core/kernel/match_spec.rb +0 -5
  311. data/spec/opal/core/kernel/method_spec.rb +0 -31
  312. data/spec/opal/core/kernel/methods_spec.rb +0 -25
  313. data/spec/opal/core/kernel/nil_spec.rb +0 -7
  314. data/spec/opal/core/kernel/p_spec.rb +0 -15
  315. data/spec/opal/core/kernel/printf_spec.rb +0 -11
  316. data/spec/opal/core/kernel/proc_spec.rb +0 -13
  317. data/spec/opal/core/kernel/raise_spec.rb +0 -13
  318. data/spec/opal/core/kernel/rand_spec.rb +0 -19
  319. data/spec/opal/core/kernel/require_tree_spec.rb +0 -18
  320. data/spec/opal/core/kernel/respond_to_spec.rb +0 -44
  321. data/spec/opal/core/kernel/send_spec.rb +0 -56
  322. data/spec/opal/core/kernel/sprintf_spec.rb +0 -5
  323. data/spec/opal/core/language/arguments/mlhs_arg_spec.rb +0 -19
  324. data/spec/opal/core/language/class_spec.rb +0 -55
  325. data/spec/opal/core/language/constant_lookup_spec.rb +0 -38
  326. data/spec/opal/core/language/equal_spec.rb +0 -8
  327. data/spec/opal/core/language/fixtures/array.rb +0 -11
  328. data/spec/opal/core/language/fixtures/block.rb +0 -57
  329. data/spec/opal/core/language/fixtures/break.rb +0 -240
  330. data/spec/opal/core/language/fixtures/ensure.rb +0 -72
  331. data/spec/opal/core/language/fixtures/literal_lambda.rb +0 -7
  332. data/spec/opal/core/language/fixtures/metaclass.rb +0 -33
  333. data/spec/opal/core/language/fixtures/module.rb +0 -24
  334. data/spec/opal/core/language/fixtures/next.rb +0 -128
  335. data/spec/opal/core/language/fixtures/return.rb +0 -118
  336. data/spec/opal/core/language/fixtures/send.rb +0 -111
  337. data/spec/opal/core/language/fixtures/send_1.9.rb +0 -22
  338. data/spec/opal/core/language/fixtures/super.rb +0 -308
  339. data/spec/opal/core/language/fixtures/variables.rb +0 -58
  340. data/spec/opal/core/language/fixtures/yield.rb +0 -28
  341. data/spec/opal/core/language/heredoc_spec.rb +0 -42
  342. data/spec/opal/core/language/keyword_arguments_spec.rb +0 -11
  343. data/spec/opal/core/language/predefined_spec.rb +0 -138
  344. data/spec/opal/core/language/regexp_spec.rb +0 -20
  345. data/spec/opal/core/language/rescue_spec.rb +0 -18
  346. data/spec/opal/core/language/safe_navigator_spec.rb +0 -7
  347. data/spec/opal/core/language/send_spec.rb +0 -222
  348. data/spec/opal/core/language/string_spec.rb +0 -44
  349. data/spec/opal/core/language/ternary_operator_spec.rb +0 -20
  350. data/spec/opal/core/language/versions/array_1.9.rb +0 -39
  351. data/spec/opal/core/language/versions/block_1.9.rb +0 -0
  352. data/spec/opal/core/language/versions/break_1.9.rb +0 -0
  353. data/spec/opal/core/language/versions/case_1.9.rb +0 -20
  354. data/spec/opal/core/language/versions/def_2_0_spec.rb +0 -58
  355. data/spec/opal/core/language/versions/hash_1_9_spec.rb +0 -23
  356. data/spec/opal/core/language/versions/literal_lambda_1.9.rb +0 -143
  357. data/spec/opal/core/language/versions/not_1.9.rb +0 -22
  358. data/spec/opal/core/language/versions/send_1.9.rb +0 -241
  359. data/spec/opal/core/language/versions/symbol_1.9.rb +0 -15
  360. data/spec/opal/core/language/versions/variables_1.9.rb +0 -8
  361. data/spec/opal/core/language_spec.rb +0 -77
  362. data/spec/opal/core/marshal/dump_spec.rb +0 -53
  363. data/spec/opal/core/marshal/load_spec.rb +0 -7
  364. data/spec/opal/core/method/to_proc_spec.rb +0 -28
  365. data/spec/opal/core/module/alias_method_spec.rb +0 -28
  366. data/spec/opal/core/module/ancestors_spec.rb +0 -11
  367. data/spec/opal/core/module/append_features_spec.rb +0 -14
  368. data/spec/opal/core/module/attr_accessor_spec.rb +0 -26
  369. data/spec/opal/core/module/const_defined_spec.rb +0 -84
  370. data/spec/opal/core/module/const_get_spec.rb +0 -85
  371. data/spec/opal/core/module/const_missing_spec.rb +0 -17
  372. data/spec/opal/core/module/const_set_spec.rb +0 -64
  373. data/spec/opal/core/module/constants_spec.rb +0 -49
  374. data/spec/opal/core/module/fixtures/classes.rb +0 -444
  375. data/spec/opal/core/module/method_defined_spec.rb +0 -48
  376. data/spec/opal/core/module/method_lookup_spec.rb +0 -13
  377. data/spec/opal/core/module/module_function_spec.rb +0 -25
  378. data/spec/opal/core/module/name_spec.rb +0 -41
  379. data/spec/opal/core/module/public_method_defined_spec.rb +0 -18
  380. data/spec/opal/core/module/remove_const_spec.rb +0 -22
  381. data/spec/opal/core/module/undef_method_spec.rb +0 -66
  382. data/spec/opal/core/numeric/bit_and_spec.rb +0 -7
  383. data/spec/opal/core/numeric/bit_or_spec.rb +0 -8
  384. data/spec/opal/core/numeric/bit_xor_spec.rb +0 -6
  385. data/spec/opal/core/numeric/ceil_spec.rb +0 -8
  386. data/spec/opal/core/numeric/chr_spec.rb +0 -8
  387. data/spec/opal/core/numeric/comparison_spec.rb +0 -24
  388. data/spec/opal/core/numeric/complement_spec.rb +0 -8
  389. data/spec/opal/core/numeric/divide_spec.rb +0 -10
  390. data/spec/opal/core/numeric/eql_spec.rb +0 -9
  391. data/spec/opal/core/numeric/exponent_spec.rb +0 -33
  392. data/spec/opal/core/numeric/floor_spec.rb +0 -8
  393. data/spec/opal/core/numeric/gt_spec.rb +0 -11
  394. data/spec/opal/core/numeric/gte_spec.rb +0 -12
  395. data/spec/opal/core/numeric/integer_spec.rb +0 -9
  396. data/spec/opal/core/numeric/left_shift_spec.rb +0 -21
  397. data/spec/opal/core/numeric/lt_spec.rb +0 -11
  398. data/spec/opal/core/numeric/lte_spec.rb +0 -12
  399. data/spec/opal/core/numeric/minus_spec.rb +0 -8
  400. data/spec/opal/core/numeric/modulo_spec.rb +0 -19
  401. data/spec/opal/core/numeric/multiply_spec.rb +0 -9
  402. data/spec/opal/core/numeric/next_spec.rb +0 -9
  403. data/spec/opal/core/numeric/ord_spec.rb +0 -9
  404. data/spec/opal/core/numeric/plus_spec.rb +0 -8
  405. data/spec/opal/core/numeric/pred_spec.rb +0 -7
  406. data/spec/opal/core/numeric/right_shift_spec.rb +0 -25
  407. data/spec/opal/core/numeric/step_spec.rb +0 -11
  408. data/spec/opal/core/numeric/succ_spec.rb +0 -9
  409. data/spec/opal/core/numeric/times_spec.rb +0 -36
  410. data/spec/opal/core/numeric/to_f_spec.rb +0 -7
  411. data/spec/opal/core/numeric/to_i_spec.rb +0 -7
  412. data/spec/opal/core/numeric/to_json_spec.rb +0 -8
  413. data/spec/opal/core/numeric/to_s_spec.rb +0 -26
  414. data/spec/opal/core/numeric/uminus_spec.rb +0 -9
  415. data/spec/opal/core/numeric/upto_spec.rb +0 -19
  416. data/spec/opal/core/numeric/zero_spec.rb +0 -7
  417. data/spec/opal/core/object_id_spec.rb +0 -56
  418. data/spec/opal/core/proc/call_spec.rb +0 -21
  419. data/spec/opal/core/proc/element_reference_spec.rb +0 -21
  420. data/spec/opal/core/proc/proc_tricks_spec.rb +0 -7
  421. data/spec/opal/core/runtime/begin_spec.rb +0 -39
  422. data/spec/opal/core/runtime/block_spec.rb +0 -23
  423. data/spec/opal/core/runtime/bridged_classes_spec.rb +0 -123
  424. data/spec/opal/core/runtime/constants_spec.rb +0 -13
  425. data/spec/opal/core/runtime/donate_spec.rb +0 -53
  426. data/spec/opal/core/runtime/eval_spec.rb +0 -5
  427. data/spec/opal/core/runtime/is_a_spec.rb +0 -36
  428. data/spec/opal/core/runtime/main_methods_spec.rb +0 -27
  429. data/spec/opal/core/runtime/method_missing_spec.rb +0 -68
  430. data/spec/opal/core/runtime/method_spec.rb +0 -31
  431. data/spec/opal/core/runtime/operator_call_spec.rb +0 -13
  432. data/spec/opal/core/runtime/paren_spec.rb +0 -14
  433. data/spec/opal/core/runtime/rescue_spec.rb +0 -106
  434. data/spec/opal/core/runtime/return_spec.rb +0 -38
  435. data/spec/opal/core/runtime/singleton_class_spec.rb +0 -13
  436. data/spec/opal/core/runtime/super_spec.rb +0 -223
  437. data/spec/opal/core/runtime/truthy_spec.rb +0 -63
  438. data/spec/opal/core/runtime/variables_spec.rb +0 -20
  439. data/spec/opal/core/runtime_spec.rb +0 -58
  440. data/spec/opal/core/source_map_spec.rb +0 -49
  441. data/spec/opal/core/string_spec.rb +0 -32
  442. data/spec/opal/core/time_spec.rb +0 -38
  443. data/spec/opal/javascript_api_spec.rb +0 -16
  444. data/spec/opal/stdlib/erb/erb_spec.rb +0 -30
  445. data/spec/opal/stdlib/erb/inline_block.opalerb +0 -3
  446. data/spec/opal/stdlib/erb/quoted.opalerb +0 -1
  447. data/spec/opal/stdlib/erb/simple.opalerb +0 -1
  448. data/spec/opal/stdlib/js_spec.rb +0 -66
  449. data/spec/opal/stdlib/json/ext_spec.rb +0 -48
  450. data/spec/opal/stdlib/json/parse_spec.rb +0 -37
  451. data/spec/opal/stdlib/native/alias_native_spec.rb +0 -27
  452. data/spec/opal/stdlib/native/array_spec.rb +0 -11
  453. data/spec/opal/stdlib/native/each_spec.rb +0 -13
  454. data/spec/opal/stdlib/native/element_reference_spec.rb +0 -16
  455. data/spec/opal/stdlib/native/exposure_spec.rb +0 -33
  456. data/spec/opal/stdlib/native/ext_spec.rb +0 -19
  457. data/spec/opal/stdlib/native/hash_spec.rb +0 -67
  458. data/spec/opal/stdlib/native/initialize_spec.rb +0 -17
  459. data/spec/opal/stdlib/native/method_missing_spec.rb +0 -51
  460. data/spec/opal/stdlib/native/native_alias_spec.rb +0 -19
  461. data/spec/opal/stdlib/native/native_class_spec.rb +0 -18
  462. data/spec/opal/stdlib/native/native_module_spec.rb +0 -13
  463. data/spec/opal/stdlib/native/native_reader_spec.rb +0 -22
  464. data/spec/opal/stdlib/native/native_writer_spec.rb +0 -30
  465. data/spec/opal/stdlib/native/new_spec.rb +0 -92
  466. data/spec/opal/stdlib/native/struct_spec.rb +0 -12
  467. data/spec/opal/stdlib/promise/always_spec.rb +0 -49
  468. data/spec/opal/stdlib/promise/error_spec.rb +0 -15
  469. data/spec/opal/stdlib/promise/rescue_spec.rb +0 -53
  470. data/spec/opal/stdlib/promise/then_spec.rb +0 -79
  471. data/spec/opal/stdlib/promise/trace_spec.rb +0 -51
  472. data/spec/opal/stdlib/promise/value_spec.rb +0 -15
  473. data/spec/opal/stdlib/promise/when_spec.rb +0 -34
  474. data/spec/opal/stdlib/source_map_spec.rb +0 -8
  475. data/spec/opal/stdlib/strscan/scan_spec.rb +0 -11
  476. data/spec/opal/stdlib/template/paths_spec.rb +0 -10
  477. data/spec/opal/stdlib/thread/mutex_spec.rb +0 -40
  478. data/spec/opal/stdlib/thread/thread_queue_spec.rb +0 -32
  479. data/spec/opal/stdlib/thread/thread_spec.rb +0 -60
  480. data/spec/ruby_specs +0 -122
  481. data/spec/spec_helper.rb +0 -27
  482. data/spec/support/match_helpers.rb +0 -57
  483. data/spec/support/mspec_rspec_adapter.rb +0 -33
  484. data/spec/support/rewriters_helper.rb +0 -24
  485. data/stdlib/phantomjs.rb +0 -17
  486. data/tasks/testing/sprockets-phantomjs.js +0 -54
  487. data/test/nodejs/fixtures/hello.rb +0 -1
  488. data/test/nodejs/test_dir.rb +0 -17
  489. data/test/nodejs/test_file.rb +0 -87
  490. data/test/nodejs/test_io.rb +0 -18
  491. data/test/nodejs/test_opal_builder.rb +0 -12
  492. data/test/opal/test_keyword.rb +0 -590
  493. data/test/opal/unsupported_and_bugs.rb +0 -39
@@ -5,13 +5,7 @@ require 'source_map'
5
5
 
6
6
  module Opal
7
7
  module BuilderProcessors
8
- DEFAULT_PROCESSORS = []
9
-
10
8
  class Processor
11
- def self.inherited(processor)
12
- DEFAULT_PROCESSORS << processor
13
- end
14
-
15
9
  def initialize(source, filename, options = {})
16
10
  @source, @filename, @options = source, filename, options
17
11
  @requires = []
@@ -27,8 +21,10 @@ module Opal
27
21
  @extensions = extensions
28
22
  matches = extensions.join('|')
29
23
  matches = "(#{matches})" if extensions.size == 1
30
-
31
24
  @match_regexp = Regexp.new "\\.#{matches}#{REGEXP_END}"
25
+
26
+ ::Opal::Builder.register_processor(self, extensions)
27
+ nil
32
28
  end
33
29
 
34
30
  def self.extensions
@@ -112,6 +108,11 @@ module Opal
112
108
  def compiler_class
113
109
  ::Opal::Compiler
114
110
  end
111
+
112
+ # Also catch a files with missing extensions and nil.
113
+ def self.match? other
114
+ super or File.extname(other.to_s) == ''
115
+ end
115
116
  end
116
117
 
117
118
  class OpalERBProcessor < RubyProcessor
@@ -116,7 +116,7 @@ module Opal
116
116
 
117
117
  def show_sexp
118
118
  evals_or_file do |contents, filename|
119
- buffer = ::Parser::Source::Buffer.new(filename)
119
+ buffer = ::Opal::Source::Buffer.new(filename)
120
120
  buffer.source = contents
121
121
  sexp = Opal::Parser.default_parser.parse(buffer)
122
122
  puts sexp.inspect
@@ -81,7 +81,7 @@ module Opal
81
81
  options[:compile] = true
82
82
  end
83
83
 
84
- on('-R', '--runner RUNNER', %w[nodejs server phantomjs applescript nashorn], 'Choose the runner: nodejs (default), server') do |runner|
84
+ on('-R', '--runner RUNNER', %w[nodejs server applescript nashorn chrome], 'Choose the runner: nodejs (default), server, chrome') do |runner|
85
85
  options[:runner] = runner.to_sym
86
86
  end
87
87
 
@@ -20,7 +20,7 @@ module Opal
20
20
  end
21
21
 
22
22
  require 'opal/cli_runners/applescript'
23
- require 'opal/cli_runners/phantomjs'
24
23
  require 'opal/cli_runners/nodejs'
25
24
  require 'opal/cli_runners/server'
26
25
  require 'opal/cli_runners/nashorn'
26
+ require 'opal/cli_runners/chrome'
@@ -1,5 +1,4 @@
1
1
  # frozen_string_literal: true
2
- require 'opal/cli_runners'
3
2
 
4
3
  module Opal
5
4
  module CliRunners
@@ -0,0 +1,135 @@
1
+ var CDP = require("chrome-remote-interface");
2
+ var fs = require("fs");
3
+
4
+ // NOTE: the code above doesn't work on Windows
5
+ // and it doesn't support interactive stdin input (which is ok for our scenario)
6
+ var opal_code = fs.readFileSync("/dev/stdin").toString();
7
+
8
+ // Chrome can't handle huge data passed to `addScriptToEvaluateOnLoad`
9
+ // https://groups.google.com/a/chromium.org/forum/#!topic/chromium-discuss/U5qyeX_ydBo
10
+ // The only way is to create temporary files and pass them to chrome.
11
+ fs.writeFileSync("/tmp/chrome-opal.js", opal_code);
12
+ fs.writeFileSync("/tmp/chrome-opal.html", "" +
13
+ "<html>" +
14
+ "<head>" +
15
+ "<meta charset='utf-8'>" +
16
+ "<script src='chrome-opal.js'></script>" +
17
+ "</head>" +
18
+ "<body>" +
19
+ "</body>" +
20
+ "</html>"
21
+ );
22
+
23
+ var options = {
24
+ host: process.env.CHROME_HOST || 'localhost',
25
+ port: process.env.CHROME_PORT || 9222
26
+ };
27
+
28
+ CDP(options, function(client) {
29
+ var Page = client.Page,
30
+ Runtime = client.Runtime,
31
+ Console = client.Console;
32
+
33
+ Promise.all([
34
+ Console.enable(),
35
+ Page.enable(),
36
+ Runtime.enable(),
37
+ ]).then(function() {
38
+ // This hook catches only the first argument of `console.log`
39
+ // More advanced version Runtime.consoleAPICalled returns all arguments
40
+ // but all of them are not formatted, i.e. by calling
41
+ // console.log('string', [1, 2, 3], {a: 'b'})
42
+ // it returns the following data to the callback:
43
+ // {
44
+ // "type":"log",
45
+ // "args":[
46
+ // {
47
+ // "type":"string",
48
+ // "value":"string"
49
+ // },
50
+ // {
51
+ // "type":"object",
52
+ // "subtype":"array",
53
+ // "className":"Array",
54
+ // "description":"Array(3)",
55
+ // "objectId":"{\"injectedScriptId\":11,\"id\":1}",
56
+ // "preview":{
57
+ // "type":"object",
58
+ // "subtype":"array",
59
+ // "description":"Array(3)",
60
+ // "overflow":false,
61
+ // "properties":[
62
+ // {"name":"0","type":"number","value":"1"},
63
+ // {"name":"1","type":"number","value":"2"},
64
+ // {"name":"2","type":"number","value":"3"}
65
+ // ]
66
+ // }
67
+ // },
68
+ // {
69
+ // "type":"object",
70
+ // "className":"Object",
71
+ // "description":"Object",
72
+ // "objectId":"{\"injectedScriptId\":11,\"id\":2}",
73
+ // "preview":{
74
+ // "type":"object",
75
+ // "description":"Object",
76
+ // "overflow":false,
77
+ // "properties":[
78
+ // {"name":"a","type":"string","value":"b"}
79
+ // ]
80
+ // }
81
+ // }
82
+ // ],
83
+ // // ...
84
+ // }
85
+ // Supporting this format for complex data structure is challenging, feel free to contribute!
86
+ //
87
+ Console.messageAdded(function(console_message) {
88
+ process.stdout.write(console_message.message.text);
89
+ });
90
+
91
+ Runtime.exceptionThrown(function(exception) {
92
+ var exceptionDetails = exception.exceptionDetails,
93
+ properties = exceptionDetails.exception.preview.properties,
94
+ stackTrace = exceptionDetails.stackTrace.callFrames,
95
+ name, message, trace = [], i;
96
+
97
+
98
+ for (i = 0; i < properties.length; i++) {
99
+ var property = properties[i];
100
+
101
+ if (property.name == "name") {
102
+ name = property.value;
103
+ }
104
+
105
+ if (property.name == "message") {
106
+ message = property.value;
107
+ }
108
+ }
109
+
110
+ console.log(name + " : " + message);
111
+
112
+ for (i = 0; i < stackTrace.length; i++) {
113
+ var raw = stackTrace[i];
114
+
115
+ console.log(" at " + raw.functionName + " (" + raw.url + ":" + raw.lineNumber + ":" + raw.columnNumber + ")")
116
+ }
117
+
118
+ process.exit(1);
119
+ })
120
+
121
+ Page.loadEventFired(() => {
122
+ Runtime.evaluate({ expression: "window.OPAL_EXIT_CODE" }).then(function(output) {
123
+ client.close();
124
+
125
+ if (typeof(output.result) !== "undefined" && output.result.type === "number") {
126
+ process.exit(output.result.value);
127
+ } else {
128
+ process.exit(0);
129
+ }
130
+ })
131
+ });
132
+
133
+ Page.navigate({ url: 'file:///tmp/chrome-opal.html' })
134
+ });
135
+ });
@@ -0,0 +1,100 @@
1
+ # frozen_string_literal: true
2
+ require 'shellwords'
3
+ require 'socket'
4
+ require 'timeout'
5
+
6
+ module Opal
7
+ module CliRunners
8
+ class Chrome
9
+ SCRIPT_PATH = File.expand_path('../chrome.js', __FILE__).freeze
10
+
11
+ DEFAULT_CHROME_HOST = 'localhost'.freeze
12
+ DEFAULT_CHROME_PORT = 9222.freeze
13
+
14
+ def initialize(options)
15
+ @output = options.fetch(:output, $stdout)
16
+ end
17
+ attr_reader :output, :exit_status
18
+
19
+ def run(code, argv)
20
+ with_chrome_server do
21
+ cmd = [
22
+ 'env',
23
+ "CHROME_HOST=#{chrome_host}",
24
+ "CHROME_PORT=#{chrome_port}",
25
+ 'node',
26
+ SCRIPT_PATH,
27
+ ]
28
+
29
+ IO.popen(cmd, 'w', out: output) do |io|
30
+ io.write(code)
31
+ end
32
+
33
+ @exit_status = $?.exitstatus
34
+ end
35
+ end
36
+
37
+ private
38
+
39
+ def chrome_host
40
+ ENV['CHROME_HOST'] || DEFAULT_CHROME_HOST
41
+ end
42
+
43
+ def chrome_port
44
+ ENV['CHROME_PORT'] || DEFAULT_CHROME_PORT
45
+ end
46
+
47
+ def with_chrome_server
48
+ if chrome_server_running?
49
+ yield
50
+ else
51
+ run_chrome_server { yield }
52
+ end
53
+ end
54
+
55
+ def run_chrome_server
56
+ raise "Chrome server can be started only on localhost" if chrome_host != DEFAULT_CHROME_HOST
57
+
58
+ chrome_server_cmd = "#{chrome_executable} --headless --disable-gpu --remote-debugging-port=#{chrome_port} #{ENV['CHROME_OPTS']}"
59
+ puts chrome_server_cmd
60
+
61
+ chrome_pid = Process.spawn(chrome_server_cmd)
62
+
63
+ Timeout.timeout(1) do
64
+ loop do
65
+ break if chrome_server_running?
66
+ sleep 0.1
67
+ end
68
+ end
69
+
70
+ yield
71
+ rescue Timeout::Error
72
+ puts 'Failed to start chrome server'
73
+ puts 'Make sure that you have it installed and that its version is > 59'
74
+ ensure
75
+ Process.kill('HUP', chrome_pid) if chrome_pid
76
+ end
77
+
78
+ def chrome_server_running?
79
+ puts "Connecting to #{chrome_host}:#{chrome_port}..."
80
+ TCPSocket.new(chrome_host, chrome_port).close
81
+ true
82
+ rescue Errno::ECONNREFUSED, Errno::EADDRNOTAVAIL
83
+ false
84
+ end
85
+
86
+ def chrome_executable
87
+ ENV['GOOGLE_CHROME_BINARY'] || case RbConfig::CONFIG['host_os']
88
+ when /mswin|msys|mingw|cygwin|bccwin|wince|emc/
89
+ raise "Headless chrome is supported only by Mac OS and Linux"
90
+ when /darwin|mac os/
91
+ "/Applications/Google\\ Chrome.app/Contents/MacOS/Google\\ Chrome"
92
+ when /linux/
93
+ 'google-chrome-stable'
94
+ when /solaris|bsd/
95
+ raise "Headless chrome is supported only by Mac OS and Linux"
96
+ end
97
+ end
98
+ end
99
+ end
100
+ end
@@ -1,5 +1,4 @@
1
1
  # frozen_string_literal: true
2
- require 'opal/cli_runners'
3
2
  require 'opal/paths'
4
3
 
5
4
  module Opal
@@ -0,0 +1 @@
1
+ lib/opal/cli_runners/node_modules/.bin/../chrome-remote-interface/bin/client.js
@@ -0,0 +1,18 @@
1
+ Copyright (c) 2017 Andrea Cardaci <cyrus.and@gmail.com>
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining a copy of
4
+ this software and associated documentation files (the "Software"), to deal in
5
+ the Software without restriction, including without limitation the rights to
6
+ use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
7
+ the Software, and to permit persons to whom the Software is furnished to do so,
8
+ subject to the following conditions:
9
+
10
+ The above copyright notice and this permission notice shall be included in all
11
+ copies or substantial portions of the Software.
12
+
13
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
15
+ FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
16
+ COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
17
+ IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
18
+ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,843 @@
1
+ chrome-remote-interface [![Build Status](https://travis-ci.org/cyrus-and/chrome-remote-interface.svg?branch=master)](https://travis-ci.org/cyrus-and/chrome-remote-interface)
2
+ =======================
3
+
4
+ [Chrome Debugging Protocol] interface that helps to instrument Chrome (or any
5
+ other suitable [implementation](#implementations)) by providing a simple
6
+ abstraction of commands and notifications using a straightforward JavaScript
7
+ API.
8
+
9
+ This module is one of the many [third-party protocol clients][3rd-party].
10
+
11
+ [3rd-party]: https://developer.chrome.com/devtools/docs/debugging-clients#chrome-remote-interface
12
+
13
+ Sample API usage
14
+ ----------------
15
+
16
+ The following snippet loads `https://github.com` and dumps every request made:
17
+
18
+ ```js
19
+ const CDP = require('chrome-remote-interface');
20
+
21
+ CDP((client) => {
22
+ // extract domains
23
+ const {Network, Page} = client;
24
+ // setup handlers
25
+ Network.requestWillBeSent((params) => {
26
+ console.log(params.request.url);
27
+ });
28
+ Page.loadEventFired(() => {
29
+ client.close();
30
+ });
31
+ // enable events then start!
32
+ Promise.all([
33
+ Network.enable(),
34
+ Page.enable()
35
+ ]).then(() => {
36
+ return Page.navigate({url: 'https://github.com'});
37
+ }).catch((err) => {
38
+ console.error(err);
39
+ client.close();
40
+ });
41
+ }).on('error', (err) => {
42
+ // cannot connect to the remote endpoint
43
+ console.error(err);
44
+ });
45
+ ```
46
+
47
+ Find more examples in the [wiki], in particular notice how the above can be
48
+ rewritten using the [`async`/`await`][async-await-example] primitives.
49
+
50
+ [wiki]: https://github.com/cyrus-and/chrome-remote-interface/wiki
51
+ [async-await-example]: https://github.com/cyrus-and/chrome-remote-interface/wiki/Async-await-example
52
+
53
+ Installation
54
+ ------------
55
+
56
+ npm install chrome-remote-interface
57
+
58
+ Install globally (`-g`) to just use the [bundled client](#bundled-client).
59
+
60
+ Implementations
61
+ ---------------
62
+
63
+ This module should work with every application implementing the
64
+ [Chrome Debugging Protocol]. In particular, it has been tested against the
65
+ following implementations:
66
+
67
+ Implementation | Protocol version | [Protocol] | [List] | [New] | [Activate] | [Close] | [Version]
68
+ ---------------------------|--------------------|------------|--------|-------|------------|---------|-----------
69
+ [Google Chrome][1.1] | [tip-of-tree][1.2] | yes | yes | yes | yes | yes | yes
70
+ [Microsoft Edge][2.1] | [*partial*][2.2] | yes | yes | no | no | no | yes
71
+ [Node.js][3.1] ([v6.3.0]+) | [node][3.2] | yes | no | no | no | no | yes
72
+ [Safari (iOS)][4.1] | [*partial*][4.2] | no | yes | no | no | no | no
73
+
74
+ [1.1]: #chromechromium
75
+ [1.2]: https://chromedevtools.github.io/devtools-protocol/tot/
76
+
77
+ [2.1]: #edge
78
+ [2.2]: https://github.com/Microsoft/edge-diagnostics-adapter/wiki/Supported-features-and-API
79
+
80
+ [3.1]: #nodejs
81
+ [3.2]: https://chromedevtools.github.io/devtools-protocol/v8/
82
+
83
+ [4.1]: #safari-ios
84
+ [4.2]: http://trac.webkit.org/browser/trunk/Source/JavaScriptCore/inspector/protocol
85
+
86
+ [v6.3.0]: https://nodejs.org/en/blog/release/v6.3.0/
87
+
88
+ [Protocol]: #cdpprotocoloptions-callback
89
+ [List]: #cdplistoptions-callback
90
+ [New]: #cdpnewoptions-callback
91
+ [Activate]: #cdpactivateoptions-callback
92
+ [Close]: #cdpcloseoptions-callback
93
+ [Version]: #cdpversionoptions-callback
94
+
95
+ The meaning of *target* varies according to the implementation, for example,
96
+ each Chrome tab represents a target whereas for Node.js a target is the
97
+ currently inspected script.
98
+
99
+ Setup
100
+ -----
101
+
102
+ An instance of either Chrome itself or another implementation needs to be
103
+ running on a known port in order to use this module (defaults to
104
+ `localhost:9222`).
105
+
106
+ ### Chrome/Chromium
107
+
108
+ #### Desktop
109
+
110
+ Start Chrome with the `--remote-debugging-port` option, for example:
111
+
112
+ google-chrome --remote-debugging-port=9222
113
+
114
+ ##### Headless
115
+
116
+ Since version 59, additionally use the `--headless` option, for example:
117
+
118
+ google-chrome --headless --remote-debugging-port=9222
119
+
120
+ #### Android
121
+
122
+ Plug the device and enable the [port forwarding][adb], for example:
123
+
124
+ adb forward tcp:9222 localabstract:chrome_devtools_remote
125
+
126
+ [adb]: https://developer.chrome.com/devtools/docs/remote-debugging-legacy
127
+
128
+ ##### WebView
129
+
130
+ In order to be inspectable, a WebView must
131
+ be [configured for debugging][webview] and the corresponding process ID must be
132
+ known. There are several ways to obtain it, for example:
133
+
134
+ adb shell grep -a webview_devtools_remote /proc/net/unix
135
+
136
+ Finally, port forwarding can be enabled as follows:
137
+
138
+ adb forward tcp:9222 localabstract:webview_devtools_remote_<pid>
139
+
140
+ [webview]: https://developers.google.com/web/tools/chrome-devtools/remote-debugging/webviews#configure_webviews_for_debugging
141
+
142
+ ### Edge
143
+
144
+ Install and run the [Edge Diagnostics Adapter][edge-adapter].
145
+
146
+ [edge-adapter]: https://github.com/Microsoft/edge-diagnostics-adapter
147
+
148
+ ### Node.js
149
+
150
+ Start Node.js with the `--inspect` option, for example:
151
+
152
+ node --inspect=9222 script.js
153
+
154
+ ### Safari (iOS)
155
+
156
+ Install and run the [iOS WebKit Debug Proxy][iwdp].
157
+
158
+ [iwdp]: https://github.com/google/ios-webkit-debug-proxy
159
+
160
+ Bundled client
161
+ --------------
162
+
163
+ This module comes with a bundled client application that can be used to
164
+ interactively control a remote instance.
165
+
166
+ ### Target management
167
+
168
+ The bundled client exposes subcommands to interact with the HTTP frontend
169
+ (e.g., [List](#cdplistoptions-callback), [New](#cdpnewoptions-callback), etc.),
170
+ run with `--help` to display the list of available options.
171
+
172
+ Here are some examples:
173
+
174
+ ```javascript
175
+ $ chrome-remote-interface new 'http://example.com'
176
+ {
177
+ "description": "",
178
+ "devtoolsFrontendUrl": "/devtools/inspector.html?ws=localhost:9222/devtools/page/b049bb56-de7d-424c-a331-6ae44cf7ae01",
179
+ "id": "b049bb56-de7d-424c-a331-6ae44cf7ae01",
180
+ "thumbnailUrl": "/thumb/b049bb56-de7d-424c-a331-6ae44cf7ae01",
181
+ "title": "",
182
+ "type": "page",
183
+ "url": "http://example.com/",
184
+ "webSocketDebuggerUrl": "ws://localhost:9222/devtools/page/b049bb56-de7d-424c-a331-6ae44cf7ae01"
185
+ }
186
+ $ chrome-remote-interface close 'b049bb56-de7d-424c-a331-6ae44cf7ae01'
187
+ ```
188
+
189
+ ### Inspection
190
+
191
+ Using the `inspect` subcommand it is possible to
192
+ perform [command execution](#clientdomainmethodparams-callback)
193
+ and [event binding](#clientdomaineventcallback) in a REPL fashion. But unlike
194
+ the regular API the callbacks are overridden to conveniently display the result
195
+ of the commands and the message of the events. Also, the event binding is
196
+ simplified here, executing a shorthand method (e.g., `Page.loadEventFired()`)
197
+ toggles the event registration.
198
+
199
+ Remember that the REPL interface provides completion.
200
+
201
+ Here is a sample session:
202
+
203
+ ```javascript
204
+ $ chrome-remote-interface inspect
205
+ >>> Runtime.evaluate({expression: 'window.location.toString()'})
206
+ { result:
207
+ { result:
208
+ { type: 'string',
209
+ value: 'https://www.google.it/_/chrome/newtab?espv=2&ie=UTF-8' },
210
+ wasThrown: false } }
211
+ >>> Page.enable()
212
+ { result: {} }
213
+ >>> Page.loadEventFired() // registered
214
+ { 'Page.loadEventFired': true }
215
+ >>> Page.loadEventFired() // unregistered
216
+ { 'Page.loadEventFired': false }
217
+ >>> Page.loadEventFired() // registered
218
+ { 'Page.loadEventFired': true }
219
+ >>> Page.navigate({url: 'https://github.com'})
220
+ { result: { frameId: '28677.1' } }
221
+ { 'Page.loadEventFired': { timestamp: 21385.383076 } }
222
+ >>> Runtime.evaluate({expression: 'window.location.toString()'})
223
+ { result:
224
+ { result: { type: 'string', value: 'https://github.com/' },
225
+ wasThrown: false } }
226
+ ```
227
+
228
+ #### Event filtering
229
+
230
+ To reduce the amount of data displayed by the event listeners it is possible to
231
+ provide a filter function. In this example only the resource URL is shown:
232
+
233
+ ```javascript
234
+ $ chrome-remote-interface inspect
235
+ >>> Network.enable()
236
+ { result: {} }
237
+ >>> Network.requestWillBeSent(params => params.request.url)
238
+ { 'Network.requestWillBeSent': 'params => params.request.url' }
239
+ >>> Page.navigate({url: 'https://www.wikipedia.org'})
240
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/' }
241
+ { result: { frameId: '5530.1' } }
242
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/img/Wikipedia_wordmark.png' }
243
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/img/Wikipedia-logo-v2.png' }
244
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/js/index-3b68787aa6.js' }
245
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/js/gt-ie9-c84bf66d33.js' }
246
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/img/sprite-bookshelf_icons.png?16ed124e8ca7c5ce9d463e8f99b2064427366360' }
247
+ { 'Network.requestWillBeSent': 'https://www.wikipedia.org/portal/wikipedia.org/assets/img/sprite-project-logos.png?9afc01c5efe0a8fb6512c776955e2ad3eb48fbca' }
248
+ ```
249
+
250
+ Embedded documentation
251
+ ----------------------
252
+
253
+ In both the REPL and the regular API every object of the protocol is *decorated*
254
+ with the meta information found within the descriptor. In addition The
255
+ `category` field is added, which determines if the member is a `command`, an
256
+ `event` or a `type`.
257
+
258
+ For example to learn how to call `Page.navigate`:
259
+
260
+ ```javascript
261
+ >>> Page.navigate
262
+ { [Function]
263
+ category: 'command',
264
+ parameters: { url: { type: 'string', description: 'URL to navigate the page to.' } },
265
+ returns:
266
+ [ { name: 'frameId',
267
+ '$ref': 'FrameId',
268
+ hidden: true,
269
+ description: 'Frame id that will be navigated.' } ],
270
+ description: 'Navigates current page to the given URL.',
271
+ handlers: [ 'browser', 'renderer' ] }
272
+ ```
273
+
274
+ To learn about the parameters returned by the `Network.requestWillBeSent` event:
275
+
276
+ ```javascript
277
+ >>> Network.requestWillBeSent
278
+ { [Function]
279
+ category: 'event',
280
+ description: 'Fired when page is about to send HTTP request.',
281
+ parameters:
282
+ { requestId: { '$ref': 'RequestId', description: 'Request identifier.' },
283
+ frameId:
284
+ { '$ref': 'Page.FrameId',
285
+ description: 'Frame identifier.',
286
+ hidden: true },
287
+ loaderId: { '$ref': 'LoaderId', description: 'Loader identifier.' },
288
+ documentURL:
289
+ { type: 'string',
290
+ description: 'URL of the document this request is loaded for.' },
291
+ request: { '$ref': 'Request', description: 'Request data.' },
292
+ timestamp: { '$ref': 'Timestamp', description: 'Timestamp.' },
293
+ wallTime:
294
+ { '$ref': 'Timestamp',
295
+ hidden: true,
296
+ description: 'UTC Timestamp.' },
297
+ initiator: { '$ref': 'Initiator', description: 'Request initiator.' },
298
+ redirectResponse:
299
+ { optional: true,
300
+ '$ref': 'Response',
301
+ description: 'Redirect response data.' },
302
+ type:
303
+ { '$ref': 'Page.ResourceType',
304
+ optional: true,
305
+ hidden: true,
306
+ description: 'Type of this resource.' } } }
307
+ ```
308
+
309
+ To inspect the `Network.Request` (note that unlike commands and events, types
310
+ are named in upper camel case) type:
311
+
312
+ ```javascript
313
+ >>> Network.Request
314
+ { category: 'type',
315
+ id: 'Request',
316
+ type: 'object',
317
+ description: 'HTTP request data.',
318
+ properties:
319
+ { url: { type: 'string', description: 'Request URL.' },
320
+ method: { type: 'string', description: 'HTTP request method.' },
321
+ headers: { '$ref': 'Headers', description: 'HTTP request headers.' },
322
+ postData:
323
+ { type: 'string',
324
+ optional: true,
325
+ description: 'HTTP POST request data.' },
326
+ mixedContentType:
327
+ { optional: true,
328
+ type: 'string',
329
+ enum: [Object],
330
+ description: 'The mixed content status of the request, as defined in http://www.w3.org/TR/mixed-content/' },
331
+ initialPriority:
332
+ { '$ref': 'ResourcePriority',
333
+ description: 'Priority of the resource request at the time request is sent.' } } }
334
+ ```
335
+
336
+ Chrome Debugging Protocol versions
337
+ ----------------------------------
338
+
339
+ `chrome-remote-interface` uses the [local version] of the protocol descriptor by
340
+ default. This file is manually updated from time to time using
341
+ `scripts/update-protocol.sh` and pushed to this repository.
342
+
343
+ This behavior can be changed by setting the `remote` option to `true`
344
+ upon [connection](#cdpoptions-callback), in which case the remote instance is
345
+ *asked* to provide its own protocol descriptor.
346
+
347
+ Chrome < 60.0.3097.0 is not able to do that, so in that case the protocol
348
+ descriptor is fetched from the source repository.
349
+
350
+ To override the above behavior there are basically three options:
351
+
352
+ - pass a custom protocol descriptor upon [connection](#cdpoptions-callback)
353
+ (`protocol` option);
354
+
355
+ - use the *raw* version of the [commands](#clientsendmethod-params-callback)
356
+ and [events](#event-domainmethod) interface;
357
+
358
+ - update the local copy with `scripts/update-protocol.sh` (not present when
359
+ fetched with `npm install`).
360
+
361
+ [local version]: lib/protocol.json
362
+
363
+ Browser usage
364
+ -------------
365
+
366
+ This module is able to run within a web context, with obvious limitations
367
+ though, namely external HTTP requests
368
+ ([List](#cdplistoptions-callback), [New](#cdpnewoptions-callback), etc.) cannot
369
+ be performed directly, for this reason the user must provide a global
370
+ `criRequest` in order to use them:
371
+
372
+ ```js
373
+ function criRequest(options, callback) {}
374
+ ```
375
+
376
+ `options` is the same object used by the Node.js `http` module and `callback` is
377
+ a function taking two arguments: `err` (JavaScript `Error` object or `null`) and
378
+ `data` (string result).
379
+
380
+ ### Using [webpack](https://webpack.github.io/)
381
+
382
+ It just works, simply require this module:
383
+
384
+ ```js
385
+ const CDP = require('chrome-remote-interface');
386
+ ```
387
+
388
+ To use a non-minified version manually run webpack with:
389
+
390
+ DEBUG=true npm run webpack
391
+
392
+ ### Using *vanilla* JavaScript
393
+
394
+ To generate a JavaScript file that can be used with a `<script>` element:
395
+
396
+ 1. run `npm install` from the root directory;
397
+
398
+ 2. manually run webpack with:
399
+
400
+ TARGET=var npm run webpack
401
+ TARGET=var DEBUG=true npm run webpack
402
+
403
+ 3. use as:
404
+
405
+ ```html
406
+ <script>
407
+ function criRequest(options, callback) { /*...*/ }
408
+ </script>
409
+ <script src="chrome-remote-interface.js"></script>
410
+ ```
411
+
412
+ API
413
+ ---
414
+
415
+ The API consists of three parts:
416
+
417
+ - *DevTools* methods (for those [implementations](#implementations) that support
418
+ them, e.g., [List](#cdplistoptions-callback), [New](#cdpnewoptions-callback),
419
+ etc.);
420
+
421
+ - [connection](#cdpoptions-callback) establishment;
422
+
423
+ - the actual [protocol interaction](#class-cdp).
424
+
425
+ ### CDP([options], [callback])
426
+
427
+ Connects to a remote instance using the [Chrome Debugging Protocol].
428
+
429
+ `options` is an object with the following optional properties:
430
+
431
+ - `host`: HTTP frontend host. Defaults to `localhost`;
432
+ - `port`: HTTP frontend port. Defaults to `9222`;
433
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`;
434
+ - `target`: determines which target this client should attach to. The behavior
435
+ changes according to the type:
436
+
437
+ - a `function` that takes the array returned by the `List` method and returns
438
+ a target or its numeric index relative to the array;
439
+ - a target `object` like those returned by the `New` and `List` methods;
440
+ - a `string` representing the raw WebSocket URL, in this case `host` and
441
+ `port` are not used to fetch the target list, yet they are used to complete
442
+ the URL if relative;
443
+ - a `string` representing the target id.
444
+
445
+ Defaults to a function which returns the first available target according to
446
+ the implementation (note that at most one connection can be established to the
447
+ same target);
448
+ - `protocol`: [Chrome Debugging Protocol] descriptor object. Defaults to use the
449
+ protocol chosen according to the `remote` option;
450
+ - `remote`: a boolean indicating whether the protocol must be fetched *remotely*
451
+ or if the local version must be used. It has no effect if the `protocol`
452
+ option is set. Defaults to `false`.
453
+
454
+ These options are also valid properties of all the instances of the `CDP` class.
455
+
456
+ `callback` is a listener automatically added to the `connect` event of the
457
+ returned `EventEmitter`. When `callback` is omitted a `Promise` object is
458
+ returned which becomes fulfilled if the `connect` event is triggered and
459
+ rejected if the `error` event is triggered.
460
+
461
+ The `EventEmitter` supports the following events:
462
+
463
+ #### Event: 'connect'
464
+
465
+ ```javascript
466
+ function (client) {}
467
+ ```
468
+
469
+ Emitted when the connection to the WebSocket is established.
470
+
471
+ `client` is an instance of the `CDP` class.
472
+
473
+ #### Event: 'error'
474
+
475
+ ```javascript
476
+ function (err) {}
477
+ ```
478
+
479
+ Emitted when `http://host:port/json` cannot be reached or if it is not possible
480
+ to connect to the WebSocket.
481
+
482
+ `err` is an instance of `Error`.
483
+
484
+ ### CDP.Protocol([options], [callback])
485
+
486
+ Fetch the [Chrome Debugging Protocol] descriptor.
487
+
488
+ `options` is an object with the following optional properties:
489
+
490
+ - `host`: HTTP frontend host. Defaults to `localhost`;
491
+ - `port`: HTTP frontend port. Defaults to `9222`;
492
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`;
493
+ - `remote`: a boolean indicating whether the protocol must be fetched *remotely*
494
+ or if the local version must be returned. If it is not possible to fulfill the
495
+ request then the local version is used. Defaults to `false`.
496
+
497
+ `callback` is executed when the protocol is fetched, it gets the following
498
+ arguments:
499
+
500
+ - `err`: a `Error` object indicating the success status;
501
+ - `protocol`: an object with the following properties:
502
+ - `remote`: a boolean indicating whether the returned descriptor is the
503
+ remote version or not (due to user choice or error);
504
+ - `descriptor`: the [Chrome Debugging Protocol] descriptor.
505
+
506
+ When `callback` is omitted a `Promise` object is returned.
507
+
508
+ For example:
509
+
510
+ ```javascript
511
+ const CDP = require('chrome-remote-interface');
512
+ CDP.Protocol(function (err, protocol) {
513
+ if (!err) {
514
+ console.log(JSON.stringify(protocol.descriptor, null, 4));
515
+ }
516
+ });
517
+ ```
518
+
519
+ ### CDP.List([options], [callback])
520
+
521
+ Request the list of the available open targets/tabs of the remote instance.
522
+
523
+ `options` is an object with the following optional properties:
524
+
525
+ - `host`: HTTP frontend host. Defaults to `localhost`;
526
+ - `port`: HTTP frontend port. Defaults to `9222`;
527
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`.
528
+
529
+ `callback` is executed when the list is correctly received, it gets the
530
+ following arguments:
531
+
532
+ - `err`: a `Error` object indicating the success status;
533
+ - `targets`: the array returned by `http://host:port/json/list` containing the
534
+ target list.
535
+
536
+ When `callback` is omitted a `Promise` object is returned.
537
+
538
+ For example:
539
+
540
+ ```javascript
541
+ const CDP = require('chrome-remote-interface');
542
+ CDP.List(function (err, targets) {
543
+ if (!err) {
544
+ console.log(targets);
545
+ }
546
+ });
547
+ ```
548
+
549
+ ### CDP.New([options], [callback])
550
+
551
+ Create a new target/tab in the remote instance.
552
+
553
+ `options` is an object with the following optional properties:
554
+
555
+ - `host`: HTTP frontend host. Defaults to `localhost`;
556
+ - `port`: HTTP frontend port. Defaults to `9222`;
557
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`;
558
+ - `url`: URL to load in the new target/tab. Defaults to `about:blank`.
559
+
560
+ `callback` is executed when the target is created, it gets the following
561
+ arguments:
562
+
563
+ - `err`: a `Error` object indicating the success status;
564
+ - `target`: the object returned by `http://host:port/json/new` containing the
565
+ target.
566
+
567
+ When `callback` is omitted a `Promise` object is returned.
568
+
569
+ For example:
570
+
571
+ ```javascript
572
+ const CDP = require('chrome-remote-interface');
573
+ CDP.New(function (err, target) {
574
+ if (!err) {
575
+ console.log(target);
576
+ }
577
+ });
578
+ ```
579
+
580
+ ### CDP.Activate([options], [callback])
581
+
582
+ Activate an open target/tab of the remote instance.
583
+
584
+ `options` is an object with the following properties:
585
+
586
+ - `host`: HTTP frontend host. Defaults to `localhost`;
587
+ - `port`: HTTP frontend port. Defaults to `9222`;
588
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`;
589
+ - `id`: Target id. Required, no default.
590
+
591
+ `callback` is executed when the response to the activation request is
592
+ received. It gets the following arguments:
593
+
594
+ - `err`: a `Error` object indicating the success status;
595
+
596
+ When `callback` is omitted a `Promise` object is returned.
597
+
598
+ For example:
599
+
600
+ ```javascript
601
+ const CDP = require('chrome-remote-interface');
602
+ CDP.Activate({'id': 'CC46FBFA-3BDA-493B-B2E4-2BE6EB0D97EC'}, function (err) {
603
+ if (!err) {
604
+ console.log('target is activated');
605
+ }
606
+ });
607
+ ```
608
+
609
+ ### CDP.Close([options], [callback])
610
+
611
+ Close an open target/tab of the remote instance.
612
+
613
+ `options` is an object with the following properties:
614
+
615
+ - `host`: HTTP frontend host. Defaults to `localhost`;
616
+ - `port`: HTTP frontend port. Defaults to `9222`;
617
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`;
618
+ - `id`: Target id. Required, no default.
619
+
620
+ `callback` is executed when the response to the close request is received. It
621
+ gets the following arguments:
622
+
623
+ - `err`: a `Error` object indicating the success status;
624
+
625
+ When `callback` is omitted a `Promise` object is returned.
626
+
627
+ For example:
628
+
629
+ ```javascript
630
+ const CDP = require('chrome-remote-interface');
631
+ CDP.Close({'id': 'CC46FBFA-3BDA-493B-B2E4-2BE6EB0D97EC'}, function (err) {
632
+ if (!err) {
633
+ console.log('target is closing');
634
+ }
635
+ });
636
+ ```
637
+
638
+ Note that the callback is fired when the target is *queued* for removal, but the
639
+ actual removal will occur asynchronously.
640
+
641
+ ### CDP.Version([options], [callback])
642
+
643
+ Request version information from the remote instance.
644
+
645
+ `options` is an object with the following optional properties:
646
+
647
+ - `host`: HTTP frontend host. Defaults to `localhost`;
648
+ - `port`: HTTP frontend port. Defaults to `9222`;
649
+ - `secure`: HTTPS/WSS frontend. Defaults to `false`.
650
+
651
+ `callback` is executed when the version information is correctly received, it
652
+ gets the following arguments:
653
+
654
+ - `err`: a `Error` object indicating the success status;
655
+ - `info`: a JSON object returned by `http://host:port/json/version` containing
656
+ the version information.
657
+
658
+ When `callback` is omitted a `Promise` object is returned.
659
+
660
+ For example:
661
+
662
+ ```javascript
663
+ const CDP = require('chrome-remote-interface');
664
+ CDP.Version(function (err, info) {
665
+ if (!err) {
666
+ console.log(info);
667
+ }
668
+ });
669
+ ```
670
+
671
+ ### Class: CDP
672
+
673
+ #### Event: 'event'
674
+
675
+ ```javascript
676
+ function (message) {}
677
+ ```
678
+
679
+ Emitted when the remote instance sends any notification through the WebSocket.
680
+
681
+ `message` is the object received, it has the following properties:
682
+
683
+ - `method`: a string describing the notification (e.g.,
684
+ `'Network.requestWillBeSent'`);
685
+ - `params`: an object containing the payload.
686
+
687
+ Refer to the [Chrome Debugging Protocol] specification for more information.
688
+
689
+ For example:
690
+
691
+ ```javascript
692
+ client.on('event', function (message) {
693
+ if (message.method === 'Network.requestWillBeSent') {
694
+ console.log(message.params);
695
+ }
696
+ });
697
+ ```
698
+
699
+ #### Event: '`<domain>`.`<method>`'
700
+
701
+ ```javascript
702
+ function (params) {}
703
+ ```
704
+
705
+ Emitted when the remote instance sends a notification for `<domain>.<method>`
706
+ through the WebSocket.
707
+
708
+ `params` is an object containing the payload.
709
+
710
+ This is just a utility event which allows to easily listen for specific
711
+ notifications (see [`'event'`](#event-event)), for example:
712
+
713
+ ```javascript
714
+ client.on('Network.requestWillBeSent', console.log);
715
+ ```
716
+
717
+ #### Event: 'ready'
718
+
719
+ ```javascript
720
+ function () {}
721
+ ```
722
+
723
+ Emitted every time that there are no more pending commands waiting for a
724
+ response from the remote instance. The interaction is asynchronous so the only
725
+ way to serialize a sequence of commands is to use the callback provided by
726
+ the [`send`](#clientsendmethod-params-callback) method. This event acts as a
727
+ barrier and it is useful to avoid the *callback hell* in certain simple
728
+ situations.
729
+
730
+ Users are encouraged to extensively check the response of each method and should
731
+ prefer the promises API when dealing with complex asynchronous program flows.
732
+
733
+ For example to load a URL only after having enabled the notifications of both
734
+ `Network` and `Page` domains:
735
+
736
+ ```javascript
737
+ client.Network.enable();
738
+ client.Page.enable();
739
+ client.once('ready', function () {
740
+ client.Page.navigate({'url': 'https://github.com'});
741
+ });
742
+ ```
743
+
744
+ In this particular case, not enforcing this kind of serialization may cause that
745
+ the remote instance does not properly deliver the desired notifications the
746
+ client.
747
+
748
+
749
+ #### Event: 'disconnect'
750
+
751
+ ```javascript
752
+ function () {}
753
+ ```
754
+
755
+ Emitted when the instance closes the WebSocket connection.
756
+
757
+ This may happen for example when the user opens DevTools or when the tab is
758
+ closed.
759
+
760
+ #### client.send(method, [params], [callback])
761
+
762
+ Issue a command to the remote instance.
763
+
764
+ `method` is a string describing the command.
765
+
766
+ `params` is an object containing the payload.
767
+
768
+ `callback` is executed when the remote instance sends a response to this
769
+ command, it gets the following arguments:
770
+
771
+ - `error`: a boolean value indicating the success status, as reported by the
772
+ remote instance;
773
+ - `response`: an object containing either the response (`result` field, if
774
+ `error === false`) or the indication of the error (`error` field, if `error
775
+ === true`).
776
+
777
+ When `callback` is omitted a `Promise` object is returned instead, with the
778
+ fulfilled/rejected states implemented according to the `error` parameter.
779
+
780
+ Note that the field `id` mentioned in the [Chrome Debugging Protocol]
781
+ specification is managed internally and it is not exposed to the user.
782
+
783
+ For example:
784
+
785
+ ```javascript
786
+ client.send('Page.navigate', {'url': 'https://github.com'}, console.log);
787
+ ```
788
+
789
+ #### client.`<domain>`.`<method>`([params], [callback])
790
+
791
+ Just a shorthand for:
792
+
793
+ ```javascript
794
+ client.send('<domain>.<method>', params, callback);
795
+ ```
796
+
797
+ For example:
798
+
799
+ ```javascript
800
+ client.Page.navigate({'url': 'https://github.com'}, console.log);
801
+ ```
802
+
803
+ #### client.`<domain>`.`<event>`([callback])
804
+
805
+ Just a shorthand for:
806
+
807
+ ```javascript
808
+ client.on('<domain>.<event>', callback);
809
+ ```
810
+
811
+ The only difference is that when `callback` is omitted the event is registered
812
+ only once and a `Promise` object is returned.
813
+
814
+ For example:
815
+
816
+ ```javascript
817
+ client.Network.requestWillBeSent(console.log);
818
+ ```
819
+
820
+ #### client.close([callback])
821
+
822
+ Close the connection to the remote instance.
823
+
824
+ `callback` is executed when the WebSocket is successfully closed.
825
+
826
+ When `callback` is omitted a `Promise` object is returned.
827
+
828
+ Contributors
829
+ ------------
830
+
831
+ - [Andrey Sidorov](https://github.com/sidorares)
832
+ - [Greg Cochard](https://github.com/gcochard)
833
+
834
+ Resources
835
+ ---------
836
+
837
+ - [Chrome Debugging Protocol]
838
+ - [Chrome Debugging Protocol Google group](https://groups.google.com/forum/#!forum/chrome-debugging-protocol)
839
+ - [devtools-protocol official repo](https://github.com/ChromeDevTools/devtools-protocol)
840
+ - [Showcase Chrome Debugging Protocol Clients](https://developer.chrome.com/devtools/docs/debugging-clients)
841
+ - [Awesome chrome-devtools](https://github.com/ChromeDevTools/awesome-chrome-devtools)
842
+
843
+ [Chrome Debugging Protocol]: https://chromedevtools.github.io/devtools-protocol/