logstash-core 1.5.0.rc3.snapshot1-java → 1.5.0.rc3.snapshot2-java

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.

Potentially problematic release.


This version of logstash-core might be problematic. Click here for more details.

checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: ccb8f6feb74845cf8d8edc1560b620889bc64e32
4
- data.tar.gz: 7a9557a4e3ce4d677d76b0a000712a535284ce00
3
+ metadata.gz: 9ec518211d023c5f4499757aed7d6e3cfdf7c2fa
4
+ data.tar.gz: 8434ea102ecd49a99ddbf66f9c1730028087f661
5
5
  SHA512:
6
- metadata.gz: 3abbaebd57fc5378d3c4a94e24cbea76c16f5618d219e8048d5c14b900cb3613cf2f96aa6987d5d758094296257f96578aea7064b3ba7b44992a77a6a01d36d5
7
- data.tar.gz: a64b9710d36d5614a9cf5279f02bdee89f799aca9d7bdf6710cd8d19f1959321a1053ec07116400cb5bfabdc462075e91735bd61b2fbc83c785d301ab03843c8
6
+ metadata.gz: a2312511be9d28f1a5d0b07fc66bfba8a50dcdb3299c15b6ee9bc803356f2fc4ee668b9c38047b64cfc4532117f4c43e9fa6fd20236cb20abd391001c75177ba
7
+ data.tar.gz: 44784d222a78ba4cfe8ee0a9b84b342d780280fcc62fbb3b0823bb1c0f110b08ca941e3e2c204e8f31bcd3c245b390170e012e35b030d41fd6e9ae9603a8a8ee
@@ -172,7 +172,6 @@ class LogStash::Agent < Clamp::Command
172
172
 
173
173
  if RUBY_PLATFORM == "java"
174
174
  show_version_java
175
- show_version_elasticsearch
176
175
  end
177
176
 
178
177
  if [:debug].include?(verbosity?) || debug?
@@ -190,13 +189,6 @@ class LogStash::Agent < Clamp::Command
190
189
  puts RUBY_DESCRIPTION
191
190
  end # def show_version_ruby
192
191
 
193
- def show_version_elasticsearch
194
- LogStash::Environment.load_elasticsearch_jars!
195
-
196
- $stdout.write("Elasticsearch: ");
197
- org.elasticsearch.Version::main([])
198
- end # def show_version_elasticsearch
199
-
200
192
  def show_version_java
201
193
  properties = java.lang.System.getProperties
202
194
  puts "java #{properties["java.version"]} (#{properties["java.vendor"]})"
@@ -23,6 +23,28 @@ end
23
23
 
24
24
  module LogStash
25
25
  module Bundler
26
+ # Take a gem package and extract it to a specific target
27
+ # @param [String] Gem file, this must be a path
28
+ # @param [String, String] Return a Gem::Package and the installed path
29
+ def self.unpack(file, path)
30
+ require "rubygems/package"
31
+ require "securerandom"
32
+
33
+ # We are creating a random directory per extract,
34
+ # if we dont do this bundler will not trigger download of the dependencies.
35
+ # Use case is:
36
+ # - User build his own gem with a fix
37
+ # - User doesnt increment the version
38
+ # - User install the same version but different code or dependencies multiple times..
39
+ basename = ::File.basename(file, '.gem')
40
+ unique = SecureRandom.hex(4)
41
+ target_path = ::File.expand_path(::File.join(path, unique, basename))
42
+
43
+ package = ::Gem::Package.new(file)
44
+ package.extract_files(target_path)
45
+
46
+ return [package, target_path]
47
+ end
26
48
 
27
49
  # capture any $stdout from the passed block. also trap any exception in that block, in which case the trapped exception will be returned
28
50
  # @param [Proc] the code block to execute
@@ -53,6 +75,9 @@ module LogStash
53
75
 
54
76
  ENV["GEM_PATH"] = LogStash::Environment.logstash_gem_home
55
77
 
78
+ # force Rubygems sources to our Gemfile sources
79
+ ::Gem.sources = options[:rubygems_source] if options[:rubygems_source]
80
+
56
81
  ::Bundler.settings[:path] = LogStash::Environment::BUNDLE_DIR
57
82
  ::Bundler.settings[:gemfile] = LogStash::Environment::GEMFILE_PATH
58
83
  ::Bundler.settings[:without] = options[:without].join(":")
@@ -60,7 +85,7 @@ module LogStash
60
85
  try = 0
61
86
 
62
87
  # capture_stdout also traps any raised exception and pass them back as the function return [output, exception]
63
- capture_stdout do
88
+ output, exception = capture_stdout do
64
89
  loop do
65
90
  begin
66
91
  ::Bundler.reset!
@@ -81,11 +106,15 @@ module LogStash
81
106
 
82
107
  try += 1
83
108
  $stderr.puts("Error #{e.class}, retrying #{try}/#{options[:max_tries]}")
84
- $stderr.puts(e.message) if ENV["DEBUG"]
109
+ $stderr.puts(e.message)
85
110
  sleep(0.5)
86
111
  end
87
112
  end
88
113
  end
114
+
115
+ raise exception if exception
116
+
117
+ return output
89
118
  end
90
119
 
91
120
  # build Bundler::CLI.start arguments array from the given options hash
@@ -107,4 +136,4 @@ module LogStash
107
136
  arguments.flatten
108
137
  end
