tikh-klarlack 0.0.7

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.
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 Max Schöfmann
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.rdoc ADDED
@@ -0,0 +1,43 @@
1
+ = klarlack
2
+
3
+ Klarlack is a ruby client library for the varnish administration interface.
4
+
5
+ See also: http://www.varnish-cache.org
6
+
7
+ Please note: You need at least version 2.0.3 of varnish for purging to work.
8
+
9
+ === Installation (from gemcutter.org)
10
+
11
+ sudo gem install klarlack
12
+
13
+ === Example
14
+
15
+ Lets purge all blog posts from the cache...
16
+
17
+ require 'rubygems'
18
+ require 'klarlack'
19
+
20
+ varnish = Varnish::Client.new '127.0.0.1:6082'
21
+ # the regexp is not a ruby regexp, just a plain string varnishd understands
22
+ varnish.purge :url, "^/posts/.*"
23
+
24
+ In a Rails app, you might want to use use this in a cache sweeper.
25
+
26
+ === Specs
27
+
28
+ Start up a local varnishd with <tt>-T 127.0.0.1:6082</tt>. Then run
29
+
30
+ spec spec
31
+
32
+ === TODO
33
+
34
+ * Support authentication when varnishd is started with <tt>-S</tt>
35
+ * Make parameter manipulation/display more friendly
36
+
37
+ === WTF?
38
+
39
+ http://dict.leo.org/?search=klarlack
40
+
41
+ === Copyright
42
+
43
+ Copyright (c) 2009-2010 Max Schöfmann. Distributed under the MIT-License
data/Rakefile ADDED
@@ -0,0 +1,48 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+
4
+ begin
5
+ require 'jeweler'
6
+ Jeweler::Tasks.new do |gem|
7
+ gem.name = "klarlack"
8
+ gem.summary = %Q{ruby client for varnishd's admin interface}
9
+ gem.email = "max@pragmatic-it.de"
10
+ gem.homepage = "http://github.com/schoefmax/klarlack"
11
+ gem.authors = ["Max Schöfmann"]
12
+
13
+ # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
14
+ end
15
+ rescue LoadError
16
+ puts "Jeweler not available. Install it with: sudo gem install technicalpickles-jeweler -s http://gems.github.com"
17
+ end
18
+
19
+ require 'spec/rake/spectask'
20
+ Spec::Rake::SpecTask.new(:spec) do |spec|
21
+ spec.libs << 'lib' << 'spec'
22
+ spec.spec_files = FileList['spec/**/*_spec.rb']
23
+ end
24
+
25
+ Spec::Rake::SpecTask.new(:rcov) do |spec|
26
+ spec.libs << 'lib' << 'spec'
27
+ spec.pattern = 'spec/**/*_spec.rb'
28
+ spec.rcov = true
29
+ end
30
+
31
+
32
+ task :default => :spec
33
+
34
+ require 'rake/rdoctask'
35
+ Rake::RDocTask.new do |rdoc|
36
+ if File.exist?('VERSION.yml')
37
+ config = YAML.load(File.read('VERSION.yml'))
38
+ version = "#{config[:major]}.#{config[:minor]}.#{config[:patch]}"
39
+ else
40
+ version = ""
41
+ end
42
+
43
+ rdoc.rdoc_dir = 'rdoc'
44
+ rdoc.title = "klarlack #{version}"
45
+ rdoc.rdoc_files.include('README*')
46
+ rdoc.rdoc_files.include('lib/**/*.rb')
47
+ end
48
+
data/VERSION.yml ADDED
@@ -0,0 +1,4 @@
1
+ ---
2
+ :minor: 0
3
+ :patch: 6
4
+ :major: 0
data/lib/klarlack.rb ADDED
@@ -0,0 +1,7 @@
1
+ require 'socket'
2
+ require 'varnish/socket_factory'
3
+ require 'varnish/client'
4
+
5
+ module Varnish
6
+ VERSION = '0.0.6'
7
+ end
@@ -0,0 +1,302 @@
1
+ module Varnish
2
+ class Error < StandardError; end
3
+ class BrokenConnection < Error; end
4
+ class CommandFailed < Error; end
5
+ class Client
6
+ # Default management port of varnishd
7
+ DEFAULT_PORT = 6082
8
+
9
+ # We assume varnishd on localhost
10
+ DEFAULT_HOST = 'localhost'
11
+
12
+ DEFAULT_OPTS = {
13
+ :keep_alive => false,
14
+ :timeout => 1,
15
+ :secret_file => nil
16
+ }
17
+
18
+ # timeout in seconds when connecting to varnishd. Default is 1
19
+ attr_accessor :timeout
20
+
21
+ # set to true, to keep the connection alive. Default is false
22
+ attr_accessor :keep_alive
23
+
24
+ # the authentication secret file if needed. Default is nil
25
+ attr_accessor :secret_file
26
+
27
+ # hostname or IP-address of varnishd. Default is "localhost"
28
+ attr_accessor :host
29
+
30
+ # port number of varnishd. Default is 6082
31
+ attr_accessor :port
32
+
33
+ # Examples:
34
+ #
35
+ # Varnish::Client.new "127.0.0.1"
36
+ # Varnish::Client.new "mydomain.com:6082"
37
+ # Varnish::Client.new :timeout => 5
38
+ # Varnish::Client.new "10.0.0.3:6060", :timeout => nil, :keep_alive => true
39
+ #
40
+ # === Configuration options
41
+ #
42
+ # +timeout+:: if specified (seconds), calls to varnish
43
+ # will be wrapped in a timeout, default is 1 second.
44
+ # Disable with <tt>:timeout => nil</tt>
45
+ # +keep_alive+:: if true, the connection is kept alive by sending
46
+ # ping commands to varnishd every few seconds
47
+ # +secret_file+:: specifies the authentication secret file
48
+ def initialize(*args)
49
+ opts = {}
50
+
51
+ case args.length
52
+ when 0
53
+ self.server = DEFAULT_HOST
54
+ when 1
55
+ arg = args[0]
56
+ case arg
57
+ when String
58
+ self.server = arg
59
+ when Hash
60
+ self.server = DEFAULT_HOST
61
+ opts = arg
62
+ end
63
+ when 2
64
+ self.server = args[0]
65
+ opts = args[1]
66
+ else
67
+ raise ArgumentError, "wrong number of arguments (#{args.length} for 2)"
68
+ end
69
+
70
+ opts = DEFAULT_OPTS.merge(opts)
71
+ @timeout = opts[:timeout]
72
+ @keep_alive = opts[:keep_alive]
73
+ @secret_file = opts[:secret_file]
74
+
75
+ @mutex = Mutex.new
76
+ end
77
+
78
+ # Set the varnishd management host and port.
79
+ # Expects a string as "hostname" or "hostname:port"
80
+ def server=(server)
81
+ @host, @port = server.split(':')
82
+ @port = (@port || DEFAULT_PORT).to_i
83
+ server
84
+ end
85
+
86
+ # Returns the varnishd management host and port as "hostname:port"
87
+ def server
88
+ "#{@host}:#{@port}"
89
+ end
90
+
91
+ # Manipulate the VCL configuration
92
+ #
93
+ # .vcl :load, <configname>, <filename>
94
+ # .vcl :inline, <configname>, <quoted_VCLstring>
95
+ # .vcl :use, <configname>
96
+ # .vcl :discard, <configname>
97
+ # .vcl :list
98
+ # .vcl :show, <configname>
99
+ #
100
+ # Returns an array of VCL configurations for :list, and the servers
101
+ # response as string otherwise
102
+ #
103
+ # Ex.:
104
+ # v = Varnish::Client.new
105
+ # v.vcl :list
106
+ # #=> [["active", 0, "boot"]]
107
+ #
108
+ # v.vcl :load, "newconf", "/etc/varnish/myconf.vcl"
109
+ #
110
+ #
111
+ def vcl(op, *params)
112
+ response = cmd("vcl.#{op}", *params)
113
+ case op
114
+ when :list
115
+ response.split("\n").map do |line|
116
+ a = line.split(/\s+/, 3)
117
+ [a[0], a[1].to_i, a[2]]
118
+ end
119
+ else
120
+ response
121
+ end
122
+ end
123
+
124
+ # Purge objects from the cache or show the purge queue.
125
+ #
126
+ # Takes one or two arguments:
127
+ #
128
+ # 1.
129
+ # .purge :url, <regexp>
130
+ # .purge :hash, <regexp>
131
+ #
132
+ # <regexp> is a string containing a varnish compatible regexp
133
+ #
134
+ # 2.
135
+ # .purge <costum-purge-conditions>
136
+ # .purge :list
137
+ #
138
+ # Returns true for purging, returns an array containing the purge queue
139
+ # for :list
140
+ #
141
+ # Ex.:
142
+ # v = Varnish::Client.new
143
+ # v.purge :url, '.*'
144
+ #
145
+ # v.purge "req.http.host ~ www.foo.com && req.http.url ~ images"
146
+ #
147
+ # v.purge :list
148
+ # #=> [[1, "req.url ~ .*"]]
149
+ #
150
+ def purge(*args)
151
+ c = 'purge'
152
+ c << ".#{args.shift}" if [:url, :hash, :list].include?(args.first)
153
+ response = cmd(c, *args)
154
+ case c
155
+ when 'purge.list'
156
+ response.split("\n").map do |line|
157
+ a = line.split("\t")
158
+ [a[0].to_i, a[1]]
159
+ end
160
+ else
161
+ bool response
162
+ end
163
+ end
164
+
165
+ # Ping the server to keep the connection alive
166
+ def ping(timestamp = nil)
167
+ cmd("ping", timestamp)
168
+ end
169
+
170
+ # Returns a hash of status information
171
+ #
172
+ # Ex.:
173
+ # v = Varnish::Client.new
174
+ # v.stats
175
+ # => {"Total header bytes"=>0, "Cache misses"=>0 ...}
176
+ def stats
177
+ result = cmd("stats")
178
+ Hash[*result.split("\n").map { |line|
179
+ stat = line.strip!.split(/\s+/, 2)
180
+ [stat[1], stat[0].to_i]
181
+ }.flatten
182
+ ]
183
+ end
184
+
185
+ # Set and show parameters
186
+ #
187
+ # .param :show, [-l], [<param>]
188
+ # .param :set, <param>, <value>
189
+ def param(op, *args)
190
+ cmd("param.#{op}", *args)
191
+ end
192
+
193
+ # Returns the status string from varnish.
194
+ # See also #running? and #stopped?
195
+ def status
196
+ cmd("status")
197
+ end
198
+
199
+ def start
200
+ bool cmd("start")
201
+ end
202
+
203
+ def stop
204
+ bool cmd("stop")
205
+ end
206
+
207
+ def running?
208
+ bool status =~ /running/
209
+ end
210
+
211
+ def stopped?
212
+ bool status =~ /stopped/
213
+ end
214
+
215
+ # close the connection to varnishd.
216
+ # Note that the connection will automatically be re-established
217
+ # when another command is issued.
218
+ def disconnect
219
+ if connected?
220
+ @conn.write "quit\n"
221
+ @conn.gets
222
+ @conn.close unless @conn.closed?
223
+ end
224
+ end
225
+
226
+ def connected?
227
+ bool @conn && !@conn.closed?
228
+ end
229
+
230
+ private
231
+
232
+ # Sends a command to varnishd.
233
+ # Raises a Varnish::CommandFailed error when a non-200 status is returned
234
+ # Returns the response text
235
+ def cmd(name, *params)
236
+ @mutex.synchronize do
237
+ connect unless connected?
238
+ @conn.write "#{name} #{params.join(' ').gsub('\\', '\\\\\\')}\n"
239
+ status, length = conn_gets.split # <status> <content_length>\n
240
+ content = conn_read(length.to_i + 1) # +1 = \n
241
+ content.chomp!
242
+ raise CommandFailed, "Command #{name} returned with status #{status}: #{content}" if status.to_i != 200
243
+ content
244
+ end
245
+ end
246
+
247
+ def get_challenge_or_banner
248
+ status, length = conn_gets.split # <status> <content_length>\n
249
+ content = conn_read(length.to_i + 1) # +1 = \n
250
+ if status.to_i == 107
251
+ @conn.write "auth #{auth_response(content[0,32])}\n"
252
+ end
253
+ end
254
+
255
+ def connect
256
+ @conn = SocketFactory.tcp_socket(@host, @port, @timeout)
257
+ get_challenge_or_banner
258
+
259
+ # If keep alive, we ping the server every few seconds.
260
+ if @keep_alive
261
+ varnish = self
262
+ Thread.new do
263
+ while(true) do
264
+ if varnish.connected?
265
+ varnish.ping
266
+ sleep 5
267
+ else
268
+ break
269
+ end
270
+ end
271
+ end
272
+ end
273
+
274
+ @conn
275
+ end
276
+
277
+ def conn_gets
278
+ @conn.gets || raise(BrokenConnection, "Expected to read one line from Varnish, got nil")
279
+ end
280
+
281
+ def conn_read(bytes)
282
+ @conn.read(bytes) || raise(BrokenConnection, "Expected to read #{bytes} bytes from Varnish, got nil")
283
+ end
284
+
285
+ def auth_response(challenge)
286
+ ctx = Digest::SHA2.new
287
+ ctx << challenge
288
+ ctx << "\n"
289
+ ctx << File.read(secret_file)
290
+ ctx << challenge
291
+ ctx << "\n"
292
+ puts "#{ctx.to_s}"
293
+ ctx.to_s
294
+ end
295
+
296
+ # converts +value+ into a boolean
297
+ def bool(value)
298
+ !!value
299
+ end
300
+
301
+ end
302
+ end
@@ -0,0 +1,57 @@
1
+ module Varnish
2
+ # Wrapper around Ruby's Socket.
3
+ #
4
+ # Uses Mike Perhams superior (in both reliability and
5
+ # performance) connection technique with proper timeouts:
6
+ # See: http://github.com/mperham/memcache-client
7
+ class SocketFactory
8
+
9
+ begin
10
+ # Try to use the SystemTimer gem instead of Ruby's timeout library
11
+ # when running on something that looks like Ruby 1.8.x. See:
12
+ # http://ph7spot.com/articles/system_timer
13
+ # We don't want to bother trying to load SystemTimer on jruby and
14
+ # ruby 1.9+.
15
+ if RUBY_VERSION =~ /^1\.8\./ and RUBY_PLATFORM !~ /java/
16
+ require 'system_timer'
17
+ Timer = SystemTimer
18
+ else
19
+ require 'timeout'
20
+ Timer = Timeout
21
+ end
22
+ rescue LoadError => e
23
+ $stderr.puts "[klarlack] Could not load SystemTimer gem, falling back to Ruby's slower/unsafe timeout library: #{e.message}"
24
+ require 'timeout'
25
+ Timer = Timeout
26
+ end
27
+
28
+ def self.tcp_socket(host, port, timeout = nil)
29
+ addr = Socket.getaddrinfo(host, nil)
30
+ sock = Socket.new(Socket.const_get(addr[0][0]), Socket::SOCK_STREAM, 0)
31
+
32
+ if timeout
33
+ secs = Integer(timeout)
34
+ usecs = Integer((timeout - secs) * 1_000_000)
35
+ optval = [secs, usecs].pack("l_2")
36
+ sock.setsockopt Socket::SOL_SOCKET, Socket::SO_RCVTIMEO, optval
37
+ sock.setsockopt Socket::SOL_SOCKET, Socket::SO_SNDTIMEO, optval
38
+
39
+ # Socket timeouts don't work for more complex IO operations
40
+ # like gets which lay on top of read. We need to fall back to
41
+ # the standard Timeout mechanism.
42
+ sock.instance_eval <<-EOR
43
+ alias :blocking_gets :gets
44
+ def gets
45
+ Timer.timeout(#{timeout}) do
46
+ self.blocking_gets
47
+ end
48
+ end
49
+ EOR
50
+ end
51
+ sock.connect(Socket.pack_sockaddr_in(port, addr[0][3]))
52
+ sock.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
53
+ sock
54
+ end
55
+
56
+ end
57
+ end
@@ -0,0 +1,198 @@
1
+ require 'spec/spec_helper'
2
+
3
+ describe Varnish::Client do
4
+
5
+ before(:each) do
6
+ @varnish = Varnish::Client.new "127.0.0.1:6082"
7
+ end
8
+
9
+ describe '(connection handling)' do
10
+
11
+ it 'should not be connected on object instantiation' do
12
+ @varnish.connected?.should be_false
13
+ end
14
+
15
+ it 'should not raise an error when trying to disconnect a non-connected client' do
16
+ lambda { @varnish.disconnect }.should_not raise_error
17
+ end
18
+
19
+ it 'should automatically connect when a command is issued' do
20
+ @varnish.ping
21
+ @varnish.connected?.should be_true
22
+ end
23
+
24
+ it 'should use timeouts when sending commands' do
25
+ Varnish::SocketFactory::Timer.should_receive(:timeout).and_return("200 0")
26
+ @varnish.timeout = 10
27
+ @varnish.ping
28
+ end
29
+
30
+ it 'should be possible to disable timeouts' do
31
+ Varnish::SocketFactory::Timer.should_not_receive(:timeout)
32
+ @varnish.timeout = nil
33
+ @varnish.ping
34
+ end
35
+
36
+ it '#disconnect should close the connection' do
37
+ @varnish.ping
38
+ @varnish.connected?.should be_true
39
+ @varnish.disconnect
40
+ @varnish.connected?.should be_false
41
+ end
42
+
43
+ it 'given keep_alive is set, the connection should be kept alive with pings' do
44
+ @varnish.keep_alive = true
45
+ @varnish.should_receive :ping
46
+ @varnish.send :connect
47
+ end
48
+
49
+ it 'given keep_alive is not set, no pings should be sent to varnishd' do
50
+ @varnish.keep_alive = false
51
+ @varnish.should_not_receive :ping
52
+ @varnish.send :connect
53
+ end
54
+
55
+ it '#server should return the host and port for the connection' do
56
+ @varnish.host = "foohost"
57
+ @varnish.port = 1234
58
+ @varnish.server.should == "foohost:1234"
59
+ end
60
+
61
+ it '#server= should set the host and port for the connection' do
62
+ @varnish.server = "blahost:9876"
63
+ @varnish.host.should == "blahost"
64
+ @varnish.port.should == 9876
65
+ end
66
+
67
+ end
68
+
69
+ describe '(commands)' do
70
+
71
+ before(:each) do
72
+ ensure_started
73
+ end
74
+
75
+ # ... the specs for #param, #purge and #vcl could be better ...
76
+
77
+ it '#param should send the param command to varnishd' do
78
+ @varnish.param(:show).should_not be_empty
79
+ end
80
+
81
+ it '#purge should allow purging by url, hash and custom fields' do
82
+ @varnish.purge(:url, '^/articles/.*').should be_true
83
+ @varnish.purge(:hash, 12345).should be_true
84
+ @varnish.purge("req.http.host", "~", "www.example.com").should be_true
85
+ @varnish.purge("req.http.host ~ www.example.com").should be_true
86
+ end
87
+
88
+ it '#purge with :list should return an array with queued purges' do
89
+ @varnish.purge(:url, '^/posts/.*')
90
+ list = @varnish.purge(:list)
91
+ list.last[0].should be_kind_of(Integer)
92
+ list.last[1].should == "req.url ~ ^/posts/.*"
93
+ end
94
+
95
+ it '#vcl with :list should return an array of VCL configurations' do
96
+ list = @varnish.vcl(:list)
97
+ list.should_not be_empty
98
+ list.should be_kind_of(Array)
99
+ list.first[0].should be_kind_of(String)
100
+ list.first[1].should be_kind_of(Integer)
101
+ list.first[2].should be_kind_of(String)
102
+ end
103
+
104
+ it '#ping should send a ping to the server and return a string containing the response' do
105
+ @varnish.ping.should =~ /^PONG \d+/
106
+ end
107
+
108
+
109
+ it '#status should return a string explaining the daemons status' do
110
+ @varnish.status.should =~ /running|stopped|stopping|starting/
111
+ end
112
+
113
+ it "#stats should return a hash containing status information" do
114
+ stats = @varnish.stats
115
+ stats.should_not be_empty
116
+ stats.values.each {|v| v.should be_kind_of(Integer) }
117
+ stats.keys.each {|k| k.should_not be_empty }
118
+ end
119
+
120
+ end
121
+
122
+ describe '(regression)' do
123
+
124
+ it '#purge.hash with regex containing backslashes should be escaped properly' do
125
+ test_regex = '/home\?x=1'
126
+ @varnish.purge :hash, test_regex
127
+ list = @varnish.purge :list
128
+ list.flatten.join.should include(test_regex)
129
+ end
130
+
131
+ end
132
+
133
+ describe '(broken connection)' do
134
+
135
+ before(:each) do
136
+ fake_connection!(:connected => true, :return => "200 1\n")
137
+ end
138
+
139
+ it 'should fail with a Varnish::Error when the connection does return nil for gets' do
140
+ @conn.stub!(:gets).and_return(nil)
141
+ lambda { @varnish.ping }.should raise_error(Varnish::BrokenConnection)
142
+ end
143
+
144
+ it 'should fail with a Varnish::Error when the connection does return nil for read' do
145
+ @conn.stub!(:read).and_return(nil)
146
+ lambda { @varnish.ping }.should raise_error(Varnish::BrokenConnection)
147
+ end
148
+
149
+ end
150
+
151
+ describe '(daemon lifecycle)' do
152
+
153
+ it '#start, #stop, #running?, #stopped? should bahave as advertised' do
154
+ ensure_stopped # issues #stop
155
+ @varnish.stopped?.should be_true
156
+ @varnish.running?.should be_false
157
+ ensure_started # issues #start
158
+ @varnish.stopped?.should be_false
159
+ @varnish.running?.should be_true
160
+ end
161
+
162
+ it 'starting an already started daemon should raise an error' do
163
+ ensure_started
164
+ lambda { @varnish.start }.should raise_error(Varnish::CommandFailed)
165
+ end
166
+
167
+ it 'stopping an already stopped daemon should raise an error' do
168
+ ensure_stopped
169
+ lambda { @varnish.stop }.should raise_error(Varnish::CommandFailed)
170
+ end
171
+
172
+ end
173
+
174
+ def ensure_started
175
+ @varnish.start if @varnish.stopped?
176
+ while(!@varnish.running?) do sleep 0.1 end
177
+ end
178
+
179
+ def ensure_stopped
180
+ @varnish.stop if @varnish.running?
181
+ while(!@varnish.stopped?) do sleep 0.1 end
182
+ end
183
+
184
+ class FakeConn
185
+ attr_accessor :retval
186
+ def read(*args) @retval end
187
+ def gets(*args) @retval end
188
+ def write(str) str.to_s.size end
189
+ end
190
+
191
+ def fake_connection!(opts = {})
192
+ @conn = FakeConn.new
193
+ @conn.retval = opts[:return] || ''
194
+ @varnish.stub!(:connected?).and_return(opts[:connected] || false)
195
+ @varnish.instance_variable_set('@conn', @conn)
196
+ end
197
+
198
+ end
@@ -0,0 +1,5 @@
1
+ require 'spec'
2
+
3
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
4
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
5
+ require 'klarlack'
metadata ADDED
@@ -0,0 +1,78 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: tikh-klarlack
3
+ version: !ruby/object:Gem::Version
4
+ hash: 17
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 0
9
+ - 7
10
+ version: 0.0.7
11
+ platform: ruby
12
+ authors:
13
+ - "Max Sch\xC3\xB6fmann"
14
+ - Konstantin Tikhonov
15
+ autorequire:
16
+ bindir: bin
17
+ cert_chain: []
18
+
19
+ date: 2010-04-07 00:00:00 +04:00
20
+ default_executable:
21
+ dependencies: []
22
+
23
+ description:
24
+ email: max@pragmatic-it.de
25
+ executables: []
26
+
27
+ extensions: []
28
+
29
+ extra_rdoc_files:
30
+ - LICENSE
31
+ - README.rdoc
32
+ files:
33
+ - LICENSE
34
+ - README.rdoc
35
+ - Rakefile
36
+ - VERSION.yml
37
+ - lib/klarlack.rb
38
+ - lib/varnish/client.rb
39
+ - lib/varnish/socket_factory.rb
40
+ - spec/klarlack_spec.rb
41
+ - spec/spec_helper.rb
42
+ has_rdoc: true
43
+ homepage: http://github.com/schoefmax/klarlack
44
+ licenses: []
45
+
46
+ post_install_message:
47
+ rdoc_options:
48
+ - --charset=UTF-8
49
+ require_paths:
50
+ - lib
51
+ required_ruby_version: !ruby/object:Gem::Requirement
52
+ none: false
53
+ requirements:
54
+ - - ">="
55
+ - !ruby/object:Gem::Version
56
+ hash: 3
57
+ segments:
58
+ - 0
59
+ version: "0"
60
+ required_rubygems_version: !ruby/object:Gem::Requirement
61
+ none: false
62
+ requirements:
63
+ - - ">="
64
+ - !ruby/object:Gem::Version
65
+ hash: 3
66
+ segments:
67
+ - 0
68
+ version: "0"
69
+ requirements: []
70
+
71
+ rubyforge_project:
72
+ rubygems_version: 1.3.7
73
+ signing_key:
74
+ specification_version: 3
75
+ summary: ruby client for varnishd's admin interface
76
+ test_files:
77
+ - spec/klarlack_spec.rb
78
+ - spec/spec_helper.rb