fluentd-server 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.env +5 -0
- data/.gitignore +17 -0
- data/.travis.yml +5 -0
- data/API.md +21 -0
- data/CHANGELOG.md +3 -0
- data/Gemfile +9 -0
- data/Procfile +1 -0
- data/README.md +127 -0
- data/Rakefile +26 -0
- data/bench/bench.rb +83 -0
- data/bench/result.md +17 -0
- data/bin/fluentd-server +7 -0
- data/config.ru +15 -0
- data/config/unicorn.conf +20 -0
- data/db/migrate/20140512203133_create_posts.rb +14 -0
- data/db/schema.rb +25 -0
- data/fluentd-server.gemspec +43 -0
- data/lib/fluentd_server.rb +1 -0
- data/lib/fluentd_server/cli.rb +64 -0
- data/lib/fluentd_server/config.rb +27 -0
- data/lib/fluentd_server/decorator.rb +21 -0
- data/lib/fluentd_server/environments.rb +34 -0
- data/lib/fluentd_server/logger.rb +90 -0
- data/lib/fluentd_server/model.rb +10 -0
- data/lib/fluentd_server/version.rb +3 -0
- data/lib/fluentd_server/web.rb +101 -0
- data/lib/fluentd_server/web_helper.rb +91 -0
- data/public/css/bootstrap.min.css +7 -0
- data/public/fonts/glyphicons-halflings-regular.eot +0 -0
- data/public/fonts/glyphicons-halflings-regular.svg +229 -0
- data/public/fonts/glyphicons-halflings-regular.ttf +0 -0
- data/public/fonts/glyphicons-halflings-regular.woff +0 -0
- data/public/js/bootstrap.min.js +7 -0
- data/public/js/jquery-1.10.2.min.js +6 -0
- data/public/js/jquery-1.10.2.min.map +0 -0
- data/public/js/jquery.storageapi.min.js +2 -0
- data/spec/api_spec.rb +42 -0
- data/spec/spec_helper.rb +14 -0
- data/spec/web_helper_spec.rb +27 -0
- data/spec/web_spec.rb +55 -0
- data/views/_navbar.slim +15 -0
- data/views/layout.slim +22 -0
- data/views/posts/create.slim +19 -0
- data/views/posts/edit.slim +23 -0
- data/views/posts/index.slim +9 -0
- metadata +363 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 23543f023f2b14f82abde08cceba1337e730c494
|
4
|
+
data.tar.gz: bb43d8d9a3686cc3e1cba3da52bf532438ba1cc9
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: b430c589ae0aaa6f102d36c98a61dc6230510ea590f528922f26d30a3e4b1511b07b323d7107b82ed417c00fab6734cb657ff7e4ceca60ef771d9a0766a0be64
|
7
|
+
data.tar.gz: 512e455f5e280674c272a992c8ea676323e207c7693eb597d460a9a6d3c88135b394d21b95872724a28c13f340d53538e5832f982b34132cf34644bc1dde0376
|
data/.env
ADDED
data/.gitignore
ADDED
data/API.md
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
## API
|
2
|
+
|
3
|
+
### GET /api/:name
|
4
|
+
|
5
|
+
Get the contents of Fluentd config whose name is :name.
|
6
|
+
Query parameters are replaced with variables in erb.
|
7
|
+
|
8
|
+
Supported query parameter formats are:
|
9
|
+
|
10
|
+
* var=value
|
11
|
+
|
12
|
+
* The variable `var` is replaced with its value in erb.
|
13
|
+
|
14
|
+
* var[]=value1&var[]=value2
|
15
|
+
|
16
|
+
* Array. The variable `var[idx]` such as `var[0]` and `var[1]` is replaced with its value in erb.
|
17
|
+
|
18
|
+
* var[key1]=value1&var[key2]=value2
|
19
|
+
|
20
|
+
* Hash. The variable `var[key]` such as `var['key1']` and `var['key2']` is replaced with its value in erb.
|
21
|
+
|
data/CHANGELOG.md
ADDED
data/Gemfile
ADDED
data/Procfile
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
web: bundle exec unicorn -E production -p $PORT -o $HOST -c config/unicorn.conf
|
data/README.md
ADDED
@@ -0,0 +1,127 @@
|
|
1
|
+
# Fluentd Server
|
2
|
+
|
3
|
+
[](http://travis-ci.org/sonots/fluentd-server)
|
4
|
+
[](https://coveralls.io/r/sonots/fluentd-server?branch=master)
|
5
|
+
|
6
|
+
A Fluentd config distribution server
|
7
|
+
|
8
|
+
Demo: [http://fluentd-server.herokuapp.com](http://fluentd-server.herokuapp.com)
|
9
|
+
|
10
|
+
## What You Can Do
|
11
|
+
|
12
|
+
With Fluentd Server, you can manage fluentd configuration files centrally with `erb`.
|
13
|
+
|
14
|
+
For example, you may create a config post whose name is `worker` as:
|
15
|
+
|
16
|
+
```
|
17
|
+
<source>
|
18
|
+
type forward
|
19
|
+
port <%= port %>
|
20
|
+
</source>
|
21
|
+
|
22
|
+
<match **>
|
23
|
+
type stdout
|
24
|
+
</match>
|
25
|
+
```
|
26
|
+
|
27
|
+
Then you can download the config via an API whose uri is like `/api/worker?port=24224` where its query parameters are replaced with variables in the erb.
|
28
|
+
The downloaded contents should become as follows:
|
29
|
+
|
30
|
+
```
|
31
|
+
<source>
|
32
|
+
type forward
|
33
|
+
port 24224
|
34
|
+
</source>
|
35
|
+
|
36
|
+
<match **>
|
37
|
+
type stdout
|
38
|
+
</match>
|
39
|
+
```
|
40
|
+
|
41
|
+
## How to Use
|
42
|
+
|
43
|
+
The `include` directive of fluentd config supports `http`, so write just one line on your fluentd.conf as:
|
44
|
+
|
45
|
+
```
|
46
|
+
# /etc/fluentd.conf
|
47
|
+
include http://fqdn.to.fluentd-server/api/:name?port=24224
|
48
|
+
```
|
49
|
+
|
50
|
+
where :name is the name of your config post, so that it will download the real configuration from the Fluentd Server.
|
51
|
+
|
52
|
+
## Installation
|
53
|
+
|
54
|
+
Prerequisites
|
55
|
+
|
56
|
+
* SQLite
|
57
|
+
* Ruby 2.0 or later
|
58
|
+
|
59
|
+
### From Gem package
|
60
|
+
|
61
|
+
Easy steps on installation with gem and SQLite.
|
62
|
+
|
63
|
+
```bash
|
64
|
+
$ gem install fluentd-server
|
65
|
+
$ gem install sqlite3
|
66
|
+
$ fluentd-server new
|
67
|
+
$ cd fluentd-server
|
68
|
+
$ fluentd-server init # creates database scheme on SQLite
|
69
|
+
$ fluentd-server start
|
70
|
+
```
|
71
|
+
|
72
|
+
Then see `http://localhost:5126/`.
|
73
|
+
|
74
|
+
### From Git repository
|
75
|
+
|
76
|
+
Install from git repository.
|
77
|
+
|
78
|
+
```bash
|
79
|
+
$ git clone https://github.com/sonots/fluentd-server.git
|
80
|
+
$ cd fluentd-server
|
81
|
+
$ bundle
|
82
|
+
$ bundle exec fluentd-server init # creates database scheme on SQLite
|
83
|
+
$ bundle exec fluentd-server start
|
84
|
+
```
|
85
|
+
|
86
|
+
Then see `http://localhost:5126/`.
|
87
|
+
|
88
|
+
## Configuration
|
89
|
+
|
90
|
+
To configure fluentd-server, edit the `.env` file in the project root directory.
|
91
|
+
|
92
|
+
The default configuration is as follows:
|
93
|
+
|
94
|
+
```
|
95
|
+
PORT=5126
|
96
|
+
HOST=0.0.0.0
|
97
|
+
# DATABASE_URL=sqlite3:data/fluentd_server.db
|
98
|
+
# LOG_PATH=log/application.log
|
99
|
+
# LOG_LEVEL=warn
|
100
|
+
```
|
101
|
+
|
102
|
+
## HTTP API
|
103
|
+
|
104
|
+
See [API.md](API.md).
|
105
|
+
|
106
|
+
## ToDo
|
107
|
+
|
108
|
+
* Local file storage
|
109
|
+
|
110
|
+
* Saving and loading conf from localfiles rather than DB would be nice because it makes possible to manage conf with git
|
111
|
+
* Fluentd Server should cache them on memory, and refresh caches by detecting files are updated
|
112
|
+
|
113
|
+
## ChangeLog
|
114
|
+
|
115
|
+
See [CHANGELOG.md](CHANGELOG.md) for details.
|
116
|
+
|
117
|
+
## Contributing
|
118
|
+
|
119
|
+
1. Fork it
|
120
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
121
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
122
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
123
|
+
5. Create new [Pull Request](../../pull/new/master)
|
124
|
+
|
125
|
+
## Copyright
|
126
|
+
|
127
|
+
Copyright (c) 2014 Naotoshi Seo. See [LICENSE](LICENSE) for details.
|
data/Rakefile
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
require "bundler/gem_tasks"
|
2
|
+
|
3
|
+
require 'rspec/core/rake_task'
|
4
|
+
RSpec::Core::RakeTask.new(:spec) do |t|
|
5
|
+
t.rspec_opts = ["-c", "-f progress"] # '--format specdoc'
|
6
|
+
t.pattern = 'spec/**/*_spec.rb'
|
7
|
+
end
|
8
|
+
|
9
|
+
lib = File.expand_path('../lib', __FILE__)
|
10
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
11
|
+
require 'dotenv/tasks'
|
12
|
+
require 'fluentd_server/config'
|
13
|
+
|
14
|
+
require 'sinatra/activerecord/rake'
|
15
|
+
|
16
|
+
task :console => :dotenv do
|
17
|
+
require "fluentd_server"
|
18
|
+
require 'irb'
|
19
|
+
# require 'irb/completion'
|
20
|
+
ARGV.clear
|
21
|
+
IRB.start
|
22
|
+
end
|
23
|
+
task :c => :console
|
24
|
+
|
25
|
+
task :test => :spec
|
26
|
+
task :default => :spec
|
data/bench/bench.rb
ADDED
@@ -0,0 +1,83 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'parallel'
|
4
|
+
require 'net/http'
|
5
|
+
|
6
|
+
def main
|
7
|
+
requests = 20000 # number of requests to perform
|
8
|
+
concurrency = 126 # number of multiple requests to make
|
9
|
+
name = 'worker'
|
10
|
+
puts "requests = #{requests}"
|
11
|
+
puts "concurrency = #{concurrency}"
|
12
|
+
|
13
|
+
client = Client.new("http://localhost:5126")
|
14
|
+
|
15
|
+
duration = elapsed_time do
|
16
|
+
Parallel.each_with_index([name]*requests, :in_processes => concurrency) do |name, i|
|
17
|
+
puts "processing #{i}" if i % 1000 == 0
|
18
|
+
res = client.get(name)
|
19
|
+
puts 'error' unless res.code == '200'
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
req_per_sec = ( duration > 0 ) ? requests/duration : 0
|
24
|
+
puts "req/sec = #{req_per_sec}"
|
25
|
+
end
|
26
|
+
|
27
|
+
def elapsed_time(&block)
|
28
|
+
s = Time.now
|
29
|
+
yield
|
30
|
+
Time.now - s
|
31
|
+
end
|
32
|
+
|
33
|
+
class Client
|
34
|
+
attr_reader :base_uri
|
35
|
+
attr_reader :host
|
36
|
+
attr_reader :port
|
37
|
+
attr_accessor :debug_dev
|
38
|
+
attr_accessor :open_timeout
|
39
|
+
attr_accessor :read_timeout
|
40
|
+
attr_accessor :verify_ssl
|
41
|
+
attr_accessor :keepalive
|
42
|
+
|
43
|
+
def initialize(base_uri = 'http://127.0.0.1:5126', opts = {})
|
44
|
+
@base_uri = base_uri
|
45
|
+
|
46
|
+
URI.parse(base_uri).tap {|uri|
|
47
|
+
@host = uri.host
|
48
|
+
@port = uri.port
|
49
|
+
@use_ssl = uri.scheme == 'https'
|
50
|
+
}
|
51
|
+
@debug_dev = opts['debug_dev'] # IO object such as STDOUT
|
52
|
+
@open_timeout = opts['open_timeout'] # 60
|
53
|
+
@read_timeout = opts['read_timeout'] # 60
|
54
|
+
@verify_ssl = opts['verify_ssl']
|
55
|
+
@keepalive = opts['keepalive']
|
56
|
+
end
|
57
|
+
|
58
|
+
def http_connection
|
59
|
+
Net::HTTP.new(@host, @port).tap {|http|
|
60
|
+
http.use_ssl = @use_ssl
|
61
|
+
http.open_timeout = @open_timeout if @open_timeout
|
62
|
+
http.read_timeout = @read_timeout if @read_timeout
|
63
|
+
http.verify_mode = OpenSSL::SSL::VERIFY_NONE unless @verify_ssl
|
64
|
+
http.set_debug_output(@debug_dev) if @debug_dev
|
65
|
+
}
|
66
|
+
end
|
67
|
+
|
68
|
+
def get_request(path, extheader = {})
|
69
|
+
Net::HTTP::Get.new(path).tap {|req|
|
70
|
+
req['Host'] = @host
|
71
|
+
req['Connection'] = 'Keep-Alive' if @keepalive
|
72
|
+
extheader.each {|key, value| req[key] = value }
|
73
|
+
}
|
74
|
+
end
|
75
|
+
|
76
|
+
def get(name)
|
77
|
+
path = "/api/#{name}"
|
78
|
+
req = get_request(path)
|
79
|
+
@res = http_connection.start {|http| http.request(req) }
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
83
|
+
main
|
data/bench/result.md
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
The conf body as followings, would be too small to evaluate:
|
2
|
+
|
3
|
+
```
|
4
|
+
<source>
|
5
|
+
type forward
|
6
|
+
port <%= port %>
|
7
|
+
</source>
|
8
|
+
```
|
9
|
+
|
10
|
+
| # of requests | concurrency | server | # of workers | req/sec |
|
11
|
+
|---------------|-------------|---------|--------------|---------|
|
12
|
+
|20000 |126 | unicorn | 1 |865.07 |
|
13
|
+
|20000 |126 | unicorn | 12 |4116.78 |
|
14
|
+
|20000 |126 | puma | 1 |634.20|
|
15
|
+
|20000 |126 | puma | 12 |3765.66 |
|
16
|
+
|
17
|
+
Let's use unicorn
|
data/bin/fluentd-server
ADDED
data/config.ru
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require "rubygems"
|
2
|
+
require "sinatra"
|
3
|
+
require "fluentd_server"
|
4
|
+
require "fluentd_server/web"
|
5
|
+
|
6
|
+
## Unicorn self-process killer
|
7
|
+
#require 'unicorn/worker_killer'
|
8
|
+
#
|
9
|
+
## Max requests per worker
|
10
|
+
#use Unicorn::WorkerKiller::MaxRequests, 3072, 4096
|
11
|
+
#
|
12
|
+
## Max memory size (RSS) per worker
|
13
|
+
#use Unicorn::WorkerKiller::Oom, (192*(1024**2)), (256*(1024**2))
|
14
|
+
|
15
|
+
run FluentdServer::Web
|
data/config/unicorn.conf
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
worker_processes 1
|
2
|
+
# timeout 6000
|
3
|
+
# preload_app true
|
4
|
+
|
5
|
+
GC.respond_to?(:copy_on_write_friendly=) and GC.copy_on_write_friendly = true
|
6
|
+
|
7
|
+
before_fork do |server, worker|
|
8
|
+
defined?(ActiveRecord::Base) and ActiveRecord::Base.connection.disconnect!
|
9
|
+
|
10
|
+
old_pid = "#{server.config[:pid]}.oldbin"
|
11
|
+
if old_pid != server.pid
|
12
|
+
begin
|
13
|
+
sig = (worker.nr + 1) >= server.worker_processes ? :QUIT : :TTOU
|
14
|
+
Process.kill(sig, File.read(old_pid).to_i)
|
15
|
+
rescue Errno::ENOENT, Errno::ESRCH
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
sleep 1
|
20
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
class CreatePosts < ActiveRecord::Migration
|
2
|
+
def self.up
|
3
|
+
create_table :posts do |t|
|
4
|
+
t.string :name
|
5
|
+
t.text :body
|
6
|
+
t.timestamps
|
7
|
+
end
|
8
|
+
add_index :posts, :name, length: 255, unique: true # explicit length is required for MySQL
|
9
|
+
end
|
10
|
+
|
11
|
+
def self.down
|
12
|
+
drop_table :posts
|
13
|
+
end
|
14
|
+
end
|
data/db/schema.rb
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
# encoding: UTF-8
|
2
|
+
# This file is auto-generated from the current state of the database. Instead
|
3
|
+
# of editing this file, please use the migrations feature of Active Record to
|
4
|
+
# incrementally modify your database, and then regenerate this schema definition.
|
5
|
+
#
|
6
|
+
# Note that this schema.rb definition is the authoritative source for your
|
7
|
+
# database schema. If you need to create the application database on another
|
8
|
+
# system, you should be using db:schema:load, not running all the migrations
|
9
|
+
# from scratch. The latter is a flawed and unsustainable approach (the more migrations
|
10
|
+
# you'll amass, the slower it'll run and the greater likelihood for issues).
|
11
|
+
#
|
12
|
+
# It's strongly recommended that you check this file into your version control system.
|
13
|
+
|
14
|
+
ActiveRecord::Schema.define(version: 20140512203133) do
|
15
|
+
|
16
|
+
create_table "posts", force: true do |t|
|
17
|
+
t.string "name"
|
18
|
+
t.text "body"
|
19
|
+
t.datetime "created_at"
|
20
|
+
t.datetime "updated_at"
|
21
|
+
end
|
22
|
+
|
23
|
+
add_index "posts", ["name"], name: "index_posts_on_name", unique: true
|
24
|
+
|
25
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'fluentd_server/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "fluentd-server"
|
8
|
+
spec.version = FluentdServer::VERSION
|
9
|
+
spec.authors = ["Naotoshi Seo"]
|
10
|
+
spec.email = ["sonots@gmail.com"]
|
11
|
+
spec.description = %q{Fluentd config distribution server}
|
12
|
+
spec.summary = spec.description
|
13
|
+
spec.homepage = "https://github.com/sonots/fluentd-server"
|
14
|
+
spec.license = "MIT"
|
15
|
+
|
16
|
+
spec.files = `git ls-files`.split($/)
|
17
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
18
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
|
21
|
+
spec.add_development_dependency "bundler", "~> 1.3"
|
22
|
+
spec.add_development_dependency "rspec"
|
23
|
+
spec.add_development_dependency "capybara"
|
24
|
+
spec.add_development_dependency "pry"
|
25
|
+
spec.add_development_dependency "pry-nav"
|
26
|
+
spec.add_development_dependency "rake"
|
27
|
+
|
28
|
+
spec.add_runtime_dependency "dotenv"
|
29
|
+
spec.add_runtime_dependency "foreman"
|
30
|
+
spec.add_runtime_dependency "thor"
|
31
|
+
|
32
|
+
spec.add_runtime_dependency "sinatra"
|
33
|
+
spec.add_runtime_dependency "activerecord"
|
34
|
+
spec.add_runtime_dependency "sinatra-contrib"
|
35
|
+
spec.add_runtime_dependency "sinatra-activerecord"
|
36
|
+
spec.add_runtime_dependency 'sinatra-flash'
|
37
|
+
spec.add_runtime_dependency 'sinatra-redirect-with-flash'
|
38
|
+
spec.add_runtime_dependency 'sinatra-decorator'
|
39
|
+
spec.add_runtime_dependency 'slim'
|
40
|
+
spec.add_runtime_dependency "unicorn"
|
41
|
+
spec.add_runtime_dependency "unicorn-worker-killer"
|
42
|
+
# spec.add_runtime_dependency 'sqlite3'
|
43
|
+
end
|