callsite 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,66 @@
1
+ = Callsite
2
+
3
+ Caller/backtrace parser with some useful utilities for manipulating the load path, and doing other relative things.
4
+
5
+ == Usage
6
+
7
+ The primary thing you can do is parse a caller line(s).
8
+
9
+ pp Callsite.parse(caller)
10
+
11
+ Gives back
12
+
13
+ => [#<struct Callsite::Line
14
+ filename="/opt/local/lib/ruby/1.8/irb/workspace.rb",
15
+ line=52,
16
+ method="irb_binding">,
17
+ #<struct Callsite::Line filename="", line=0, method=nil>]
18
+
19
+ This is also suitable for parsing a backtrace, to get detailed information about it.
20
+
21
+ There are also five methods which patch existing objects to give you powerful usage of the caller.
22
+
23
+ === Callsite.activate_string_methods
24
+
25
+ This gives you the ~@ method on +String+, which takes any string, and gives you a relative version of it, treating it as a file path. For example,
26
+
27
+ ~'lib/callsite.rb'
28
+
29
+ Gives you (on my laptop)
30
+
31
+ => "/Users/joshua/Development/callsite/lib/callsite.rb"
32
+
33
+ === Callsite.activate_file_methods
34
+
35
+ This adds the +File.relative+ method. File.relative(file_path) has the same effect as ~file_path.
36
+
37
+ === Callsite.activate_module_methods
38
+
39
+ This adds +autoload_relative+ onto Module. This allows you to do the following.
40
+
41
+ module MyModule
42
+ autoload_relative :Whatever, "lib/whatever"
43
+ end
44
+
45
+ In this case, lib/whatever will be treated as a relative path from the definition of the module.
46
+
47
+ === Callsite.activate_kernel_dir_methods
48
+
49
+ This adds the __DIR_REL__ and optionally __DIR__ and require_relative methods to Kernel. __DIR__ or __DIR_REL__ will give you your current directory, much like
50
+ __FILE__ gives you the current __FILE__ you're in. +require_relative+ is like +require+ .. only, it's relative.
51
+
52
+ === Callsite.activate_kernel_require_methods
53
+
54
+ This adds a couple of weird methods to Kernel, require_next and require_all. There search your current $LOAD_PATH, and require the next file (ingoring the current one you're in on the load_path) or require all files of a given name.
55
+
56
+ === Callsite.activate_load_path_methods
57
+
58
+ This adds some super useful methods to $LOAD_PATH. There are find_file (finds a single file on your load path), find_all_files (finds all of em), add_current (adds to the end of the load path your current dir) and add_current! (adds it to the beginning).
59
+
60
+ == I lied
61
+
62
+ I said there were 5, I meant 6. There are 5 lights.
63
+
64
+ == This deprecates +dirge+ and +load_path_find+
65
+
66
+ Once you have this installed, you can use require 'dirge' and require 'load_path_find' to get exactly the functionality you had before.
@@ -0,0 +1,37 @@
1
+ begin
2
+ require 'jeweler'
3
+ Jeweler::Tasks.new do |s|
4
+ s.name = "callsite"
5
+ s.description = s.summary = "Caller/backtrace parser with some useful utilities for manipulating the load path, and doing other relative things."
6
+ s.email = "joshbuddy@gmail.com"
7
+ s.homepage = "http://github.com/joshbuddy/callsite"
8
+ s.authors = ["Joshua Hull"]
9
+ s.files = FileList["[A-Z]*", "{lib}/**/*"]
10
+ end
11
+ Jeweler::GemcutterTasks.new
12
+ rescue LoadError
13
+ puts "Jeweler not available. Install it with: sudo gem install technicalpickles-jeweler -s http://gems.github.com"
14
+ end
15
+
16
+ require 'spec'
17
+ require 'spec/rake/spectask'
18
+ task :spec => ['spec:dirge', 'spec:load_path_find']
19
+ namespace(:spec) do
20
+ Spec::Rake::SpecTask.new(:dirge) do |t|
21
+ t.spec_opts ||= []
22
+ t.spec_opts << "-rubygems"
23
+ t.spec_opts << '-rlib/dirge'
24
+ t.spec_opts << "--options" << "spec/spec.opts"
25
+ t.spec_files = FileList['spec/**/dirge_spec.rb']
26
+ end
27
+
28
+ Spec::Rake::SpecTask.new(:load_path_find) do |t|
29
+ t.spec_opts ||= []
30
+ t.spec_opts << "-rubygems"
31
+ t.spec_opts << '-rlib/load_path_find'
32
+ t.spec_opts << "--options" << "spec/spec.opts"
33
+ t.spec_files = FileList['spec/**/load_path_find_spec.rb']
34
+ end
35
+
36
+ end
37
+
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.0.1
@@ -0,0 +1,105 @@
1
+ $LOAD_PATH << File.dirname(__FILE__)
2
+
3
+ module Callsite
4
+ UnparsableCallLine = Class.new(RuntimeError)
5
+ Line = Struct.new(:filename, :line, :method)
6
+
7
+ def self.__DIR_REL__(called_from = nil)
8
+ called_from ||= caller.first
9
+ caller_path = parse(called_from).filename
10
+ caller_path = '.' if caller_path == ''
11
+ File.expand_path(File.dirname(caller_path))
12
+ end
13
+
14
+ def self.parse(input)
15
+ if input.is_a?(Array)
16
+ block_given? ?
17
+ input.each{|line| yield parse(line)} :
18
+ input.map{|line| parse(line)}
19
+ else
20
+ if match = input.match(/^(.*?)(:(\d+))(:in `(.*)')?$/)
21
+ Line.new(match[1], match[3].to_i, match[5])
22
+ else
23
+ raise UnparsableCallLine.new("unable to parse #{input}")
24
+ end
25
+ end
26
+ end
27
+
28
+ def self.activate_string_methods
29
+ activate_kernel_dir_methods
30
+ ::String.send(:include, StringMethods)
31
+ end
32
+
33
+ def self.activate_file_methods
34
+ activate_kernel_dir_methods
35
+ ::File.send(:extend, FileMethods)
36
+ end
37
+
38
+ def self.activate_module_methods
39
+ activate_kernel_dir_methods
40
+ ::Module.send(:include, ModuleMethods)
41
+ end
42
+
43
+ def self.activate_kernel_dir_methods
44
+ require 'loaders/kernel_dir'
45
+ end
46
+
47
+ def self.activate_kernel_require_methods
48
+ activate_loadpath_methods
49
+ require 'loaders/kernel_require'
50
+ end
51
+
52
+ def self.activate_loadpath_methods
53
+ activate_kernel_dir_methods
54
+ require 'loaders/load_path'
55
+ end
56
+
57
+ module StringMethods
58
+ unless method_defined?(:~@)
59
+ def ~@
60
+ File.expand_path(File.join(Kernel.__DIR_REL__(caller.first), self))
61
+ end
62
+ end
63
+ end
64
+
65
+ module FileMethods
66
+ def relative(path)
67
+ File.expand_path(File.join(Kernel.__DIR_REL__(caller.first), path))
68
+ end
69
+ end
70
+
71
+ module ModuleMethods
72
+ unless method_defined?(:autoload_relative)
73
+ def autoload_relative(name, filename)
74
+ autoload name, File.join(Kernel.__DIR_REL__(caller.first), filename)
75
+ end
76
+ end
77
+ end
78
+
79
+ module LoadPathMethods
80
+ def find_file(file)
81
+ find_all_files(file){|f| return f}
82
+ nil
83
+ end
84
+
85
+ def find_all_files(file, ext = nil)
86
+ file += ext if ext and File.extname(file) != ext
87
+ inject([]){|ary, path|
88
+ target = File.expand_path(file, path)
89
+ if File.readable?(target)
90
+ ary << target
91
+ yield target if block_given?
92
+ end
93
+ ary
94
+ }
95
+ end
96
+
97
+ def add_current
98
+ self << __DIR_REL__(caller.first)
99
+ end
100
+
101
+ def add_current!
102
+ self.unshift(__DIR_REL__(caller.first))
103
+ end
104
+ end
105
+ end
@@ -0,0 +1,6 @@
1
+ require 'callsite'
2
+ Callsite.activate_kernel_require_methods
3
+ Callsite.activate_kernel_dir_methods
4
+ Callsite.activate_string_methods
5
+ Callsite.activate_file_methods
6
+ Callsite.activate_module_methods
@@ -0,0 +1,7 @@
1
+ require 'callsite'
2
+ Callsite.activate_loadpath_methods
3
+ Callsite.activate_kernel_require_methods
4
+ Callsite.activate_kernel_dir_methods
5
+ Callsite.activate_string_methods
6
+ Callsite.activate_file_methods
7
+ Callsite.activate_module_methods
@@ -0,0 +1,17 @@
1
+ module Kernel
2
+ def __DIR_REL__(called_from = nil)
3
+ parsed_line = Callsite.parse(called_from || caller.first)
4
+ parsed_line && File.expand_path(File.dirname(parsed_line.filename))
5
+ end
6
+
7
+ unless method_defined?(:__DIR__)
8
+ alias_method :__DIR__, :__DIR_REL__
9
+ end
10
+
11
+ unless method_defined?(:require_relative)
12
+ def require_relative(path)
13
+ require File.join(__DIR_REL__(caller.first), path)
14
+ end
15
+ end
16
+ end
17
+
@@ -0,0 +1,18 @@
1
+ module Kernel
2
+ def require_all(req)
3
+ $LOAD_PATH.find_all_files(req, ".rb") { |file| require file }
4
+ end
5
+
6
+ def require_next(req)
7
+ found, current = false, File.expand_path(caller.first[/^[^:]+/])
8
+ $LOAD_PATH.find_all_files(req, ".rb") do |file|
9
+ if found
10
+ $LOADED_FEATURES << req
11
+ return require(file)
12
+ else
13
+ found = current == file
14
+ end
15
+ end
16
+ require req
17
+ end
18
+ end
@@ -0,0 +1,26 @@
1
+ $LOAD_PATH.instance_eval do
2
+ def find_file(file)
3
+ find_all_files(file){|f| return f}
4
+ nil
5
+ end
6
+
7
+ def find_all_files(file, ext = nil)
8
+ file += ext if ext and File.extname(file) != ext
9
+ inject([]){|ary, path|
10
+ target = File.expand_path(file, path)
11
+ if File.readable?(target)
12
+ ary << target
13
+ yield target if block_given?
14
+ end
15
+ ary
16
+ }
17
+ end
18
+
19
+ def add_current
20
+ self << __DIR_REL__(caller.first)
21
+ end
22
+
23
+ def add_current!
24
+ self.unshift(__DIR_REL__(caller.first))
25
+ end
26
+ end
@@ -0,0 +1 @@
1
+ $state1 = true
@@ -0,0 +1,2 @@
1
+ $test2 = 1
2
+ require_next "test2"
@@ -0,0 +1 @@
1
+ $state2 = true
@@ -0,0 +1 @@
1
+ $test2 = 2 if $test2 == 1
@@ -0,0 +1,33 @@
1
+ describe 'Dirge' do
2
+ it "should resolve a path through String#~" do
3
+ (~'test:2test/test').should == File.expand_path(File.join(File.dirname(__FILE__), 'test:2test', 'test'))
4
+ end
5
+
6
+ it "should resolve a path through File#relative" do
7
+ File.relative('test:2test/test').should == File.expand_path(File.join(File.dirname(__FILE__), 'test:2test', 'test'))
8
+ end
9
+
10
+ it 'should require a relative path' do
11
+ proc {
12
+ require_relative 'test:2test/test'
13
+ }.should raise_error(RuntimeError, 'okay okay, you included me')
14
+ end
15
+
16
+ it 'should autoload a relative path' do
17
+ proc {
18
+ mod = Module.new do
19
+ autoload_relative :TestingTime, 'test:2test/test'
20
+ end
21
+ mod::TestingTime
22
+ }.should raise_error(RuntimeError, 'okay okay, you included me')
23
+ end
24
+
25
+ it "should define __DIR__" do
26
+ __DIR__.should == File.expand_path(File.dirname(__FILE__))
27
+ end
28
+
29
+ it "should define __DIR__ with a custom caller" do
30
+ __DIR__('testing/test.rb:3').should == File.expand_path('testing')
31
+ end
32
+
33
+ end
@@ -0,0 +1,62 @@
1
+ require 'lib/load_path_find'
2
+
3
+ $: << File.expand_path(File.join(File.dirname(__FILE__), 'data', 'dir1'))
4
+ $: << File.expand_path(File.join(File.dirname(__FILE__), 'data', 'dir2'))
5
+
6
+ describe 'load path find' do
7
+ it "should find a file on the load path" do
8
+ target = File.join('file1')
9
+ $:.find_file(target)[-target.size, target.size].should == target
10
+ end
11
+
12
+ it "should find a directory on the load path" do
13
+ target = "data/dir1"
14
+ $:.find_file("../dir1")[-target.size, target.size].should == target
15
+ end
16
+
17
+ it "should find the first file when its ambigious" do
18
+ target = File.join('file1')
19
+ expected_target = File.join('dir1', 'file1')
20
+ $:.find_file(target)[-expected_target.size, expected_target.size].should == expected_target
21
+ end
22
+
23
+ it "should find all files that match" do
24
+ target = File.join('file1')
25
+ expected_target = File.join('dir1', 'file1')
26
+ $:.find_all_files(target).should == [
27
+ File.expand_path(File.join(File.dirname(__FILE__), 'data', 'dir1', 'file1')),
28
+ File.expand_path(File.join(File.dirname(__FILE__), 'data', 'dir2', 'file1'))
29
+ ]
30
+ end
31
+
32
+ it "should yield all files that match if a block is given" do
33
+ target = File.join('file1')
34
+ mock = Object.new
35
+ mock.should_receive(:hello).exactly(2).times
36
+ $:.find_all_files(target) { mock.hello }
37
+ end
38
+
39
+ it "should add the current path" do
40
+ $LOAD_PATH.add_current
41
+ $LOAD_PATH.last.should == __DIR__
42
+ end
43
+
44
+ it "should add the current path to the start" do
45
+ $LOAD_PATH.add_current!
46
+ $LOAD_PATH.first.should == __DIR__
47
+ end
48
+
49
+ it "should require_all" do
50
+ $state1.should be_nil
51
+ $state2.should be_nil
52
+ require_all('test')
53
+ $state1.should be_true
54
+ $state2.should be_true
55
+ end
56
+
57
+ it "should require_next" do
58
+ require 'test2'
59
+ $test2.should == 2
60
+ end
61
+
62
+ end
@@ -0,0 +1 @@
1
+ raise 'okay okay, you included me'
metadata ADDED
@@ -0,0 +1,76 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: callsite
3
+ version: !ruby/object:Gem::Version
4
+ prerelease: false
5
+ segments:
6
+ - 0
7
+ - 0
8
+ - 1
9
+ version: 0.0.1
10
+ platform: ruby
11
+ authors:
12
+ - Joshua Hull
13
+ autorequire:
14
+ bindir: bin
15
+ cert_chain: []
16
+
17
+ date: 2010-05-20 00:00:00 -04:00
18
+ default_executable:
19
+ dependencies: []
20
+
21
+ description: Caller/backtrace parser with some useful utilities for manipulating the load path, and doing other relative things.
22
+ email: joshbuddy@gmail.com
23
+ executables: []
24
+
25
+ extensions: []
26
+
27
+ extra_rdoc_files:
28
+ - README.rdoc
29
+ files:
30
+ - README.rdoc
31
+ - Rakefile
32
+ - VERSION
33
+ - lib/callsite.rb
34
+ - lib/dirge.rb
35
+ - lib/load_path_find.rb
36
+ - lib/loaders/kernel_dir.rb
37
+ - lib/loaders/kernel_require.rb
38
+ - lib/loaders/load_path.rb
39
+ has_rdoc: true
40
+ homepage: http://github.com/joshbuddy/callsite
41
+ licenses: []
42
+
43
+ post_install_message:
44
+ rdoc_options:
45
+ - --charset=UTF-8
46
+ require_paths:
47
+ - lib
48
+ required_ruby_version: !ruby/object:Gem::Requirement
49
+ requirements:
50
+ - - ">="
51
+ - !ruby/object:Gem::Version
52
+ segments:
53
+ - 0
54
+ version: "0"
55
+ required_rubygems_version: !ruby/object:Gem::Requirement
56
+ requirements:
57
+ - - ">="
58
+ - !ruby/object:Gem::Version
59
+ segments:
60
+ - 0
61
+ version: "0"
62
+ requirements: []
63
+
64
+ rubyforge_project:
65
+ rubygems_version: 1.3.6
66
+ signing_key:
67
+ specification_version: 3
68
+ summary: Caller/backtrace parser with some useful utilities for manipulating the load path, and doing other relative things.
69
+ test_files:
70
+ - spec/data/dir1/test.rb
71
+ - spec/data/dir1/test2.rb
72
+ - spec/data/dir2/test.rb
73
+ - spec/data/dir2/test2.rb
74
+ - spec/dirge_spec.rb
75
+ - spec/load_path_find_spec.rb
76
+ - spec/test:2test/test.rb