109
138
  end
110
- end
139
+ end
@@ -1,5 +1,5 @@
1
1
  require "logstash/errors"
2
- require 'logstash/version'
2
+ require "logstash/version"
3
3
 
4
4
  # monkey patch RubyGems to silence ffi warnings:
5
5
  #
@@ -44,32 +44,14 @@ module LogStash
44
44
  extend self
45
45
 
46
46
  LOGSTASH_HOME = ::File.expand_path(::File.join(::File.dirname(__FILE__), "..", ".."))
47
- JAR_DIR = ::File.join(LOGSTASH_HOME, "vendor", "jar")
48
- ELASTICSEARCH_DIR = ::File.join(LOGSTASH_HOME, "vendor", "elasticsearch")
49
47
  BUNDLE_DIR = ::File.join(LOGSTASH_HOME, "vendor", "bundle")
50
48
  GEMFILE_PATH = ::File.join(LOGSTASH_HOME, "Gemfile")
51
49
  BUNDLE_CONFIG_PATH = ::File.join(LOGSTASH_HOME, ".bundle", "config")
52
50
  BOOTSTRAP_GEM_PATH = ::File.join(LOGSTASH_HOME, 'build', 'bootstrap')
51
+ LOCAL_GEM_PATH = ::File.join(LOGSTASH_HOME, 'vendor', 'local_gems')
53
52
 
54
53
  LOGSTASH_ENV = (ENV["LS_ENV"] || 'production').to_s.freeze
55
54
 
56
- # loads currently embedded elasticsearch jars
57
- # @raise LogStash::EnvironmentError if not running under JRuby or if no jar files are found
58
- def load_elasticsearch_jars!
59
- raise(LogStash::EnvironmentError, "JRuby is required") unless jruby?
60
-
61
- require "java"
62
- jars_path = ::File.join(ELASTICSEARCH_DIR, "**", "*.jar")
63
- jar_files = Dir.glob(jars_path)
64
-
65
- raise(LogStash::EnvironmentError, "Could not find Elasticsearch jar files under #{ELASTICSEARCH_DIR}") if jar_files.empty?
66
-
67
- jar_files.each do |jar|
68
- loaded = require jar
69
- puts("Loaded #{jar}") if $DEBUG && loaded
70
- end
71
- end
72
-
73
55
  def logstash_gem_home
74
56
  ::File.join(BUNDLE_DIR, ruby_engine, gem_ruby_version)
75
57
  end
@@ -113,6 +95,43 @@ module LogStash
113
95
  ::Bundler.setup
114
96
  end
115
97
 
98
+ def runtime_jars_root(dir_name, package)
99
+ ::File.join(dir_name, package, "runtime-jars")
100
+ end
101
+
102
+ def test_jars_root(dir_name, package)
103
+ ::File.join(dir_name, package, "test-jars")
104
+ end
105
+
106
+ def load_runtime_jars!(dir_name="vendor", package="jar-dependencies")
107
+ load_jars!(::File.join(runtime_jars_root(dir_name, package), "*.jar"))
108
+ end
109
+
110
+ def load_test_jars!(dir_name="vendor", package="jar-dependencies")
111
+ load_jars!(::File.join(test_jars_root(dir_name, package), "*.jar"))
112
+ end
113
+
114
+ def load_jars!(pattern)
115
+ raise(LogStash::EnvironmentError, I18n.t("logstash.environment.jruby-required")) unless LogStash::Environment.jruby?
116
+
117
+ jar_files = find_jars(pattern)
118
+ require_jars! jar_files
119
+ end
120
+
121
+ def find_jars(pattern)
122
+ require 'java'
123
+ jar_files = Dir.glob(pattern)
124
+ raise(LogStash::EnvironmentError, I18n.t("logstash.environment.missing-jars", :pattern => pattern)) if jar_files.empty?
125
+ jar_files
126
+ end
127
+
128
+ def require_jars!(files)
129
+ files.each do |jar_file|
130
+ loaded = require jar_file
131
+ puts("Loaded #{jar_file}") if $DEBUG && loaded
132
+ end
133
+ end
134
+
116
135
  def ruby_bin
117
136
  ENV["USE_RUBY"] == "1" ? "ruby" : File.join("vendor", "jruby", "bin", "jruby")
118
137
  end
@@ -176,8 +176,14 @@ class LogStash::Event
176
176
  end
177
177
 
178
178
  public
179
- def include?(key)
180
- return !self[key].nil?
179
+ def include?(fieldref)
180
+ if fieldref.start_with?(METADATA_BRACKETS)
181
+ @metadata_accessors.include?(fieldref[METADATA_BRACKETS.length .. -1])
182
+ elsif fieldref == METADATA
183
+ true
184
+ else
185
+ @accessors.include?(fieldref)
186
+ end
181
187
  end # def include?
182
188
 
183
189
  # Append an event to this one.
@@ -1,3 +1,4 @@
1
+ require "logstash/util"
1
2
  module LogStash
2
3
 
3
4
  class GemfileError < StandardError; end
@@ -17,6 +18,7 @@ module LogStash
17
18
 
18
19
  def load
19
20
  @gemset ||= DSL.parse(@io.read)
21
+ backup
20
22
  self
21
23
  end
22
24
 
@@ -51,6 +53,23 @@ module LogStash
51
53
  def remove(name)
52
54
  @gemset.remove_gem(name)
