sql_mapper 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.
- data/lib/sql_mapper.rb +139 -0
- metadata +103 -0
data/lib/sql_mapper.rb
ADDED
@@ -0,0 +1,139 @@
|
|
1
|
+
require 'singleton'
|
2
|
+
require 'active_record'
|
3
|
+
|
4
|
+
module ActiveRecord
|
5
|
+
module SqlMapper
|
6
|
+
class Context
|
7
|
+
include Singleton
|
8
|
+
|
9
|
+
def initialize
|
10
|
+
@result_class = Struct
|
11
|
+
@queries = {}
|
12
|
+
end
|
13
|
+
|
14
|
+
def queries
|
15
|
+
@queries.dup
|
16
|
+
end
|
17
|
+
|
18
|
+
def map(name, sql, result_class=nil)
|
19
|
+
mapping = QueryMapping.new name, sql, (result_class || @result_class)
|
20
|
+
@queries[name] = mapping
|
21
|
+
end
|
22
|
+
|
23
|
+
def result_class(clazz=nil)
|
24
|
+
@result_class = clazz if not clazz.nil? and clazz.is_a? Class
|
25
|
+
@result_class
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
class QueryMapping
|
30
|
+
attr_reader :key
|
31
|
+
attr_accessor :sql, :result_class
|
32
|
+
|
33
|
+
def initialize(key, sql, result_class=Context.result_class)
|
34
|
+
@key = key
|
35
|
+
@sql = sql
|
36
|
+
@result_class = result_class
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
class DefaultExecStrategy
|
41
|
+
def initialize(sql, result_class)
|
42
|
+
@sql = sql
|
43
|
+
@result_class = result_class
|
44
|
+
end
|
45
|
+
|
46
|
+
def do_fetch
|
47
|
+
@raw_results = ActiveRecord::Base.connection.exec_query(@sql)
|
48
|
+
end
|
49
|
+
|
50
|
+
def process_results
|
51
|
+
@raw_results.rows.map{|row| @result_class.new *row}
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
class StructExecStrategy < DefaultExecStrategy
|
56
|
+
def initialize(sql, result_class)
|
57
|
+
super(sql, result_class)
|
58
|
+
end
|
59
|
+
|
60
|
+
def do_fetch
|
61
|
+
@raw_results = ActiveRecord::Base.connection.exec_query(@sql)
|
62
|
+
col_names = @raw_results.columns.map{|c| c.to_sym}
|
63
|
+
@result_class = @result_class.new(*col_names)
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
class HashExecStrategy
|
68
|
+
def initialize(sql, result_class)
|
69
|
+
@sql = sql
|
70
|
+
@result_class = result_class
|
71
|
+
end
|
72
|
+
|
73
|
+
def do_fetch
|
74
|
+
@raw_results = ActiveRecord::Base.connection.select_all(@sql)
|
75
|
+
end
|
76
|
+
|
77
|
+
def process_results
|
78
|
+
@raw_results.map{|hash| symbolize_hash hash}
|
79
|
+
end
|
80
|
+
|
81
|
+
private
|
82
|
+
def symbolize_hash(hash)
|
83
|
+
hash.inject({}) {|new,(k,v)| new[k.to_sym] = v; new}
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
# Json execution strategy?
|
88
|
+
EXEC_STRATEGIES = {
|
89
|
+
:default => DefaultExecStrategy,
|
90
|
+
Struct => StructExecStrategy,
|
91
|
+
Hash => HashExecStrategy
|
92
|
+
}
|
93
|
+
|
94
|
+
def self.config(&block)
|
95
|
+
Context.instance.instance_exec &block
|
96
|
+
end
|
97
|
+
|
98
|
+
def self.fetch(opts={})
|
99
|
+
sql, result_class = construct_sql_for opts
|
100
|
+
strategy_class = (EXEC_STRATEGIES[result_class] || EXEC_STRATEGIES[:default])
|
101
|
+
strategy = strategy_class.new(sql, result_class)
|
102
|
+
strategy.do_fetch
|
103
|
+
strategy.process_results
|
104
|
+
end
|
105
|
+
|
106
|
+
def self.fetch_one(opts={})
|
107
|
+
results = fetch(opts)
|
108
|
+
results[0]
|
109
|
+
end
|
110
|
+
|
111
|
+
private
|
112
|
+
def self.construct_sql_for(opts={})
|
113
|
+
raise ":query option must be specified" if not opts.include? :query
|
114
|
+
sql = opts[:query]
|
115
|
+
|
116
|
+
result_class = opts[:result_class] || Context.instance.result_class
|
117
|
+
if opts[:query].kind_of? Symbol
|
118
|
+
mapping = Context.instance.queries[opts[:query]]
|
119
|
+
raise "No query named #{opts[:query]} found" if mapping.nil?
|
120
|
+
sql = mapping.sql
|
121
|
+
result_class = mapping.result_class
|
122
|
+
end
|
123
|
+
|
124
|
+
if opts.include? :params
|
125
|
+
sql_array = [sql] + wrap_non_arrays_in_array(opts[:params])
|
126
|
+
sql = ActiveRecord::Base.send :sanitize_sql_array, sql_array
|
127
|
+
end
|
128
|
+
[sql, result_class]
|
129
|
+
end
|
130
|
+
|
131
|
+
def self.wrap_non_arrays_in_array(val)
|
132
|
+
if val.kind_of? Array
|
133
|
+
val
|
134
|
+
else
|
135
|
+
[val]
|
136
|
+
end
|
137
|
+
end
|
138
|
+
end
|
139
|
+
end
|
metadata
ADDED
@@ -0,0 +1,103 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: sql_mapper
|
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
|
+
- Lance Woodson
|
13
|
+
autorequire:
|
14
|
+
bindir: bin
|
15
|
+
cert_chain: []
|
16
|
+
|
17
|
+
date: 2012-11-01 00:00:00 -05:00
|
18
|
+
default_executable:
|
19
|
+
dependencies:
|
20
|
+
- !ruby/object:Gem::Dependency
|
21
|
+
name: activerecord
|
22
|
+
prerelease: false
|
23
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
24
|
+
requirements:
|
25
|
+
- - ">="
|
26
|
+
- !ruby/object:Gem::Version
|
27
|
+
segments:
|
28
|
+
- 2
|
29
|
+
- 3
|
30
|
+
- 0
|
31
|
+
version: 2.3.0
|
32
|
+
type: :runtime
|
33
|
+
version_requirements: *id001
|
34
|
+
- !ruby/object:Gem::Dependency
|
35
|
+
name: pg
|
36
|
+
prerelease: false
|
37
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
38
|
+
requirements:
|
39
|
+
- - ">="
|
40
|
+
- !ruby/object:Gem::Version
|
41
|
+
segments:
|
42
|
+
- 0
|
43
|
+
- 11
|
44
|
+
- 0
|
45
|
+
version: 0.11.0
|
46
|
+
type: :development
|
47
|
+
version_requirements: *id002
|
48
|
+
- !ruby/object:Gem::Dependency
|
49
|
+
name: sqlite3
|
50
|
+
prerelease: false
|
51
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
52
|
+
requirements:
|
53
|
+
- - ">="
|
54
|
+
- !ruby/object:Gem::Version
|
55
|
+
segments:
|
56
|
+
- 1
|
57
|
+
- 3
|
58
|
+
- 4
|
59
|
+
version: 1.3.4
|
60
|
+
type: :development
|
61
|
+
version_requirements: *id003
|
62
|
+
description: Object-to-sql mapping support for ActiveRecord.
|
63
|
+
email: lance@webmaneuvers.com
|
64
|
+
executables: []
|
65
|
+
|
66
|
+
extensions: []
|
67
|
+
|
68
|
+
extra_rdoc_files: []
|
69
|
+
|
70
|
+
files:
|
71
|
+
- lib/sql_mapper.rb
|
72
|
+
has_rdoc: true
|
73
|
+
homepage: http://rubygems.org/gems/sql_mapper
|
74
|
+
licenses: []
|
75
|
+
|
76
|
+
post_install_message:
|
77
|
+
rdoc_options: []
|
78
|
+
|
79
|
+
require_paths:
|
80
|
+
- lib
|
81
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
82
|
+
requirements:
|
83
|
+
- - ">="
|
84
|
+
- !ruby/object:Gem::Version
|
85
|
+
segments:
|
86
|
+
- 0
|
87
|
+
version: "0"
|
88
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
89
|
+
requirements:
|
90
|
+
- - ">="
|
91
|
+
- !ruby/object:Gem::Version
|
92
|
+
segments:
|
93
|
+
- 0
|
94
|
+
version: "0"
|
95
|
+
requirements: []
|
96
|
+
|
97
|
+
rubyforge_project:
|
98
|
+
rubygems_version: 1.3.6
|
99
|
+
signing_key:
|
100
|
+
specification_version: 3
|
101
|
+
summary: Object-to-sql mapping support for ActiveRecord
|
102
|
+
test_files: []
|
103
|
+
|