fluentd 0.14.4-x64-mingw32

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of fluentd might be problematic. Click here for more details.

Files changed (328) hide show
  1. checksums.yaml +7 -0
  2. data/.github/ISSUE_TEMPLATE.md +6 -0
  3. data/.gitignore +26 -0
  4. data/.travis.yml +45 -0
  5. data/AUTHORS +2 -0
  6. data/CONTRIBUTING.md +35 -0
  7. data/COPYING +14 -0
  8. data/ChangeLog +276 -0
  9. data/Gemfile +9 -0
  10. data/README.md +51 -0
  11. data/Rakefile +53 -0
  12. data/Vagrantfile +17 -0
  13. data/appveyor.yml +41 -0
  14. data/bin/fluent-debug +5 -0
  15. data/example/copy_roundrobin.conf +39 -0
  16. data/example/filter_stdout.conf +22 -0
  17. data/example/in_forward.conf +11 -0
  18. data/example/in_http.conf +14 -0
  19. data/example/in_out_forward.conf +17 -0
  20. data/example/in_syslog.conf +15 -0
  21. data/example/in_tail.conf +14 -0
  22. data/example/in_tcp.conf +13 -0
  23. data/example/in_udp.conf +13 -0
  24. data/example/multi_filters.conf +61 -0
  25. data/example/out_buffered_null.conf +32 -0
  26. data/example/out_copy.conf +20 -0
  27. data/example/out_file.conf +13 -0
  28. data/example/out_forward.conf +35 -0
  29. data/example/out_forward_buf_file.conf +23 -0
  30. data/example/v0_12_filter.conf +78 -0
  31. data/example/v1_literal_example.conf +36 -0
  32. data/fluent.conf +139 -0
  33. data/fluentd.gemspec +51 -0
  34. data/lib/fluent/agent.rb +194 -0
  35. data/lib/fluent/command/bundler_injection.rb +45 -0
  36. data/lib/fluent/command/cat.rb +319 -0
  37. data/lib/fluent/command/debug.rb +102 -0
  38. data/lib/fluent/command/fluentd.rb +273 -0
  39. data/lib/fluent/compat/call_super_mixin.rb +67 -0
  40. data/lib/fluent/compat/exec_util.rb +129 -0
  41. data/lib/fluent/compat/file_util.rb +54 -0
  42. data/lib/fluent/compat/filter.rb +68 -0
  43. data/lib/fluent/compat/formatter.rb +111 -0
  44. data/lib/fluent/compat/formatter_utils.rb +85 -0
  45. data/lib/fluent/compat/handle_tag_and_time_mixin.rb +62 -0
  46. data/lib/fluent/compat/handle_tag_name_mixin.rb +53 -0
  47. data/lib/fluent/compat/input.rb +49 -0
  48. data/lib/fluent/compat/output.rb +677 -0
  49. data/lib/fluent/compat/output_chain.rb +60 -0
  50. data/lib/fluent/compat/parser.rb +180 -0
  51. data/lib/fluent/compat/parser_utils.rb +40 -0
  52. data/lib/fluent/compat/propagate_default.rb +62 -0
  53. data/lib/fluent/compat/record_filter_mixin.rb +34 -0
  54. data/lib/fluent/compat/set_tag_key_mixin.rb +50 -0
  55. data/lib/fluent/compat/set_time_key_mixin.rb +69 -0
  56. data/lib/fluent/compat/socket_util.rb +165 -0
  57. data/lib/fluent/compat/string_util.rb +34 -0
  58. data/lib/fluent/compat/structured_format_mixin.rb +26 -0
  59. data/lib/fluent/compat/type_converter.rb +90 -0
  60. data/lib/fluent/config.rb +56 -0
  61. data/lib/fluent/config/basic_parser.rb +123 -0
  62. data/lib/fluent/config/configure_proxy.rb +366 -0
  63. data/lib/fluent/config/dsl.rb +149 -0
  64. data/lib/fluent/config/element.rb +218 -0
  65. data/lib/fluent/config/error.rb +26 -0
  66. data/lib/fluent/config/literal_parser.rb +251 -0
  67. data/lib/fluent/config/parser.rb +107 -0
  68. data/lib/fluent/config/section.rb +212 -0
  69. data/lib/fluent/config/types.rb +136 -0
  70. data/lib/fluent/config/v1_parser.rb +190 -0
  71. data/lib/fluent/configurable.rb +176 -0
  72. data/lib/fluent/daemon.rb +15 -0
  73. data/lib/fluent/engine.rb +220 -0
  74. data/lib/fluent/env.rb +27 -0
  75. data/lib/fluent/event.rb +287 -0
  76. data/lib/fluent/event_router.rb +259 -0
  77. data/lib/fluent/filter.rb +21 -0
  78. data/lib/fluent/formatter.rb +23 -0
  79. data/lib/fluent/input.rb +21 -0
  80. data/lib/fluent/label.rb +38 -0
  81. data/lib/fluent/load.rb +36 -0
  82. data/lib/fluent/log.rb +445 -0
  83. data/lib/fluent/match.rb +141 -0
  84. data/lib/fluent/mixin.rb +31 -0
  85. data/lib/fluent/msgpack_factory.rb +62 -0
  86. data/lib/fluent/output.rb +26 -0
  87. data/lib/fluent/output_chain.rb +23 -0
  88. data/lib/fluent/parser.rb +23 -0
  89. data/lib/fluent/plugin.rb +161 -0
  90. data/lib/fluent/plugin/bare_output.rb +63 -0
  91. data/lib/fluent/plugin/base.rb +130 -0
  92. data/lib/fluent/plugin/buf_file.rb +154 -0
  93. data/lib/fluent/plugin/buf_memory.rb +34 -0
  94. data/lib/fluent/plugin/buffer.rb +603 -0
  95. data/lib/fluent/plugin/buffer/chunk.rb +160 -0
  96. data/lib/fluent/plugin/buffer/file_chunk.rb +323 -0
  97. data/lib/fluent/plugin/buffer/memory_chunk.rb +90 -0
  98. data/lib/fluent/plugin/exec_util.rb +22 -0
  99. data/lib/fluent/plugin/file_util.rb +22 -0
  100. data/lib/fluent/plugin/file_wrapper.rb +120 -0
  101. data/lib/fluent/plugin/filter.rb +93 -0
  102. data/lib/fluent/plugin/filter_grep.rb +75 -0
  103. data/lib/fluent/plugin/filter_record_transformer.rb +342 -0
  104. data/lib/fluent/plugin/filter_stdout.rb +53 -0
  105. data/lib/fluent/plugin/formatter.rb +45 -0
  106. data/lib/fluent/plugin/formatter_csv.rb +47 -0
  107. data/lib/fluent/plugin/formatter_hash.rb +29 -0
  108. data/lib/fluent/plugin/formatter_json.rb +44 -0
  109. data/lib/fluent/plugin/formatter_ltsv.rb +41 -0
  110. data/lib/fluent/plugin/formatter_msgpack.rb +29 -0
  111. data/lib/fluent/plugin/formatter_out_file.rb +78 -0
  112. data/lib/fluent/plugin/formatter_single_value.rb +34 -0
  113. data/lib/fluent/plugin/formatter_stdout.rb +74 -0
  114. data/lib/fluent/plugin/in_debug_agent.rb +64 -0
  115. data/lib/fluent/plugin/in_dummy.rb +135 -0
  116. data/lib/fluent/plugin/in_exec.rb +149 -0
  117. data/lib/fluent/plugin/in_forward.rb +366 -0
  118. data/lib/fluent/plugin/in_gc_stat.rb +52 -0
  119. data/lib/fluent/plugin/in_http.rb +422 -0
  120. data/lib/fluent/plugin/in_monitor_agent.rb +401 -0
  121. data/lib/fluent/plugin/in_object_space.rb +90 -0
  122. data/lib/fluent/plugin/in_syslog.rb +204 -0
  123. data/lib/fluent/plugin/in_tail.rb +838 -0
  124. data/lib/fluent/plugin/in_tcp.rb +41 -0
  125. data/lib/fluent/plugin/in_udp.rb +37 -0
  126. data/lib/fluent/plugin/in_unix.rb +201 -0
  127. data/lib/fluent/plugin/input.rb +33 -0
  128. data/lib/fluent/plugin/multi_output.rb +95 -0
  129. data/lib/fluent/plugin/out_buffered_null.rb +59 -0
  130. data/lib/fluent/plugin/out_buffered_stdout.rb +70 -0
  131. data/lib/fluent/plugin/out_copy.rb +42 -0
  132. data/lib/fluent/plugin/out_exec.rb +114 -0
  133. data/lib/fluent/plugin/out_exec_filter.rb +393 -0
  134. data/lib/fluent/plugin/out_file.rb +167 -0
  135. data/lib/fluent/plugin/out_forward.rb +646 -0
  136. data/lib/fluent/plugin/out_null.rb +27 -0
  137. data/lib/fluent/plugin/out_relabel.rb +28 -0
  138. data/lib/fluent/plugin/out_roundrobin.rb +80 -0
  139. data/lib/fluent/plugin/out_stdout.rb +48 -0
  140. data/lib/fluent/plugin/out_stream.rb +130 -0
  141. data/lib/fluent/plugin/output.rb +1020 -0
  142. data/lib/fluent/plugin/owned_by_mixin.rb +42 -0
  143. data/lib/fluent/plugin/parser.rb +175 -0
  144. data/lib/fluent/plugin/parser_apache.rb +28 -0
  145. data/lib/fluent/plugin/parser_apache2.rb +84 -0
  146. data/lib/fluent/plugin/parser_apache_error.rb +26 -0
  147. data/lib/fluent/plugin/parser_csv.rb +33 -0
  148. data/lib/fluent/plugin/parser_json.rb +79 -0
  149. data/lib/fluent/plugin/parser_ltsv.rb +50 -0
  150. data/lib/fluent/plugin/parser_multiline.rb +104 -0
  151. data/lib/fluent/plugin/parser_nginx.rb +28 -0
  152. data/lib/fluent/plugin/parser_none.rb +36 -0
  153. data/lib/fluent/plugin/parser_regexp.rb +73 -0
  154. data/lib/fluent/plugin/parser_syslog.rb +82 -0
  155. data/lib/fluent/plugin/parser_tsv.rb +37 -0
  156. data/lib/fluent/plugin/socket_util.rb +22 -0
  157. data/lib/fluent/plugin/storage.rb +84 -0
  158. data/lib/fluent/plugin/storage_local.rb +132 -0
  159. data/lib/fluent/plugin/string_util.rb +22 -0
  160. data/lib/fluent/plugin_helper.rb +42 -0
  161. data/lib/fluent/plugin_helper/child_process.rb +298 -0
  162. data/lib/fluent/plugin_helper/compat_parameters.rb +224 -0
  163. data/lib/fluent/plugin_helper/event_emitter.rb +80 -0
  164. data/lib/fluent/plugin_helper/event_loop.rb +118 -0
  165. data/lib/fluent/plugin_helper/formatter.rb +149 -0
  166. data/lib/fluent/plugin_helper/inject.rb +125 -0
  167. data/lib/fluent/plugin_helper/parser.rb +147 -0
  168. data/lib/fluent/plugin_helper/retry_state.rb +177 -0
  169. data/lib/fluent/plugin_helper/storage.rb +331 -0
  170. data/lib/fluent/plugin_helper/thread.rb +147 -0
  171. data/lib/fluent/plugin_helper/timer.rb +90 -0
  172. data/lib/fluent/plugin_id.rb +63 -0
  173. data/lib/fluent/process.rb +504 -0
  174. data/lib/fluent/registry.rb +99 -0
  175. data/lib/fluent/root_agent.rb +314 -0
  176. data/lib/fluent/rpc.rb +94 -0
  177. data/lib/fluent/supervisor.rb +680 -0
  178. data/lib/fluent/system_config.rb +122 -0
  179. data/lib/fluent/test.rb +56 -0
  180. data/lib/fluent/test/base.rb +85 -0
  181. data/lib/fluent/test/driver/base.rb +179 -0
  182. data/lib/fluent/test/driver/base_owned.rb +70 -0
  183. data/lib/fluent/test/driver/base_owner.rb +125 -0
  184. data/lib/fluent/test/driver/event_feeder.rb +98 -0
  185. data/lib/fluent/test/driver/filter.rb +57 -0
  186. data/lib/fluent/test/driver/formatter.rb +30 -0
  187. data/lib/fluent/test/driver/input.rb +31 -0
  188. data/lib/fluent/test/driver/multi_output.rb +52 -0
  189. data/lib/fluent/test/driver/output.rb +76 -0
  190. data/lib/fluent/test/driver/parser.rb +30 -0
  191. data/lib/fluent/test/driver/test_event_router.rb +45 -0
  192. data/lib/fluent/test/filter_test.rb +77 -0
  193. data/lib/fluent/test/formatter_test.rb +65 -0
  194. data/lib/fluent/test/helpers.rb +79 -0
  195. data/lib/fluent/test/input_test.rb +172 -0
  196. data/lib/fluent/test/log.rb +73 -0
  197. data/lib/fluent/test/output_test.rb +156 -0
  198. data/lib/fluent/test/parser_test.rb +70 -0
  199. data/lib/fluent/time.rb +175 -0
  200. data/lib/fluent/timezone.rb +133 -0
  201. data/lib/fluent/unique_id.rb +39 -0
  202. data/lib/fluent/version.rb +21 -0
  203. data/lib/fluent/winsvc.rb +71 -0
  204. data/test/compat/test_calls_super.rb +166 -0
  205. data/test/compat/test_parser.rb +82 -0
  206. data/test/config/assertions.rb +42 -0
  207. data/test/config/test_config_parser.rb +507 -0
  208. data/test/config/test_configurable.rb +1194 -0
  209. data/test/config/test_configure_proxy.rb +386 -0
  210. data/test/config/test_dsl.rb +415 -0
  211. data/test/config/test_element.rb +403 -0
  212. data/test/config/test_literal_parser.rb +297 -0
  213. data/test/config/test_section.rb +184 -0
  214. data/test/config/test_system_config.rb +120 -0
  215. data/test/config/test_types.rb +171 -0
  216. data/test/helper.rb +119 -0
  217. data/test/plugin/data/2010/01/20100102-030405.log +0 -0
  218. data/test/plugin/data/2010/01/20100102-030406.log +0 -0
  219. data/test/plugin/data/2010/01/20100102.log +0 -0
  220. data/test/plugin/data/log/bar +0 -0
  221. data/test/plugin/data/log/foo/bar.log +0 -0
  222. data/test/plugin/data/log/test.log +0 -0
  223. data/test/plugin/test_bare_output.rb +118 -0
  224. data/test/plugin/test_base.rb +75 -0
  225. data/test/plugin/test_buf_file.rb +571 -0
  226. data/test/plugin/test_buf_memory.rb +42 -0
  227. data/test/plugin/test_buffer.rb +1200 -0
  228. data/test/plugin/test_buffer_chunk.rb +168 -0
  229. data/test/plugin/test_buffer_file_chunk.rb +771 -0
  230. data/test/plugin/test_buffer_memory_chunk.rb +265 -0
  231. data/test/plugin/test_file_util.rb +96 -0
  232. data/test/plugin/test_filter.rb +353 -0
  233. data/test/plugin/test_filter_grep.rb +119 -0
  234. data/test/plugin/test_filter_record_transformer.rb +600 -0
  235. data/test/plugin/test_filter_stdout.rb +211 -0
  236. data/test/plugin/test_formatter_csv.rb +94 -0
  237. data/test/plugin/test_formatter_json.rb +30 -0
  238. data/test/plugin/test_formatter_ltsv.rb +52 -0
  239. data/test/plugin/test_formatter_msgpack.rb +28 -0
  240. data/test/plugin/test_formatter_out_file.rb +95 -0
  241. data/test/plugin/test_formatter_single_value.rb +38 -0
  242. data/test/plugin/test_in_debug_agent.rb +28 -0
  243. data/test/plugin/test_in_dummy.rb +188 -0
  244. data/test/plugin/test_in_exec.rb +133 -0
  245. data/test/plugin/test_in_forward.rb +635 -0
  246. data/test/plugin/test_in_gc_stat.rb +39 -0
  247. data/test/plugin/test_in_http.rb +442 -0
  248. data/test/plugin/test_in_monitor_agent.rb +329 -0
  249. data/test/plugin/test_in_object_space.rb +64 -0
  250. data/test/plugin/test_in_syslog.rb +205 -0
  251. data/test/plugin/test_in_tail.rb +1001 -0
  252. data/test/plugin/test_in_tcp.rb +102 -0
  253. data/test/plugin/test_in_udp.rb +121 -0
  254. data/test/plugin/test_in_unix.rb +126 -0
  255. data/test/plugin/test_input.rb +122 -0
  256. data/test/plugin/test_multi_output.rb +180 -0
  257. data/test/plugin/test_out_buffered_null.rb +79 -0
  258. data/test/plugin/test_out_buffered_stdout.rb +122 -0
  259. data/test/plugin/test_out_copy.rb +160 -0
  260. data/test/plugin/test_out_exec.rb +155 -0
  261. data/test/plugin/test_out_exec_filter.rb +262 -0
  262. data/test/plugin/test_out_file.rb +383 -0
  263. data/test/plugin/test_out_forward.rb +590 -0
  264. data/test/plugin/test_out_null.rb +29 -0
  265. data/test/plugin/test_out_relabel.rb +28 -0
  266. data/test/plugin/test_out_roundrobin.rb +146 -0
  267. data/test/plugin/test_out_stdout.rb +92 -0
  268. data/test/plugin/test_out_stream.rb +93 -0
  269. data/test/plugin/test_output.rb +568 -0
  270. data/test/plugin/test_output_as_buffered.rb +1604 -0
  271. data/test/plugin/test_output_as_buffered_overflow.rb +250 -0
  272. data/test/plugin/test_output_as_buffered_retries.rb +839 -0
  273. data/test/plugin/test_output_as_buffered_secondary.rb +817 -0
  274. data/test/plugin/test_output_as_standard.rb +374 -0
  275. data/test/plugin/test_owned_by.rb +35 -0
  276. data/test/plugin/test_parser_apache.rb +42 -0
  277. data/test/plugin/test_parser_apache2.rb +38 -0
  278. data/test/plugin/test_parser_apache_error.rb +45 -0
  279. data/test/plugin/test_parser_base.rb +32 -0
  280. data/test/plugin/test_parser_csv.rb +104 -0
  281. data/test/plugin/test_parser_json.rb +107 -0
  282. data/test/plugin/test_parser_labeled_tsv.rb +129 -0
  283. data/test/plugin/test_parser_multiline.rb +100 -0
  284. data/test/plugin/test_parser_nginx.rb +48 -0
  285. data/test/plugin/test_parser_none.rb +53 -0
  286. data/test/plugin/test_parser_regexp.rb +277 -0
  287. data/test/plugin/test_parser_syslog.rb +66 -0
  288. data/test/plugin/test_parser_time.rb +46 -0
  289. data/test/plugin/test_parser_tsv.rb +121 -0
  290. data/test/plugin/test_storage.rb +167 -0
  291. data/test/plugin/test_storage_local.rb +8 -0
  292. data/test/plugin/test_string_util.rb +26 -0
  293. data/test/plugin_helper/test_child_process.rb +608 -0
  294. data/test/plugin_helper/test_compat_parameters.rb +242 -0
  295. data/test/plugin_helper/test_event_emitter.rb +51 -0
  296. data/test/plugin_helper/test_event_loop.rb +52 -0
  297. data/test/plugin_helper/test_formatter.rb +252 -0
  298. data/test/plugin_helper/test_inject.rb +487 -0
  299. data/test/plugin_helper/test_parser.rb +263 -0
  300. data/test/plugin_helper/test_retry_state.rb +399 -0
  301. data/test/plugin_helper/test_storage.rb +521 -0
  302. data/test/plugin_helper/test_thread.rb +164 -0
  303. data/test/plugin_helper/test_timer.rb +131 -0
  304. data/test/scripts/exec_script.rb +32 -0
  305. data/test/scripts/fluent/plugin/formatter_known.rb +8 -0
  306. data/test/scripts/fluent/plugin/out_test.rb +81 -0
  307. data/test/scripts/fluent/plugin/out_test2.rb +80 -0
  308. data/test/scripts/fluent/plugin/parser_known.rb +4 -0
  309. data/test/test_config.rb +179 -0
  310. data/test/test_configdsl.rb +148 -0
  311. data/test/test_event.rb +329 -0
  312. data/test/test_event_router.rb +331 -0
  313. data/test/test_event_time.rb +184 -0
  314. data/test/test_filter.rb +121 -0
  315. data/test/test_formatter.rb +319 -0
  316. data/test/test_input.rb +31 -0
  317. data/test/test_log.rb +572 -0
  318. data/test/test_match.rb +137 -0
  319. data/test/test_mixin.rb +351 -0
  320. data/test/test_output.rb +214 -0
  321. data/test/test_plugin_classes.rb +136 -0
  322. data/test/test_plugin_helper.rb +81 -0
  323. data/test/test_process.rb +48 -0
  324. data/test/test_root_agent.rb +278 -0
  325. data/test/test_supervisor.rb +339 -0
  326. data/test/test_time_formatter.rb +186 -0
  327. data/test/test_unique_id.rb +47 -0
  328. metadata +823 -0