53
55
  end
56
+
57
+ def backup
58
+ @original_backup = @gemset.copy
59
+ end
60
+
61
+ def restore
62
+ @gemset = @original_backup
63
+ end
64
+
65
+ def restore!
66
+ restore
67
+ save
68
+ end
69
+
70
+ def locally_installed_gems
71
+ @gemset.gems.select { |gem| gem.options.include?(:path) }
72
+ end
54
73
  end
55
74
 
56
75
  class Gemset
@@ -101,7 +120,6 @@ module LogStash
101
120
  def copy
102
121
  Marshal.load(Marshal.dump(self))
103
122
  end
104
-
105
123
  private
106
124
 
107
125
  def sources_to_s
@@ -0,0 +1,37 @@
1
+ class LogStash::PluginManager::Command < Clamp::Command
2
+ def gemfile
3
+ @gemfile ||= LogStash::Gemfile.new(File.new(LogStash::Environment::GEMFILE_PATH, 'r+')).load
4
+ end
5
+
6
+ # If set in debug mode we will raise an exception and display the stacktrace
7
+ def report_exception(readable_message, exception)
8
+ if ENV["DEBUG"]
9
+ raise exception
10
+ else
11
+ signal_error("#{readable_message}, message: #{exception.message}")
12
+ end
13
+ end
14
+
15
+ def display_bundler_output(output)
16
+ if ENV['DEBUG'] && output
17
+ # Display what bundler did in the last run
18
+ $stderr.puts("Bundler output")
19
+ $stderr.puts(output)
20
+ end
21
+ end
22
+
23
+
24
+ # Each plugin install for a gemfile create a path with a unique id.
25
+ # we must clear what is not currently used in the
26
+ def remove_unused_locally_installed_gems!
27
+ used_path = gemfile.locally_installed_gems.collect { |gem| gem.options[:path] }
28
+
29
+ Dir.glob(File.join(LogStash::Environment::LOCAL_GEM_PATH, '*')) do |path|
30
+ FileUtils.rm_rf(relative_path(path)) if used_path.none? { |p| p.start_with?(relative_path(path)) }
31
+ end
32
+ end
33
+
34
+ def relative_path(path)
35
+ Pathname.new(path).relative_path_from(Pathname.new(LogStash::Environment::LOGSTASH_HOME)).to_s
36
+ end
37
+ end
@@ -1,16 +1,17 @@
1
- require 'clamp'
2
- require 'logstash/namespace'
3
- require 'logstash/environment'
4
- require 'logstash/pluginmanager/util'
5
- require 'jar-dependencies'
6
- require 'jar_install_post_install_hook'
7
- require 'file-dependencies/gem'
8
-
1
+ require "clamp"
2
+ require "logstash/namespace"
3
+ require "logstash/environment"
4
+ require "logstash/pluginmanager/util"
5
+ require "logstash/pluginmanager/command"
6
+ require "jar-dependencies"
7
+ require "jar_install_post_install_hook"
8
+ require "file-dependencies/gem"
9
9
  require "logstash/gemfile"
10
10
  require "logstash/bundler"
11
+ require "fileutils"
11
12
 
12
- class LogStash::PluginManager::Install < Clamp::Command
13
- parameter "[PLUGIN] ...", "plugin name(s) or file"
13
+ class LogStash::PluginManager::Install < LogStash::PluginManager::Command
14
+ parameter "[PLUGIN] ...", "plugin name(s) or file", :attribute_name => :plugins_arg
14
15
  option "--version", "VERSION", "version of the plugin to install"
15
16
  option "--[no-]verify", :flag, "verify plugin validity before installation", :default => true
16
17
  option "--development", :flag, "install all development dependencies of currently installed plugins", :default => false
@@ -18,95 +19,123 @@ class LogStash::PluginManager::Install < Clamp::Command
18
19
  # the install logic below support installing multiple plugins with each a version specification
19
20
  # but the argument parsing does not support it for now so currently if specifying --version only
20
21
  # one plugin name can be also specified.
21
- #
22
- # TODO: find right syntax to allow specifying list of plugins with optional version specification for each
23
-
24
22
  def execute
25
- if development?
26
- raise(LogStash::PluginManager::Error, "Cannot specify plugin(s) with --development, it will add the development dependencies of the currently installed plugins") unless plugin_list.empty?
23
+ validate_cli_options!
24
+
25
+ if local_gems?
26
+ gems = extract_local_gems_plugins
27
+ elsif development?
28
+ gems = plugins_development_gems
27
29
  else
28
- raise(LogStash::PluginManager::Error, "No plugin specified") if plugin_list.empty? && verify?
29
-
30
- # temporary until we fullfil TODO ^^
31
- raise(LogStash::PluginManager::Error, "Only 1 plugin name can be specified with --version") if version && plugin_list.size > 1
30
+ gems = plugins_gems
31
+ verify_remote!(gems) if verify?
32
32
  end
33
- raise(LogStash::PluginManager::Error, "File #{LogStash::Environment::GEMFILE_PATH} does not exist or is not writable, aborting") unless File.writable?(LogStash::Environment::GEMFILE_PATH)
34
-
35
- gemfile = LogStash::Gemfile.new(File.new(LogStash::Environment::GEMFILE_PATH, "r+")).load
36
- # keep a copy of the gemset to revert on error
37
- original_gemset = gemfile.gemset.copy
38
33
 
