fluent-plugin-serialize-nested-json 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 9f869e0a7533c134e0597890a3de49ed7ffc8844
4
+ data.tar.gz: ab55ad2cdc152698eaebe663c2610b167465f424
5
+ SHA512:
6
+ metadata.gz: 61587db062114ed826461a9a836d8f334c9a4b93912176dc6546fb4064f0e8f20cd67ad06be2929784c7375ba35a11ced059d22fd314ea7e1788664b9390b6ea
7
+ data.tar.gz: 57e5e02f236cdc1272fe8081c56f5ebbe18621c5f26ba0d4bade897e4f911f762033f16023b7469426cc6c27a347af89eb268ffae087d7ed04c5d83184500a46
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in fluent-plugin-json-in-json.gemspec
4
+ gemspec
@@ -0,0 +1,48 @@
1
+ # fluent-plugin-json-in-json [![Gem Version](https://badge.fury.io/rb/fluent-plugin-json-in-json-2.svg)](https://badge.fury.io/rb/fluent-plugin-json-in-json-2)
2
+
3
+ This is a fork repo of [arcivanov/fluent-plugin-json-in-json](https://github.com/arcivanov/fluent-plugin-json-in-json) which itself fork of [gmr/fluent-plugin-json-in-json](https://github.com/gmr/fluent-plugin-json-in-json) which is not supported now.
4
+
5
+ The purpose of this repo to publish actual version of `fluent-plugin-json-in-json` plugin.
6
+
7
+ ## Requirements
8
+
9
+ This fluentd parser plugin parses JSON log lines with nested JSON strings. For
10
+ example, given a docker log of ``{"log": "{\"foo\": \"bar\"}"}``, the log record
11
+ will be parsed into ``{:log => { :foo => "bar" }}``.
12
+
13
+ ## Installation
14
+
15
+ Add this line to your application's Gemfile:
16
+
17
+ gem 'fluent-plugin-json-in-json-2'
18
+
19
+ And then execute:
20
+
21
+ $ bundle
22
+
23
+ Or install it yourself as:
24
+
25
+ $ gem install fluent-plugin-json-in-json-2
26
+
27
+
28
+ ## Usage
29
+
30
+ ```
31
+ <source>
32
+ type tail
33
+ path /var/lib/docker/containers/*/*-json.log
34
+ pos_file /var/log/fluentd-docker.pos
35
+ time_format %Y-%m-%dT%H:%M:%S
36
+ tag docker.*
37
+ format json_in_json
38
+ read_from_head true
39
+ </source>
40
+ ```
41
+
42
+ ## Contributing
43
+
44
+ 1. Fork it
45
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
46
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
47
+ 4. Push to the branch (`git push origin my-new-feature`)
48
+ 5. Create new Pull Request
@@ -0,0 +1,10 @@
1
+ require 'bundler/gem_tasks'
2
+ require 'rake/testtask'
3
+
4
+ Rake::TestTask.new do |t|
5
+ t.libs << 'test'
6
+ t.test_files = FileList['test/test*.rb']
7
+ t.verbose = true
8
+ t.warning = true
9
+ t.ruby_opts = ['-Eascii-8bit:ascii-8bit']
10
+ end
@@ -0,0 +1,25 @@
1
+ # coding: utf-8
2
+ Gem::Specification.new do |spec|
3
+ spec.name = "fluent-plugin-serialize-nested-json"
4
+ spec.version = "0.0.1"
5
+ spec.authors = ["Yagnesh Mistry"]
6
+ spec.email = ["ysh@live.in"]
7
+ spec.description = %q{Parser plugin that serializes nested JSON attributes}
8
+ spec.summary = %q{Parser plugin that serializes nested JSON attributes}
9
+ spec.homepage = "https://github.com/ysh7/fluent-plugin-serialize-nested-json"
10
+ spec.license = "BSD"
11
+
12
+ spec.files = `git ls-files`.split($/)
13
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
14
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
15
+ spec.require_paths = ["lib"]
16
+
17
+ spec.add_runtime_dependency 'fluentd', ['>= 0.14.0', '< 2']
18
+ spec.add_runtime_dependency 'yajl-ruby', '~> 1.0'
19
+
20
+ spec.add_development_dependency 'rake', '~> 12.3'
21
+ spec.add_development_dependency 'bundler', '~> 1.16'
22
+
23
+ spec.add_development_dependency 'test-unit', ['~> 3.2']
24
+ spec.add_development_dependency 'test-unit-rr', ['~> 1.0']
25
+ end
@@ -0,0 +1,45 @@
1
+ require 'fluent/parser'
2
+ require 'yajl'
3
+
4
+ module Fluent
5
+ module Plugin
6
+ class SerializeJSONParser < Parser
7
+ Plugin.register_parser('serialize_nested_json', self)
8
+
9
+ config_set_default :time_key, 'time'
10
+ config_set_default :time_type, :float
11
+
12
+ def configure(conf)
13
+ if conf.has_key?('time_format')
14
+ conf['time_type'] ||= 'string'
15
+ end
16
+
17
+ super
18
+ end
19
+
20
+ def parse(text)
21
+ record = Yajl.load(text)
22
+
23
+ values = Hash.new
24
+
25
+ record.each do |k, v|
26
+ if v.is_a?(Hash) || v.is_a?(Array)
27
+ begin
28
+ values[k] = Yajl::Encoder.encode(v)
29
+ record.delete k
30
+ rescue Exception => e
31
+ # continue
32
+ end
33
+ end
34
+ end
35
+ record.merge!(values)
36
+
37
+ time, record = convert_values(parse_time(record), record)
38
+
39
+ yield time, record
40
+ rescue Yajl::ParseError
41
+ yield nil, nil
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,128 @@
1
+ # Some tests use Hash instead of Element for configure.
2
+ # We should rewrite these tests in the future and remove this ad-hoc code
3
+ class Hash
4
+ def corresponding_proxies
5
+ @corresponding_proxies ||= []
6
+ end
7
+
8
+ def to_masked_element
9
+ self
10
+ end
11
+ end
12
+
13
+ require 'rr'
14
+ require 'test/unit'
15
+ require 'test/unit/rr'
16
+ require 'fileutils'
17
+ require 'fluent/config/element'
18
+ require 'fluent/log'
19
+ require 'fluent/test'
20
+ require 'fluent/test/helpers'
21
+ require 'fluent/plugin/base'
22
+ require 'fluent/plugin_id'
23
+ require 'fluent/plugin_helper'
24
+ require 'fluent/msgpack_factory'
25
+ require 'fluent/time'
26
+ require 'serverengine'
27
+
28
+ module Fluent
29
+ module Plugin
30
+ class TestBase < Base
31
+ # a base plugin class, but not input nor output
32
+ # mainly for helpers and owned plugins
33
+ include PluginId
34
+ include PluginLoggerMixin
35
+ include PluginHelper::Mixin
36
+ end
37
+ end
38
+ end
39
+
40
+ unless defined?(Test::Unit::AssertionFailedError)
41
+ class Test::Unit::AssertionFailedError < StandardError
42
+ end
43
+ end
44
+
45
+ include Fluent::Test::Helpers
46
+
47
+ def unused_port(num = 1, protocol: :tcp, bind: "0.0.0.0")
48
+ case protocol
49
+ when :tcp
50
+ unused_port_tcp(num)
51
+ when :udp
52
+ unused_port_udp(num, bind: bind)
53
+ else
54
+ raise ArgumentError, "unknown protocol: #{protocol}"
55
+ end
56
+ end
57
+
58
+ def unused_port_tcp(num = 1)
59
+ ports = []
60
+ sockets = []
61
+ num.times do
62
+ s = TCPServer.open(0)
63
+ sockets << s
64
+ ports << s.addr[1]
65
+ end
66
+ sockets.each{|s| s.close }
67
+ if num == 1
68
+ return ports.first
69
+ else
70
+ return *ports
71
+ end
72
+ end
73
+
74
+ PORT_RANGE_AVAILABLE = (1024...65535)
75
+
76
+ def unused_port_udp(num = 1, bind: "0.0.0.0")
77
+ family = IPAddr.new(IPSocket.getaddress(bind)).ipv4? ? ::Socket::AF_INET : ::Socket::AF_INET6
78
+ ports = []
79
+ sockets = []
80
+ while ports.size < num
81
+ port = rand(PORT_RANGE_AVAILABLE)
82
+ u = UDPSocket.new(family)
83
+ if (u.bind(bind, port) rescue nil)
84
+ ports << port
85
+ sockets << u
86
+ else
87
+ u.close
88
+ end
89
+ end
90
+ sockets.each{|s| s.close }
91
+ if num == 1
92
+ return ports.first
93
+ else
94
+ return *ports
95
+ end
96
+ end
97
+
98
+ def waiting(seconds, logs: nil, plugin: nil)
99
+ begin
100
+ Timeout.timeout(seconds) do
101
+ yield
102
+ end
103
+ rescue Timeout::Error
104
+ if logs
105
+ STDERR.print(*logs)
106
+ elsif plugin
107
+ STDERR.print(*plugin.log.out.logs)
108
+ end
109
+ raise
110
+ end
111
+ end
112
+
113
+ def ipv6_enabled?
114
+ require 'socket'
115
+
116
+ begin
117
+ TCPServer.open("::1", 0)
118
+ true
119
+ rescue
120
+ false
121
+ end
122
+ end
123
+
124
+ dl_opts = {}
125
+ dl_opts[:log_level] = ServerEngine::DaemonLogger::WARN
126
+ logdev = Fluent::Test::DummyLogDevice.new
127
+ logger = ServerEngine::DaemonLogger.new(logdev, dl_opts)
128
+ $log ||= Fluent::Log.new(logger)
@@ -0,0 +1,67 @@
1
+ require_relative 'helper'
2
+ require 'fluent/test/driver/parser'
3
+ require 'fluent/plugin/parser_json_in_json'
4
+ require 'yajl'
5
+
6
+ class JsonInJsonParserTest < ::Test::Unit::TestCase
7
+ def setup
8
+ Fluent::Test.setup
9
+ @parser = Fluent::Test::Driver::Parser.new(Fluent::Plugin::JSONInJSONParser)
10
+ end
11
+
12
+ def test_parse_float_time()
13
+ @parser.configure({})
14
+ @parser.instance.parse('{"time":1362020400,"host":"192.168.0.1","size":777,"method":"PUT","log_json":" {\\"field1\\":\\"field1 value\\",\\"field2\\":40}"}') { |time, record|
15
+ assert_equal(event_time('2013-02-28 12:00:00 +0900').to_f, time.to_f)
16
+ assert_equal({
17
+ 'host' => '192.168.0.1',
18
+ 'size' => 777,
19
+ 'method' => 'PUT',
20
+ 'field1' => 'field1 value',
21
+ 'field2' => 40
22
+ }, record)
23
+ }
24
+ @parser.instance.parse('{"time":1362020400,"host":"192.168.0.1","size":777,"method":"PUT","log_json":"{\\"field1\\":"}') { |time, record|
25
+ assert_equal(event_time('2013-02-28 12:00:00 +0900').to_f, time.to_f)
26
+ assert_equal({
27
+ 'host' => '192.168.0.1',
28
+ 'size' => 777,
29
+ 'method' => 'PUT',
30
+ 'log_json' => '{"field1":'
31
+ }, record)
32
+ }
33
+ @parser.instance.parse('{"time":1362020400,"host":"192.168.0.1","size":777,"method":"PUT","log_json":"[\\"val1\\",\\"val2\\"]"') { |time, record|
34
+ assert_equal(event_time('2013-02-28 12:00:00 +0900').to_f, time.to_f)
35
+ assert_equal({
36
+ 'host' => '192.168.0.1',
37
+ 'size' => 777,
38
+ 'method' => 'PUT',
39
+ 'log_json' => ['val1', 'val2']
40
+ }, record)
41
+ }
42
+ end
43
+
44
+ def test_parse_string_time()
45
+ @parser.configure('time_format' => '%Y-%m-%dT%H:%M:%S.%NZ', 'keep_time_key' => 'true')
46
+ @parser.instance.parse('{"log":"2018-06-26 13:20:44.075 INFO --- [pool-8-thread-3] outgoing","stream":"stdout","time":"2018-06-26T13:20:44.076022960Z"}') { |time, record|
47
+ assert_equal(event_time('2018-06-26 13:20:44.076022960').to_f, time.to_f)
48
+ assert_equal({
49
+ 'log'=>'2018-06-26 13:20:44.075 INFO --- [pool-8-thread-3] outgoing',
50
+ 'stream'=>'stdout',
51
+ 'time'=>'2018-06-26T13:20:44.076022960Z'
52
+ }, record)
53
+ }
54
+ end
55
+
56
+ def test_yajl_load()
57
+ @parser.configure({})
58
+ @parser.instance.parse('{ "log": " [ msg ] messoge [ k ]", "stream": "stdout"}') { |time, record|
59
+ assert_equal({
60
+ 'log'=> ' [ msg ] messoge [ k ]',
61
+ 'stream'=>'stdout',
62
+ }, record)
63
+ }
64
+ # Yajl.load('["kek":1}')
65
+ end
66
+
67
+ end
metadata ADDED
@@ -0,0 +1,144 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: fluent-plugin-serialize-nested-json
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - Yagnesh Mistry
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2019-09-25 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: fluentd
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: 0.14.0
20
+ - - "<"
21
+ - !ruby/object:Gem::Version
22
+ version: '2'
23
+ type: :runtime
24
+ prerelease: false
25
+ version_requirements: !ruby/object:Gem::Requirement
26
+ requirements:
27
+ - - ">="
28
+ - !ruby/object:Gem::Version
29
+ version: 0.14.0
30
+ - - "<"
31
+ - !ruby/object:Gem::Version
32
+ version: '2'
33
+ - !ruby/object:Gem::Dependency
34
+ name: yajl-ruby
35
+ requirement: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - "~>"
38
+ - !ruby/object:Gem::Version
39
+ version: '1.0'
40
+ type: :runtime
41
+ prerelease: false
42
+ version_requirements: !ruby/object:Gem::Requirement
43
+ requirements:
44
+ - - "~>"
45
+ - !ruby/object:Gem::Version
46
+ version: '1.0'
47
+ - !ruby/object:Gem::Dependency
48
+ name: rake
49
+ requirement: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - "~>"
52
+ - !ruby/object:Gem::Version
53
+ version: '12.3'
54
+ type: :development
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ requirements:
58
+ - - "~>"
59
+ - !ruby/object:Gem::Version
60
+ version: '12.3'
61
+ - !ruby/object:Gem::Dependency
62
+ name: bundler
63
+ requirement: !ruby/object:Gem::Requirement
64
+ requirements:
65
+ - - "~>"
66
+ - !ruby/object:Gem::Version
67
+ version: '1.16'
68
+ type: :development
69
+ prerelease: false
70
+ version_requirements: !ruby/object:Gem::Requirement
71
+ requirements:
72
+ - - "~>"
73
+ - !ruby/object:Gem::Version
74
+ version: '1.16'
75
+ - !ruby/object:Gem::Dependency
76
+ name: test-unit
77
+ requirement: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - "~>"
80
+ - !ruby/object:Gem::Version
81
+ version: '3.2'
82
+ type: :development
83
+ prerelease: false
84
+ version_requirements: !ruby/object:Gem::Requirement
85
+ requirements:
86
+ - - "~>"
87
+ - !ruby/object:Gem::Version
88
+ version: '3.2'
89
+ - !ruby/object:Gem::Dependency
90
+ name: test-unit-rr
91
+ requirement: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - "~>"
94
+ - !ruby/object:Gem::Version
95
+ version: '1.0'
96
+ type: :development
97
+ prerelease: false
98
+ version_requirements: !ruby/object:Gem::Requirement
99
+ requirements:
100
+ - - "~>"
101
+ - !ruby/object:Gem::Version
102
+ version: '1.0'
103
+ description: Parser plugin that serializes nested JSON attributes
104
+ email:
105
+ - ysh@live.in
106
+ executables: []
107
+ extensions: []
108
+ extra_rdoc_files: []
109
+ files:
110
+ - ".gitignore"
111
+ - Gemfile
112
+ - README.md
113
+ - Rakefile
114
+ - fluent-plugin-serialize-nested-json.gemspec
115
+ - lib/fluent/plugin/parser_serialize_nested_json.rb
116
+ - test/helper.rb
117
+ - test/test_parser.rb
118
+ homepage: https://github.com/ysh7/fluent-plugin-serialize-nested-json
119
+ licenses:
120
+ - BSD
121
+ metadata: {}
122
+ post_install_message:
123
+ rdoc_options: []
124
+ require_paths:
125
+ - lib
126
+ required_ruby_version: !ruby/object:Gem::Requirement
127
+ requirements:
128
+ - - ">="
129
+ - !ruby/object:Gem::Version
130
+ version: '0'
131
+ required_rubygems_version: !ruby/object:Gem::Requirement
132
+ requirements:
133
+ - - ">="
134
+ - !ruby/object:Gem::Version
135
+ version: '0'
136
+ requirements: []
137
+ rubyforge_project:
138
+ rubygems_version: 2.5.2.1
139
+ signing_key:
140
+ specification_version: 4
141
+ summary: Parser plugin that serializes nested JSON attributes
142
+ test_files:
143
+ - test/helper.rb
144
+ - test/test_parser.rb