@@ -0,0 +1,90 @@
1
+ #
2
+ # Fluentd
3
+ #
4
+ # Licensed under the Apache License, Version 2.0 (the "License");
5
+ # you may not use this file except in compliance with the License.
6
+ # You may obtain a copy of the License at
7
+ #
8
+ # http://www.apache.org/licenses/LICENSE-2.0
9
+ #
10
+ # Unless required by applicable law or agreed to in writing, software
11
+ # distributed under the License is distributed on an "AS IS" BASIS,
12
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # See the License for the specific language governing permissions and
14
+ # limitations under the License.
15
+ #
16
+
17
+ require 'fluent/plugin_helper/event_loop'
18
+
19
+ module Fluent
20
+ module PluginHelper
21
+ module Timer
22
+ include Fluent::PluginHelper::EventLoop
23
+
24
+ # stop : turn checker into false (callbacks not called anymore)
25
+ # shutdown : [-]
26
+ # close : [-]
27
+ # terminate: [-]
28
+
29
+ attr_reader :_timers # for tests
30
+
31
+ # interval: integer/float, repeat: true/false
32
+ def timer_execute(title, interval, repeat: true, &block)
33
+ raise ArgumentError, "BUG: title must be a symbol" unless title.is_a? Symbol
34
+ raise ArgumentError, "BUG: block not specified for callback" unless block_given?
35
+ checker = ->(){ @_timer_running }
36
+ timer = TimerWatcher.new(title, interval, repeat, log, checker, &block)
37
+ @_timers << title
38
+ event_loop_attach(timer)
39
+ end
40
+
41
+ def timer_running?
42
+ defined?(@_timer_running) && @_timer_running
43
+ end
44
+
45
+ def initialize
46
+ super
47
+ @_timers = []
48
+ end
49
+
50
+ def start
51
+ super
52
+ @_timer_running = true
53
+ end
54
+
55
+ def stop
56
+ super
57
+ @_timer_running = false
58
+ end
59
+
60
+ def terminate
61
+ super
62
+ @_timers = []
63
+ end
64
+
65
+ class TimerWatcher < Coolio::TimerWatcher
66
+ def initialize(title, interval, repeat, log, checker, &callback)
67
+ @title = title
68
+ @callback = callback
69
+ @repeat = repeat
70
+ @log = log
71
+ @checker = checker
72
+ super(interval, repeat)
73
+ end
74
+
75
+ def on_timer
76
+ @callback.call if @checker.call
77
+ rescue => e
78
+ @log.error "Unexpected error raised. Stopping the timer.", title: @title, error: e
79
+ @log.error_backtrace
80
+ detach
81
+ @log.error "Timer detached.", title: @title
82
+ ensure
83
+ if attached?
84
+ detach unless @repeat
85
+ end
86
+ end
87
+ end
88
+ end
89
+ end
90
+ end
@@ -0,0 +1,63 @@
1
+ #
2
+ # Fluent
3
+ #
4
+ # Licensed under the Apache License, Version 2.0 (the "License");
5
+ # you may not use this file except in compliance with the License.
6
+ # You may obtain a copy of the License at
7
+ #
8
+ # http://www.apache.org/licenses/LICENSE-2.0
9
+ #
10
+ # Unless required by applicable law or agreed to in writing, software
11
+ # distributed under the License is distributed on an "AS IS" BASIS,
12
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # See the License for the specific language governing permissions and
14
+ # limitations under the License.
15
+ #
16
+
17
+ require 'set'
18
+
19
+ module Fluent
20
+ module PluginId
21
+ @@configured_ids = Set.new
22
+
23
+ def configure(conf)
24
+ @id = conf['@id']
25
+ @_id_configured = !!@id # plugin id is explicitly configured by users (or not)
26
+ if @id
27
+ @id = @id.to_s
28
+ if @@configured_ids.include?(@id) && !plugin_id_for_test?
29
+ raise Fluent::ConfigError, "Duplicated plugin id `#{@id}`. Check whole configuration and fix it."
30
+ end
31
+ @@configured_ids.add(@id)
32
+ end
33
+
34
+ super
35
+ end
36
+
37
+ def plugin_id_for_test?
38
+ caller_locations.each do |location|
39
+ # Thread::Backtrace::Location#path returns base filename or absolute path.
40
+ # #absolute_path returns absolute_path always.
41
+ # https://bugs.ruby-lang.org/issues/12159
42
+ if location.absolute_path =~ /\/test_[^\/]+\.rb$/ # location.path =~ /test_.+\.rb$/
43
+ return true
44
+ end
45
+ end
46
+ false
47
+ end
48
+
49
+ def plugin_id_configured?
50
+ if instance_variable_defined?("@_id_configured")
51
+ @_id_configured
52
+ end
53
+ end
54
+
55
+ def plugin_id
56
+ if instance_variable_defined?("@id")
57
+ @id || "object:#{object_id.to_s(16)}"
58
+ else
59
+ "object:#{object_id.to_s(16)}"
60
+ end
61
+ end
62
+ end
63
+ end
@@ -0,0 +1,504 @@
1
+ #
2
+ # Fluentd
3
+ #
4
+ # Licensed under the Apache License, Version 2.0 (the "License");
5
+ # you may not use this file except in compliance with the License.
6
+ # You may obtain a copy of the License at
7
+ #
8
+ # http://www.apache.org/licenses/LICENSE-2.0
9
+ #
10
+ # Unless required by applicable law or agreed to in writing, software
11
+ # distributed under the License is distributed on an "AS IS" BASIS,
12
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ # See the License for the specific language governing permissions and
14
+ # limitations under the License.
15
+ #
16
+
17
+ # This feature will be deprecated after introducing
18
+ # symmetric multi processing in core.
19
+
20
+ require 'thread'
21
+
22
+ require 'fluent/config'
23
+ ## This comment out (to remove circular reference) is a bit risky,
24
+ ## but in all known cases this file is required after 'fluent/engine'.
25
+ # require 'fluent/engine'
26
+ require 'fluent/event'
27
+
28
+ module Fluent
29
+ class DetachProcessManager
30
+ require 'singleton'
31
+ include Singleton
32
+
33
+ class Broker
34
+ def initialize
35
+ end
36
+
37
+ def engine
38
+ Engine
39
+ end
40
+ end
41
+
42
+ def initialize
43
+ require 'drb'
44
+ DRb.start_service(create_drb_uri, Broker.new)
45
+ @parent_uri = DRb.uri
46
+ end
47
+
48
+ def fork(delegate_object)
49
+ ipr, ipw = IO.pipe # child Engine.emit_stream -> parent Engine.emit_stream
50
+ opr, opw = IO.pipe # parent target.emit_events -> child target.emit_events
51
+
52
+ pid = Process.fork
53
+ if pid
54
+ # parent process
55
+ ipw.close
56
+ opr.close
57
+ forward_thread = process_parent(ipr, opw, pid, delegate_object)
58
+ return pid, forward_thread
59
+ end
60
+
61
+ # child process
62
+ ipr.close
63
+ opw.close
64
+ forward_thread = process_child(ipw, opr, delegate_object)
65
+ return nil, forward_thread
66
+ end
67
+
68
+ private
69
+ def read_header(ipr)
70
+ sz = ipr.read(4).unpack('N')[0]
71
+ ipr.read(sz)
72
+ end
73
+
74
+ def send_header(ipw, data)
75
+ ipw.write [data.bytesize].pack('N')
76
+ ipw.write data
77
+ ipw.flush
78
+ end
79
+
80
+ def create_drb_uri
81
+ "drbunix:" # TODO
82
+ end
83
+
84
+ private
85
+ def process_child(ipw, opr, delegate_object)
86
+ DRb.start_service(create_drb_uri, delegate_object)
87
+ child_uri = DRb.uri
88
+
89
+ send_header(ipw, child_uri)
90
+
91
+ # override target.emit_stream to write event stream to the pipe
92
+ fwd = new_forwarder(ipw, 0.5) # TODO interval
93
+ Engine.define_singleton_method(:emit_stream) do |tag,es|
94
+ fwd.emit(tag, es)
95
+ end
96
+
97
+ # read event stream from the pipe and forward to target.emit
98
+ forward_thread = Thread.new(opr, delegate_object, &method(:output_forward_main))
99
+
100
+ # override global methods to call parent process
101
+ override_shared_methods(@parent_uri)
102
+
103
+ return forward_thread
104
+ end
105
+
106
+ def override_shared_methods(parent_uri)
107
+ broker = DRbObject.new_with_uri(parent_uri)
108
+ shared_methods.each {|(broker_accessor,target,name)|
109
+ remote = broker.send(broker_accessor)
110
+ target.define_singleton_method(name) do |*args,&block|
111
+ remote.send(name, *args, &block)
112
+ end
113
+ }
114
+ end
115
+
116
+ def shared_methods
117
+ [
118
+ #[:engine, Engine, :flush!],
119
+ #[:engine, Engine, :stop],
120
+ ]
121
+ end
122
+
123
+ def process_parent(ipr, opw, pid, delegate_object)
124
+ # child_uri = read_header(ipr)
125
+
126
+ # read event stream from the pipe and forward to Engine.emit_stream
127
+ forward_thread = Thread.new(ipr, pid, &method(:input_forward_main))
128
+
129
+ # note: don't override methods in parent process
130
+ # because another process may fork after overriding
131
+ #override_delegate_methods(delegate_object, child_uri)
132
+
133
+ # return forwarder for DetachProcessMixin to
134
+ # override target.emit and write event stream to the pipe
135
+ fwd = new_forwarder(opw, 0.5) # TODO interval
136
+ # note: override emit method on DetachProcessMixin
137
+ forward_thread.define_singleton_method(:forwarder) do
138
+ fwd
139
+ end
140
+
141
+ return forward_thread
142
+ end
143
+
144
+ #def override_delegate_methods(target, child_uri)
145
+ # remote = DRbObject.new_with_uri(child_uri)
146
+ # delegate_methods(target).each {|name|
147
+ # target.define_singleton_method(name) do |*args,&block|
148
+ # remote.send(name, *args, &block)
149
+ # end
150
+ # }
151
+ #end
152
+ #
153
+ #def delegate_methods(target)
154
+ # target.methods - Object.public_instance_methods
155
+ #end
156
+
157
+ def output_forward_main(opr, target)
158
+ read_event_stream(opr) {|tag,es|
159
+ # FIXME error handling
160
+ begin
161
+ target.emit_events(tag, es)
162
+ rescue
163
+ $log.warn "failed to emit", error: $!.to_s, pid: Process.pid
164
+ $log.warn_backtrace
165
+ end
166
+ }
167
+ rescue
168
+ $log.error "error on output process forwarding thread", error: $!.to_s, pid: Process.pid
169
+ $log.error_backtrace
170
+ raise
171
+ end
172
+
173
+ def input_forward_main(ipr, pid)
174
+ read_event_stream(ipr) {|tag,es|
175
+ # FIXME error handling
176
+ begin
177
+ Engine.emit_stream(tag, es)
178
+ rescue
179
+ $log.warn "failed to emit", error: $!.to_s, pid: Process.pid
180
+ $log.warn_backtrace
181
+ end
182
+ }
183
+ rescue
184
+ $log.error "error on input process forwarding thread", error: $!.to_s, pid: Process.pid
185
+ $log.error_backtrace
186
+ raise
187
+ end
188
+
189
+ def read_event_stream(r, &block)
190
+ u = Fluent::Engine.msgpack_factory.unpacker(r)
191
+ begin
192
+ #buf = ''
193
+ #map = {}
194
+ #while true
195
+ # r.readpartial(64*1024, buf)
196
+ # u.feed_each(buf) {|tag,ms|
197
+ # if msbuf = map[tag]
198
+ # msbuf << ms
199
+ # else
200
+ # map[tag] = ms
201
+ # end
202
+ # }
203
+ # unless map.empty?
204
+ # map.each_pair {|tag,ms|
205
+ # es = MessagePackEventStream.new(ms)
206
+ # block.call(tag, es)
207
+ # }
208
+ # map.clear
209
+ # end
210
+ #end
211
+ u.each {|tag,ms|
212
+ es = MessagePackEventStream.new(ms)
213
+ block.call(tag, es)
214
+ }
215
+ rescue EOFError
216
+ ensure
217
+ r.close
218
+ end
219
+ end
220
+
221
+ def new_forwarder(w, interval)
222
+ if interval < 0.2 # TODO interval
223
+ Forwarder.new(w)
224
+ else
225
+ DelayedForwarder.new(w, interval)
226
+ end
227
+ end
228
+
229
+ class Forwarder
230
+ def initialize(w)
231
+ @w = w
232
+ end
233
+
234
+ def emit(tag, es)
235
+ ms = es.to_msgpack_stream
236
+ #[tag, ms].to_msgpack(@w) # not thread safe
237
+ @w.write [tag, ms].to_msgpack
238
+ end
239
+ end
240
+
241
+ class DelayedForwarder
242
+ def initialize(w, interval)
243
+ @w = w
244
+ @interval = interval
245
+ @buffer = {}
246
+ @mutex = Mutex.new
247
+ Thread.new(&method(:run))
248
+ end
249
+
250
+ def emit(tag, es)
251
+ stream = es.to_msgpack_stream
252
+ @mutex.synchronize do
253
+ if @buffer[tag]
254
+ @buffer[tag] << stream
255
+ else
256
+ @buffer[tag] = stream
257
+ end
258
+ end
259
+ end
260
+
261
+ def run
262
+ while true
263
+ sleep @interval
264
+
265
+ pairs = []
266
+ @mutex.synchronize do
267
+ @buffer.keys.each do |tag|
268
+ if ms = @buffer.delete(tag)
269
+ pairs << [tag, ms]
270
+ end
271
+ end
272
+ end
273
+ pairs.each do |pair|
274
+ pair.to_msgpack(@w)
275
+ end
276
+ end
277
+ rescue
278
+ $log.error "error on forwerder thread", error: $!.to_s
279
+ $log.error_backtrace
280
+ raise
281
+ end
282
+ end
283
+
284
+ class MultiForwarder
285
+ def initialize(forwarders)
286
+ @forwarders = forwarders
287
+ @rr = 1
288
+ end
289
+
290
+ def emit(tag, es)
291
+ forwarder = @forwarders[@rr]
292
+ @rr = (@rr + 1) % @forwarders.length
293
+ forwarder.emit(tag, es)
294
+ end
295
+ end
296
+ end
297
+
298
+
299
+ module DetachProcessImpl
300
+ def on_detach_process(i)
301
+ end
302
+
303
+ def on_exit_process(i)
304
+ end
305
+
306
+ private
307
+
308
+ def detach_process_impl(num, &block)
309
+ children = []
310
+
311
+ num.times do |i|
312
+ pid, forward_thread = DetachProcessManager.instance.fork(self)
313
+
314
+ if pid
315
+ # parent process
316
+ $log.info "detached process", class: self.class, pid: pid
317
+ children << [pid, forward_thread]
318
+ next
319
+ end
320
+
321
+ # child process
322
+ begin
323
+ on_detach_process(i)
324
+
325
+ block.call
326
+
327
+ # disable Engine.stop called by signal handler
328
+ Engine.define_singleton_method(:stop) do
329
+ # do nothing
330
+ end
331
+
332
+ # override signal handlers called by parent process
333
+ fin = FinishWait.new
334
+ trap :INT do
335
+ fin.stop
336
+ end
337
+ trap :TERM do
338
+ fin.stop
339
+ end
340
+ #forward_thread.join # TODO this thread won't stop because parent doesn't close pipe
341
+ fin.wait
342
+
343
+ on_exit_process(i)
344
+ exit! 0
345
+ ensure
346
+ $log.error "unknown error while shutting down this child process", error: $!.to_s, pid: Process.pid
347
+ $log.error_backtrace
348
+ end
349
+
350
+ exit! 1
351
+ end
352
+
353
+ # parent process
354
+ # override shutdown method to kill child processes
355
+ define_singleton_method(:shutdown) do
356
+ children.each {|pair|
357
+ begin
358
+ pid = pair[0]
359
+ forward_thread = pair[1]
360
+ if pid
361
+ Process.kill(:TERM, pid)
362
+ forward_thread.join # wait until child closes pipe
363
+ Process.waitpid(pid)
364
+ pair[0] = nil
365
+ end
366
+ rescue
367
+ $log.error "unknown error while shutting down remote child process", error: $!.to_s
368
+ $log.error_backtrace
369
+ end
370
+ }
371
+ end
372
+
373
+ # override target.emit_events and write event stream to the pipe
374
+ forwarders = children.map {|pair| pair[1].forwarder }
375
+ if forwarders.length > 1
376
+ # use roundrobin
377
+ fwd = DetachProcessManager::MultiForwarder.new(forwarders)
378
+ else
379
+ fwd = forwarders[0]
380
+ end
381
+ define_singleton_method(:emit_events) do |tag,es|
382
+ fwd.emit_events(tag, es)
383
+ end
384
+ end
385
+
386
+ class FinishWait
387
+ def initialize
388
+ @finished = false
389
+ @mutex = Mutex.new
390
+ @cond = ConditionVariable.new
391
+ end
392
+
393
+ def wait
394
+ @mutex.synchronize do
395
+ until @finished
396
+ @cond.wait(@mutex, 1.0)
397
+ end
398
+ end
399
+ end
400
+
401
+ def stop
402
+ return if @finished
403
+ @finished = true
404
+ # Creating new thread due to mutex can't lock in main thread during trap context
405
+ Thread.new {
406
+ @mutex.synchronize do
407
+ @cond.broadcast
408
+ end
409
+ }.run
410
+ end
411
+
412
+ def finished?
413
+ @finished
414
+ end
415
+ end
416
+ end
417
+
418
+
419
+ module DetachProcessMixin
420
+ include DetachProcessImpl
421
+
422
+ def configure(conf)
423
+ super
424
+
425
+ @detach_process = nil
426
+
427
+ if detach_process = conf['detach_process']
428
+ b3v = Config.bool_value(detach_process)
429
+ case b3v
430
+ when nil
431
+ num = detach_process.to_i
432
+ if num > 1
433
+ $log.warn "'detach_process' parameter supports only 1 process on this plugin: #{conf}"
434
+ elsif num > 0
435
+ @detach_process = true
436
+ elsif detach_process =~ /0+/
437
+ @detach_process = false
438
+ else
439
+ @detach_process = true
440
+ end
441
+ when true
442
+ @detach_process = true
443
+ when false
444
+ @detach_process = false
445
+ end
446
+ end
447
+ end
448
+
449
+ def detach_process(&block)
450
+ if @detach_process
451
+ detach_process_impl(1, &block)
452
+ else
453
+ block.call
454
+ end
455
+ end
456
+ end
457
+
458
+
459
+ module DetachMultiProcessMixin
460
+ include DetachProcessImpl
461
+
462
+ def initialize
463
+ @detach_process_num = 2
464
+ super
465
+ end
466
+
467
+ def configure(conf)
468
+ super
469
+
470
+ @detach_process = nil
471
+
472
+ if detach_process = conf['detach_process']
473
+ b3v = Config.bool_value(detach_process)
474
+ case b3v
475
+ when nil
476
+ num = detach_process.to_i
477
+ if num > 0
478
+ @detach_process = true
479
+ @detach_process_num = num
480
+ elsif detach_process =~ /0+/
481
+ @detach_process = false
482
+ else
483
+ @detach_process = true
484
+ end
485
+ when true
486
+ @detach_process = true
487
+ when false
488
+ @detach_process = false
489
+ end
490
+ end
491
+ end
492
+
493
+ private
494
+
495
+ def detach_multi_process(&block)
496
+ if @detach_process
497
+ detach_process_impl(@detach_process_num, &block)
498
+ else
499
+ block.call
500
+ end
501
+ end
502
+ end
503
+ end
504
+