39
- # force Rubygems sources to our Gemfile sources
40
- Gem.sources = gemfile.gemset.sources
41
-
42
- # install_list will be an array of [plugin name, version] tuples, version can be nil
43
- install_list = []
34
+ install_gems_list!(gems)
35
+ remove_unused_locally_installed_gems!
36
+ end
44
37
 
38
+ private
39
+ def validate_cli_options!
45
40
  if development?
46
- specs = LogStash::PluginManager.all_installed_plugins_gem_specs(gemfile)
47
- install_list = specs.inject([]) do |result, spec|
48
- result = result + spec.dependencies.select{|dep| dep.type == :development}.map{|dep| [dep.name] + dep.requirement.as_list + [{:group => :development}]}
49
- end
41
+ signal_usage_error("Cannot specify plugin(s) with --development, it will add the development dependencies of the currently installed plugins") unless plugins_arg.empty?
50
42
  else
51
- # at this point we know that plugin_list is not empty and if the --version is specified there is only one plugin in plugin_list
43
+ signal_usage_error("No plugin specified") if plugins_arg.empty? && verify?
44
+ # TODO: find right syntax to allow specifying list of plugins with optional version specification for each
45
+ signal_usage_error("Only 1 plugin name can be specified with --version") if version && plugins_arg.size > 1
46
+ end
47
+ signal_error("File #{LogStash::Environment::GEMFILE_PATH} does not exist or is not writable, aborting") unless ::File.writable?(LogStash::Environment::GEMFILE_PATH)
48
+ end
52
49
 
53
- install_list = version ? [plugin_list << version] : plugin_list.map{|plugin| [plugin, nil]}
50
+ # Check if the specified gems contains
51
+ # the logstash `metadata`
52
+ def verify_remote!(gems)
53
+ gems.each do |plugin, version|
54
+ puts("Validating #{[plugin, version].compact.join("-")}")
55
+ signal_error("Installation aborted, verification failed for #{plugin} #{version}") unless LogStash::PluginManager.logstash_plugin?(plugin, version)
56
+ end
57
+ end
54
58
 
55
- install_list.each do |plugin, version|
56
- puts("Validating #{[plugin, version].compact.join("-")}")
57
- raise(LogStash::PluginManager::Error, "Installation aborted") unless LogStash::PluginManager.logstash_plugin?(plugin, version)
58
- end if verify?
59
+ def plugins_development_gems
60
+ # Get currently defined gems and their dev dependencies
61
+ specs = []
59
62
 
60
- # at this point we know that we either have a valid gem name & version or a valid .gem file path
63
+ specs = LogStash::PluginManager.all_installed_plugins_gem_specs(gemfile)
61
64
 
62
- # if LogStash::PluginManager.plugin_file?(plugin)
63
- # raise(LogStash::PluginManager::Error) unless cache_gem_file(plugin)
64
- # spec = LogStash::PluginManager.plugin_file_spec(plugin)
65
- # gemfile.update(spec.name, spec.version.to_s)
66
- # else
67
- # plugins.each{|tuple| gemfile.update(*tuple)}
68
- # end
65
+ # Construct the list of dependencies to add to the current gemfile
66
+ specs.each_with_object([]) do |spec, install_list|
67
+ dependencies = spec.dependencies
68
+ .select { |dep| dep.type == :development }
69
+ .map { |dep| [dep.name] + dep.requirement.as_list }
70
+
71
+ install_list.concat(dependencies)
69
72
  end
73
+ end
70
74
 
75
+ def plugins_gems
76
+ version ? [plugins_arg << version] : plugins_arg.map { |plugin| [plugin, nil] }
77
+ end
71
78
 
79
+ # install_list will be an array of [plugin name, version, options] tuples, version it
80
+ # can be nil at this point we know that plugins_arg is not empty and if the
81
+ # --version is specified there is only one plugin in plugins_arg
82
+ #
83
+ def install_gems_list!(install_list)
84
+ # If something goes wrong during the installation `LogStash::Gemfile` will restore a backup version.
72
85
  install_list = LogStash::PluginManager.merge_duplicates(install_list)
73
- install_list.each{|plugin, version| gemfile.update(plugin, version)}
74
- gemfile.save
75
86
 
76
- puts("Installing" + (install_list.empty? ? "..." : " " + install_list.map{|plugin, version| plugin}.join(", ")))
87
+ # Add plugins/gems to the current gemfile
88
+ puts("Installing" + (install_list.empty? ? "..." : " " + install_list.collect(&:first).join(", ")))
89
+ install_list.each { |plugin, version, options| gemfile.update(plugin, version, options) }
90
+
91
+ # Sync gemfiles changes to disk to make them available to the `bundler install`'s API
92
+ gemfile.save
77
93
 
78
94
  bundler_options = {:install => true}
79
95
  bundler_options[:without] = [] if development?
96
+ bundler_options[:rubygems_source] = gemfile.gemset.sources
80
97
 
81
- # any errors will be logged to $stderr by invoke_bundler!
82
- output, exception = LogStash::Bundler.invoke_bundler!(bundler_options)
98
+ output = LogStash::Bundler.invoke_bundler!(bundler_options)
83
99
 
84
- if ENV["DEBUG"]
85
- $stderr.puts(output)
86
- $stderr.puts("Error: #{exception.class}, #{exception.message}") if exception
87
- end
100
+ puts("Installation successful")
101
+ rescue => exception
102
+ gemfile.restore!
103
+ report_exception("Installation Aborted", exception)
104
+ ensure
105
+ display_bundler_output(output)
106
+ end
88
107
 
89
- if exception
90
- # revert to original Gemfile content
91
- gemfile.gemset = original_gemset
92
- gemfile.save
93
- raise(LogStash::PluginManager::Error, "Installation aborted")
94
- end
108
+ # Extract the specified local gems in a predefined local path
109
+ # Update the gemfile to use a relative path to this plugin and run
110
+ # Bundler, this will mark the gem not updatable by `bin/plugin update`
111
+ # This is the most reliable way to make it work in bundler without
112
+ # hacking with `how bundler works`
113
+ #
114
+ # Bundler 2.0, will have support for plugins source we could create a .gem source
115
+ # to support it.
116
+ def extract_local_gems_plugins
117
+ plugins_arg.collect do |plugin|
118
+ # We do the verify before extracting the gem so we dont have to deal with unused path
119
+ if verify?
120
+ puts("Validating #{plugin}")
121
+ signal_error("Installation aborted, verification failed for #{plugin}") unless LogStash::PluginManager.logstash_plugin?(plugin, version)
122
+ end
95
123
 
96
- puts("Installation successful")
124
+ package, path = LogStash::Bundler.unpack(plugin, LogStash::Environment::LOCAL_GEM_PATH)
125
+ [package.spec.name, package.spec.version, { :path => relative_path(path) }]
126
+ end
97
127
  end
98
128
 
99
- # copy .gem file into bundler cache directory, log any error to $stderr
100
- # @param path [String] the source .gem file to copy
101
- # @return [Boolean] true if successful
102
- def cache_gem_file(path)
103
- dest = ::File.join(LogStash::Environment.logstash_gem_home, "cache")
104
- begin
105
- FileUtils.cp(path, dest)
106
- rescue => e
107
- $stderr.puts("Error copying #{plugin} to #{dest}, caused by #{e.class}")
108
- return false
129
+ # We cannot install both .gem and normal plugin in one call of `plugin install`
130
+ def local_gems?
131
+ return false if plugins_arg.empty?
132
+
133
+ local_gem = plugins_arg.collect { |plugin| ::File.extname(plugin) == ".gem" }.uniq
134
+
135
+ if local_gem.size == 1
136
+ return local_gem.first
137
+ else
138
+ signal_usage_error("Mixed source of plugins, you can't mix local `.gem` and remote gems")
109
139
  end
110
- true
111
140
  end
112
141
  end # class Logstash::PluginManager
@@ -1,9 +1,10 @@
1
1
  require 'clamp'
2
2
  require 'logstash/namespace'
3
3
  require 'logstash/pluginmanager/util'
4
+ require 'logstash/pluginmanager/command'
4
5
  require 'rubygems/spec_fetcher'
5
6
 
6
- class LogStash::PluginManager::List < Clamp::Command
7
+ class LogStash::PluginManager::List < LogStash::PluginManager::Command
7
8
 
8
9
  parameter "[PLUGIN]", "Part of plugin name to search for, leave empty for all plugins"
9
10
 
@@ -18,24 +19,26 @@ class LogStash::PluginManager::List < Clamp::Command
18
19
  require 'logstash/environment'
19
20
  LogStash::Environment.bundler_setup!
20
21
 
21
- Gem.configuration.verbose = false
22
+ signal_error("No plugins found") if filtered_specs.empty?
22
23
 
23
- gemfile = LogStash::Gemfile.new(File.new(LogStash::Environment::GEMFILE_PATH, "r+")).load
24
-
25
- # start with all locally installed plugin gems regardless of the Gemfile content
26
- specs = LogStash::PluginManager.find_plugins_gem_specs
27
-
28
- # apply filters
29
- specs = specs.select{|spec| gemfile.find(spec.name)} if installed?
30
- specs = specs.select{|spec| spec.name =~ /#{plugin}/i} if plugin
31
- specs = specs.select{|spec| spec.metadata['logstash_group'] == group} if group
32
-
33
- raise(LogStash::PluginManager::Error, "No plugins found") if specs.empty?
34
-
35
- specs.sort_by{|spec| spec.name}.each do |spec|
24
+ filtered_specs.sort_by{|spec| spec.name}.each do |spec|
36
25
  line = "#{spec.name}"
37
26
  line += " (#{spec.version})" if verbose?
38
27
  puts(line)
39
28
  end
40
29
  end
30
+
31
+ def filtered_specs
32
+ @filtered_specs ||= begin
33
+ # start with all locally installed plugin gems regardless of the Gemfile content
34
+ specs = LogStash::PluginManager.find_plugins_gem_specs
35
+
36
+ # apply filters
37
+ specs = specs.select{|spec| gemfile.find(spec.name)} if installed?
38
+ specs = specs.select{|spec| spec.name =~ /#{plugin}/i} if plugin
39
+ specs = specs.select{|spec| spec.metadata['logstash_group'] == group} if group
40
+
41
+ specs
42
+ end
43
+ end
41
44
  end # class Logstash::PluginManager
@@ -5,7 +5,6 @@ require "logstash/pluginmanager/uninstall"
5
5
  require "logstash/pluginmanager/list"
6
6
  require "logstash/pluginmanager/update"
7
7
  require "logstash/pluginmanager/util"
8
- require "logstash/pluginmanager/maven_tools_patch"
9
8
  require "clamp"
10
9
 
11
10
  module LogStash
@@ -3,25 +3,23 @@ require "logstash/logging"
3
3
  require "logstash/errors"
4
4
  require "logstash/environment"
5
5
  require "logstash/pluginmanager/util"
6
+ require "logstash/pluginmanager/command"
6
7
  require "clamp"
7
8
 
8
9
  require "logstash/gemfile"
9
10
  require "logstash/bundler"
10
11
 
11
- class LogStash::PluginManager::Uninstall < Clamp::Command
12
+ class LogStash::PluginManager::Uninstall < LogStash::PluginManager::Command
12
13
  parameter "PLUGIN", "plugin name"
13
14
 
14
-
15
15
  def execute
16
- raise(LogStash::PluginManager::Error, "File #{LogStash::Environment::GEMFILE_PATH} does not exist or is not writable, aborting") unless File.writable?(LogStash::Environment::GEMFILE_PATH)
16
+ LogStash::Environment.bundler_setup!
17
17
 
18
- gemfile = LogStash::Gemfile.new(File.new(LogStash::Environment::GEMFILE_PATH, "r+")).load
19
- # keep a copy of the gemset to revert on error
20
- original_gemset = gemfile.gemset.copy
18
+ signal_error("File #{LogStash::Environment::GEMFILE_PATH} does not exist or is not writable, aborting") unless File.writable?(LogStash::Environment::GEMFILE_PATH)
21
19
 
22
20
  # make sure this is an installed plugin and present in Gemfile.
23
21
  # it is not possible to uninstall a dependency not listed in the Gemfile, for example a dependent codec
24
- raise(LogStash::PluginManager::Error, "This plugin has not been previously installed, aborting") unless LogStash::PluginManager.installed_plugin?(plugin, gemfile)
22
+ signal_error("This plugin has not been previously installed, aborting") unless LogStash::PluginManager.installed_plugin?(plugin, gemfile)
25
23
 
26
24
  # since we previously did a gemfile.find(plugin) there is no reason why
27
25
  # remove would not work (return nil) here
@@ -31,19 +29,15 @@ class LogStash::PluginManager::Uninstall < Clamp::Command
31
29
  puts("Uninstalling #{plugin}")
32
30
 
33
31
  # any errors will be logged to $stderr by invoke_bundler!
34
- output, exception = LogStash::Bundler.invoke_bundler!(:install => true, :clean => true)
35
-
36
- if ENV["DEBUG"]
37
- $stderr.puts(output)
38
- $stderr.puts("Error: #{exception.class}, #{exception.message}") if exception
39
- end
40
-
41
- if exception
42
- # revert to original Gemfile content
43
- gemfile.gemset = original_gemset
44
- gemfile.save
45
- raise(LogStash::PluginManager::Error, "Uninstall aborted")
46
- end
32
+ # output, exception = LogStash::Bundler.invoke_bundler!(:install => true, :clean => true)
33
+ output = LogStash::Bundler.invoke_bundler!(:install => true)
34
+
35
+ remove_unused_locally_installed_gems!
47
36
  end
37
+ rescue => exception
38
+ gemfile.restore!
39
+ report_exception("Uninstall Aborted", exception)
40
+ ensure
41
+ display_bundler_output(output)
48
42
  end
49
43
  end
@@ -1,51 +1,80 @@
1
- require 'clamp'
2
- require 'logstash/namespace'
3
- require 'logstash/pluginmanager/util'
4
- require 'jar-dependencies'
5
- require 'jar_install_post_install_hook'
6
- require 'file-dependencies/gem'
7
-
1
+ require "clamp"
2
+ require "logstash/namespace"
3
+ require "logstash/pluginmanager/util"
4
+ require "logstash/pluginmanager/command"
5
+ require "jar-dependencies"
6
+ require "jar_install_post_install_hook"
7
+ require "file-dependencies/gem"
8
8
  require "logstash/gemfile"
9
9
  require "logstash/bundler"
10
10
 
11
- class LogStash::PluginManager::Update < Clamp::Command
12
- parameter "[PLUGIN] ...", "Plugin name(s) to upgrade to latest version"
11
+ class LogStash::PluginManager::Update < LogStash::PluginManager::Command
12
+ parameter "[PLUGIN] ...", "Plugin name(s) to upgrade to latest version", :attribute_name => :plugins_arg
13
13
 
14
14
  def execute
15
- gemfile = LogStash::Gemfile.new(File.new(LogStash::Environment::GEMFILE_PATH, "r+")).load
16
- # keep a copy of the gemset to revert on error
17
- original_gemset = gemfile.gemset.copy
18
-
19
- previous_gem_specs_map = find_latest_gem_specs
15
+ local_gems = gemfile.locally_installed_gems
20
16
 
21
- # create list of plugins to update
22
- plugins = unless plugin_list.empty?
23
- not_installed = plugin_list.select{|plugin| !previous_gem_specs_map.has_key?(plugin.downcase)}
24
- raise(LogStash::PluginManager::Error, "Plugin #{not_installed.join(', ')} is not installed so it cannot be updated, aborting") unless not_installed.empty?
25
- plugin_list
17
+ if update_all? || !local_gems.empty?
18
+ error_plugin_that_use_path!(local_gems)
26
19
  else
27
- previous_gem_specs_map.values.map{|spec| spec.name}
20
+ plugins_with_path = plugins_arg & local_gems
21
+ error_plugin_that_use_path!(plugins_with_path) if plugins_with_path.size > 0
28
22
  end
29
23
 
24
+ update_gems!
25
+ end
26
+
27
+ private
28
+ def error_plugin_that_use_path!(plugins)
29
+ signal_error("Update is not supported for manually defined plugins or local .gem plugin installations: #{plugins.collect(&:name).join(",")}")
30
+ end
31
+
32
+ def update_all?
33
+ plugins_arg.size == 0
34
+ end
35
+
36
+ def update_gems!
37
+ # If any error is raise inside the block the Gemfile will restore a backup of the Gemfile
38
+ previous_gem_specs_map = find_latest_gem_specs
39
+
30
40
  # remove any version constrain from the Gemfile so the plugin(s) can be updated to latest version
31
41
  # calling update without requiremend will remove any previous requirements
32
- plugins.select{|plugin| gemfile.find(plugin)}.each{|plugin| gemfile.update(plugin)}
42
+ plugins = plugins_to_update(previous_gem_specs_map)
43
+ plugins
44
+ .select { |plugin| gemfile.find(plugin) }
45
+ .each { |plugin| gemfile.update(plugin) }
46
+
47
+ # force a disk sync before running bundler
33
48
  gemfile.save
34
49
 
35
50
  puts("Updating " + plugins.join(", "))
36
51
 
37
52
  # any errors will be logged to $stderr by invoke_bundler!
38
- output, exception = LogStash::Bundler.invoke_bundler!(:update => plugins)
39
- output, exception = LogStash::Bundler.invoke_bundler!(:clean => true) unless exception
53
+ # Bundler cannot update and clean gems in one operation so we have to call the CLI twice.
54
+ output = LogStash::Bundler.invoke_bundler!(:update => plugins)
55
+ output = LogStash::Bundler.invoke_bundler!(:clean => true)
40
56
 
41
- if exception
42
- # revert to original Gemfile content
43
- gemfile.gemset = original_gemset
44
- gemfile.save
57
+ display_updated_plugins(previous_gem_specs_map)
58
+ rescue => exception
59
+ gemfile.restore!
60
+ report_exception("Updated Aborted", exception)
61
+ ensure
62
+ display_bundler_output(output)
63
+ end
45
64
 
46
- report_exception(output, exception)
65
+ # create list of plugins to update
66
+ def plugins_to_update(previous_gem_specs_map)
67
+ if update_all?
68
+ previous_gem_specs_map.values.map{|spec| spec.name}
69
+ else
70
+ not_installed = plugins_arg.select{|plugin| !previous_gem_specs_map.has_key?(plugin.downcase)}
71
+ signal_error("Plugin #{not_installed.join(', ')} is not installed so it cannot be updated, aborting") unless not_installed.empty?
72
+ plugins_arg
47
73
  end
74
+ end
48
75
 
76
+ # We compare the before the update and after the update
77
+ def display_updated_plugins(previous_gem_specs_map)
49
78
  update_count = 0
50
79
  find_latest_gem_specs.values.each do |spec|
51
80
  name = spec.name.downcase
@@ -59,11 +88,10 @@ class LogStash::PluginManager::Update < Clamp::Command
59
88
  update_count += 1
60
89
  end
61
90
  end
91
+
62
92
  puts("No plugin updated") if update_count.zero?
63
93
  end
64
94
 
65
- private
66
-
67
95
  # retrieve only the latest spec for all locally installed plugins
68
96
  # @return [Hash] result hash {plugin_name.downcase => plugin_spec}
69
97
  def find_latest_gem_specs
@@ -73,13 +101,4 @@ class LogStash::PluginManager::Update < Clamp::Command
73
101
  result
74
102
  end
75
103
  end
76
-
77
- def report_exception(output, exception)
78
- if ENV["DEBUG"]
79
- $stderr.puts(output)
80
- $stderr.puts("Error: #{exception.class}, #{exception.message}") if exception
81
- end
82
-
83
- raise(LogStash::PluginManager::Error, "Update aborted")
84
- end
85
104
  end
@@ -1,5 +1,6 @@
1
- module LogStash::PluginManager
1
+ require "rubygems/package"
2
2
 
3
+ module LogStash::PluginManager
3
4
  # check for valid logstash plugin gem name & version or .gem file, logs errors to $stdout
4
5
  # uses Rubygems API and will remotely validated agains the current Gem.sources
5
6
  # @param plugin [String] plugin name or .gem file path
@@ -85,4 +86,4 @@ module LogStash::PluginManager
85
86
  # TODO: properly merge versions requirements
86
87
  plugin_list.uniq(&:first)
87
88
  end
88
- end
89
+ end
data/lib/logstash/util.rb CHANGED
@@ -148,5 +148,4 @@ module LogStash::Util
148
148
  o
149
149
  end
150
150
  end
151
-
152
151
  end # module LogStash::Util
@@ -53,6 +53,11 @@ module LogStash::Util
53
53
  end
54
54
  end
55
55
 
56
+ def include?(accessor)
57
+ target, key = lookup_path(accessor)
58
+ return target.include?(key)
59
+ end
60
+
56
61
  private
57
62
 
58
63
  def lookup(accessor)
@@ -1,6 +1,6 @@
1
1
  # encoding: utf-8
2
2
  # The version of logstash.
3
- LOGSTASH_VERSION = "1.5.0-rc3.snapshot1"
3
+ LOGSTASH_VERSION = "1.5.0-rc3.snapshot2"
4
4
 
5
5
  # Note to authors: this should not include dashes because 'gem' barfs if
6
6
  # you include a dash in the version string.
data/locales/en.yml CHANGED
@@ -7,6 +7,11 @@ en:
7
7
  The error reported is:
8
8
  %{error}
9
9
  logstash:
10
+ environment:
11
+ jruby-required: >-
12
+ JRuby is required
13
+ missing-jars: >-
14
+ Could not find jar files under %{pattern}
10
15
  pipeline:
11
16
  worker-error: |-
12
17
  A plugin had an unrecoverable error. Will restart this plugin.
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: logstash-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.5.0.rc3.snapshot1
4
+ version: 1.5.0.rc3.snapshot2
5
5
  platform: java
6
6
  authors:
7
7
  - Jordan Sissel
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2015-04-08 00:00:00.000000000 Z
13
+ date: 2015-04-14 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: cabin
@@ -166,48 +166,6 @@ dependencies:
166
166
  version: '0'
167
167
  prerelease: false
168
168
  type: :runtime
169
- - !ruby/object:Gem::Dependency
170
- name: jar-dependencies
171
- version_requirements: !ruby/object:Gem::Requirement
172
- requirements:
173
- - - '='
174
- - !ruby/object:Gem::Version
175
- version: 0.1.7
176
- requirement: !ruby/object:Gem::Requirement
177
- requirements:
178
- - - '='
179
- - !ruby/object:Gem::Version
180
- version: 0.1.7
181
- prerelease: false
182
- type: :runtime
183
- - !ruby/object:Gem::Dependency
184
- name: ruby-maven
185
- version_requirements: !ruby/object:Gem::Requirement
186
- requirements:
187
- - - '='
188
- - !ruby/object:Gem::Version
189
- version: 3.1.1.0.8
190
- requirement: !ruby/object:Gem::Requirement
191
- requirements:
192
- - - '='
193
- - !ruby/object:Gem::Version
194
- version: 3.1.1.0.8
195
- prerelease: false
196
- type: :runtime
197
- - !ruby/object:Gem::Dependency
198
- name: maven-tools
199
- version_requirements: !ruby/object:Gem::Requirement
200
- requirements:
201
- - - '='
202
- - !ruby/object:Gem::Version
203
- version: 1.0.7
204
- requirement: !ruby/object:Gem::Requirement
205
- requirements:
206
- - - '='
207
- - !ruby/object:Gem::Version
208
- version: 1.0.7
209
- prerelease: false
210
- type: :runtime
211
169
  - !ruby/object:Gem::Dependency
212
170
  name: minitar
213
171
  version_requirements: !ruby/object:Gem::Requirement
@@ -236,20 +194,6 @@ dependencies:
236
194
  version: 0.1.6
237
195
  prerelease: false
238
196
  type: :runtime
239
- - !ruby/object:Gem::Dependency
240
- name: jruby-httpclient
241
- version_requirements: !ruby/object:Gem::Requirement
242
- requirements:
243
- - - '>='
244
- - !ruby/object:Gem::Version
245
- version: '0'
246
- requirement: !ruby/object:Gem::Requirement
247
- requirements:
248
- - - '>='
249
- - !ruby/object:Gem::Version
250
- version: '0'
251
- prerelease: false
252
- type: :runtime
253
197
  - !ruby/object:Gem::Dependency
254
198
  name: jrjackson
255
199
  version_requirements: !ruby/object:Gem::Requirement
@@ -373,10 +317,10 @@ files:
373
317
  - lib/logstash/pipeline.rb
374
318
  - lib/logstash/plugin.rb
375
319
  - lib/logstash/pluginmanager.rb
320
+ - lib/logstash/pluginmanager/command.rb
376
321
  - lib/logstash/pluginmanager/install.rb
377
322
  - lib/logstash/pluginmanager/list.rb
378
323
  - lib/logstash/pluginmanager/main.rb
379
- - lib/logstash/pluginmanager/maven_tools_patch.rb
380
324
  - lib/logstash/pluginmanager/uninstall.rb
381
325
  - lib/logstash/pluginmanager/update.rb
382
326
  - lib/logstash/pluginmanager/util.rb
@@ -399,7 +343,7 @@ files:
399
343
  - lib/logstash/util/socket_peer.rb
400
344
  - lib/logstash/version.rb
401
345
  - locales/en.yml
402
- homepage: http://logstash.net/
346
+ homepage: http://www.elastic.co/guide/en/logstash/current/index.html
403
347
  licenses:
404
348
  - Apache License (2.0)
405
349
  metadata: {}
@@ -1,12 +0,0 @@
1
- # This adds the "repo" element to the jar-dependencies DSL
2
- # allowing a gemspec to require a jar that exists in a custom
3
- # maven repository
4
- # Example:
5
- # gemspec.requirements << "repo http://localhosty/repo"
6
- require 'maven/tools/dsl/project_gemspec'
7
- class Maven::Tools::DSL::ProjectGemspec
8
- def repo(url)
9
- @parent.repository(:id => url, :url => url)
10
- end
11
- end
12
-