webink 1.2.9 → 1.3.0
Sign up to get free protection for your applications and to get access to all the features.
- data/bin/rfcgi +0 -0
- data/bin/webink_database +0 -0
- data/lib/webink/database.rb +72 -37
- data/lib/webink/model.rb +67 -17
- metadata +3 -3
data/bin/rfcgi
CHANGED
File without changes
|
data/bin/webink_database
CHANGED
File without changes
|
data/lib/webink/database.rb
CHANGED
@@ -153,7 +153,11 @@ module Ink
|
|
153
153
|
re.each_hash do |row|
|
154
154
|
result.push Hash.new
|
155
155
|
row.each do |k,v|
|
156
|
-
|
156
|
+
if v =~ /^[0-9]+$/
|
157
|
+
v = $&.to_i
|
158
|
+
elsif v =~ /^[0-9]+\.[0-9]+$/
|
159
|
+
v = $&.to_f
|
160
|
+
end
|
157
161
|
result[result.length-1][k] = v
|
158
162
|
end
|
159
163
|
end
|
@@ -163,7 +167,11 @@ module Ink
|
|
163
167
|
re.each do |row|
|
164
168
|
result.push Hash.new
|
165
169
|
for i in 0...re.columns.length
|
166
|
-
|
170
|
+
if row[i] =~ /^[0-9]+$/
|
171
|
+
row[i] = $&.to_i
|
172
|
+
elsif row[i] =~ /^[0-9]+\.[0-9]+$/
|
173
|
+
row[i] = $&.to_f
|
174
|
+
end
|
167
175
|
result[result.length-1][re.columns[i]] = row[i]
|
168
176
|
end
|
169
177
|
end
|
@@ -191,10 +199,12 @@ module Ink
|
|
191
199
|
# Instance method
|
192
200
|
#
|
193
201
|
# Attempts to fetch the last inserted primary key
|
202
|
+
# [param class_name:] Defines the __table__ name or class
|
194
203
|
# [returns:] primary key or nil
|
195
204
|
def last_inserted_pk(class_name)
|
196
|
-
|
197
|
-
|
205
|
+
c = (class_name.is_a? Class) ? class_name : Ink::Model.classname(class_name)
|
206
|
+
table_name = c.table_name
|
207
|
+
pk_name = c.primary_key[0]
|
198
208
|
return if not (table_name and pk_name)
|
199
209
|
response = self.query("SELECT MAX(#{pk_name}) as id FROM #{table_name};")
|
200
210
|
return (response.length > 0) ? response[0]["id"] : nil
|
@@ -218,10 +228,10 @@ module Ink
|
|
218
228
|
# Instance method
|
219
229
|
#
|
220
230
|
# Delete something from the database.
|
221
|
-
# [param class_name:] Defines the
|
231
|
+
# [param class_name:] Defines the class name or class
|
222
232
|
# [param params:] Additional SQL syntax like WHERE conditions (optional)
|
223
233
|
def remove(class_name, params="")
|
224
|
-
table_name = Ink::Model.str_to_tablename(class_name)
|
234
|
+
table_name = (class_name.is_a? Class) ? class_name.table_name : Ink::Model.str_to_tablename(class_name)
|
225
235
|
return if not table_name
|
226
236
|
self.query("DELETE FROM #{table_name} #{params};")
|
227
237
|
end
|
@@ -229,17 +239,18 @@ module Ink
|
|
229
239
|
# Instance method
|
230
240
|
#
|
231
241
|
# Retrieve class instances, that are loaded with the database result set.
|
232
|
-
# [param class_name:] Defines the
|
242
|
+
# [param class_name:] Defines the class name or class which should be queried
|
233
243
|
# [param params:] Additional SQL syntax like WHERE conditions (optional)
|
234
244
|
# [returns:] Array of class_name instances from the SQL result set
|
235
245
|
def find(class_name, params="")
|
246
|
+
c = (class_name.is_a? Class) ? class_name : Ink::Model.classname(class_name)
|
236
247
|
result = Array.new
|
237
|
-
table_name =
|
248
|
+
table_name = c.table_name
|
238
249
|
return result if not table_name
|
239
250
|
|
240
251
|
re = self.query("SELECT * FROM #{table_name} #{params};")
|
241
252
|
re.each do |entry|
|
242
|
-
instance =
|
253
|
+
instance = c.new entry
|
243
254
|
result.push instance
|
244
255
|
end
|
245
256
|
result
|
@@ -250,27 +261,29 @@ module Ink
|
|
250
261
|
# Retrieve class2 instances, that are related to the class1 instance with
|
251
262
|
# primary key class1_id. This is done via an additional relationship table.
|
252
263
|
# Only relevant for many_many relationships.
|
253
|
-
# [param class1:] Reference classname
|
264
|
+
# [param class1:] Reference classname or class
|
254
265
|
# [param class1_id:] Primary key value of the reference classname
|
255
|
-
# [param class2:] Match classname
|
266
|
+
# [param class2:] Match classname or class
|
256
267
|
# [param params:] Additional SQL syntax like GROUP BY (optional)
|
257
268
|
# [returns:] Array of class2 instances from the SQL result set
|
258
269
|
def find_union(class1, class1_id, class2, params="")
|
270
|
+
c1 = (class1.is_a? Class) ? class1 : Ink::Model.classname(class1)
|
271
|
+
c2 = (class2.is_a? Class) ? class2 : Ink::Model.classname(class2)
|
259
272
|
result = Array.new
|
260
273
|
relationship = nil
|
261
|
-
|
262
|
-
relationship = v if k.downcase ==
|
274
|
+
c1.foreign.each do |k,v|
|
275
|
+
relationship = v if k.downcase == c2.class_name.downcase
|
263
276
|
end
|
264
277
|
return result if relationship != "many_many"
|
265
|
-
fk1 =
|
266
|
-
pk2 =
|
267
|
-
fk2 =
|
268
|
-
tablename1 =
|
269
|
-
tablename2 =
|
270
|
-
union_class = ((
|
278
|
+
fk1 = c1.foreign_key[0]
|
279
|
+
pk2 = c2.primary_key[0]
|
280
|
+
fk2 = c2.foreign_key[0]
|
281
|
+
tablename1 = c1.table_name
|
282
|
+
tablename2 = c2.table_name
|
283
|
+
union_class = ((c1.class_name.downcase <=> c2.class_name.downcase) < 0) ? "#{tablename1}_#{tablename2}" : "#{tablename2}_#{tablename1}"
|
271
284
|
re = self.query("SELECT #{tablename2}.* FROM #{union_class}, #{tablename2} WHERE #{union_class}.#{fk1} = #{class1_id} AND #{union_class}.#{fk2} = #{tablename2}.#{pk2} #{params};")
|
272
285
|
re.each do |entry|
|
273
|
-
instance =
|
286
|
+
instance = c2.new entry
|
274
287
|
result.push instance
|
275
288
|
end
|
276
289
|
result
|
@@ -280,33 +293,55 @@ module Ink
|
|
280
293
|
#
|
281
294
|
# Retrieve class2 instances, that are related to the class1 instance with
|
282
295
|
# primary key class1_id. Not relevant for many_many relationships
|
283
|
-
# [param class1:] Reference classname
|
296
|
+
# [param class1:] Reference classname or class
|
284
297
|
# [param class1_id:] Primary key value of the reference classname
|
285
|
-
# [param class2:] Match classname
|
298
|
+
# [param class2:] Match classname or class
|
286
299
|
# [param params:] Additional SQL syntax like GROUP BY (optional)
|
287
300
|
# [returns:] Array of class2 instances from the SQL result set
|
288
301
|
def find_references(class1, class1_id, class2, params="")
|
302
|
+
c1 = (class1.is_a? Class) ? class1 : Ink::Model.classname(class1)
|
303
|
+
c2 = (class2.is_a? Class) ? class2 : Ink::Model.classname(class2)
|
289
304
|
result = Array.new
|
290
305
|
relationship = nil
|
291
|
-
|
292
|
-
relationship = v if k.downcase ==
|
306
|
+
c1.foreign.each do |k,v|
|
307
|
+
relationship = v if k.downcase == c2.class_name.downcase
|
293
308
|
end
|
294
309
|
return result if relationship == "many_many"
|
295
310
|
re = Array.new
|
296
|
-
fk1 =
|
297
|
-
|
298
|
-
|
311
|
+
fk1 = c1.foreign_key[0]
|
312
|
+
tablename1 = c1.table_name
|
313
|
+
tablename2 = c2.table_name
|
314
|
+
if ((c1.class_name.downcase <=> c2.class_name.downcase) < 0 and relationship == "one_one") or relationship == "one_many"
|
315
|
+
re = self.query "SELECT * FROM #{tablename2} WHERE #{c2.primary_key[0]}=(SELECT #{c2.foreign_key[0]} FROM #{tablename1} WHERE #{c1.primary_key[0]}=#{class1_id});"
|
299
316
|
else
|
300
|
-
re = self.query "SELECT * FROM #{
|
317
|
+
re = self.query "SELECT * FROM #{tablename2} WHERE #{fk1} = #{class1_id} #{params};"
|
301
318
|
end
|
302
319
|
|
303
320
|
re.each do |entry|
|
304
|
-
instance =
|
321
|
+
instance = c2.new entry
|
305
322
|
result.push instance
|
306
323
|
end
|
307
324
|
result
|
308
325
|
end
|
309
326
|
|
327
|
+
# Instance method
|
328
|
+
#
|
329
|
+
# Retrieve one class2 instance, that is related to the class1 instance with
|
330
|
+
# primary key class1_id. Only relevant for one_one and one_many relationships
|
331
|
+
# [param class1:] Reference classname or class
|
332
|
+
# [param class1_id:] Primary key value of the reference classname
|
333
|
+
# [param class2:] Match classname or class
|
334
|
+
# [param params:] Additional SQL syntax like GROUP BY (optional)
|
335
|
+
# [returns:] single class2 instance from the SQL result set
|
336
|
+
def find_reference(class1, class1_id, class2, params="")
|
337
|
+
result_array = self.find_references class1, class1_id, class2, params
|
338
|
+
if result_array.length == 1
|
339
|
+
result_array[0]
|
340
|
+
else
|
341
|
+
nil
|
342
|
+
end
|
343
|
+
end
|
344
|
+
|
310
345
|
# Instance method
|
311
346
|
#
|
312
347
|
# This method attempts to remove all existing relationship data
|
@@ -322,16 +357,16 @@ module Ink
|
|
322
357
|
secondclass = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? link : instance.class
|
323
358
|
key = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? instance.class.primary_key[0] : instance.class.foreign_key[0]
|
324
359
|
value = instance.method(instance.class.primary_key[0]).call
|
325
|
-
@db.query "UPDATE #{
|
360
|
+
@db.query "UPDATE #{firstclass.table_name} SET #{secondclass.foreign_key[0]}=NULL WHERE #{key}=#{value};"
|
326
361
|
elsif type == "one_many" or type == "many_one"
|
327
362
|
firstclass = (type == "one_many") ? instance.class : link
|
328
363
|
secondclass = (type == "one_many") ? link : instance.class
|
329
364
|
key = (type == "one_many") ? instance.class.primary_key[0] : instance.class.foreign_key[0]
|
330
365
|
value = instance.method(instance.class.primary_key[0]).call
|
331
|
-
@db.query "UPDATE #{
|
366
|
+
@db.query "UPDATE #{firstclass.table_name} SET #{secondclass.foreign_key[0]}=NULL WHERE #{key}=#{value};"
|
332
367
|
elsif type == "many_many"
|
333
|
-
tablename1 =
|
334
|
-
tablename2 =
|
368
|
+
tablename1 = instance.class.table_name
|
369
|
+
tablename2 = link.table_name
|
335
370
|
union_class = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? "#{tablename1}_#{tablename2}" : "#{tablename2}_#{tablename1}"
|
336
371
|
value = instance.method(instance.class.primary_key[0]).call
|
337
372
|
@db.query "DELETE FROM #{union_class} WHERE #{instance.class.foreign_key[0]}=#{value};"
|
@@ -390,7 +425,7 @@ module Ink
|
|
390
425
|
value = instance.method(instance.class.primary_key[0]).call
|
391
426
|
fk_set = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? fk : value
|
392
427
|
value_set = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? value : fk
|
393
|
-
@db.query "UPDATE #{
|
428
|
+
@db.query "UPDATE #{firstclass.table_name} SET #{secondclass.foreign_key[0]}=#{fk} WHERE #{key}=#{value};"
|
394
429
|
elsif type == "one_many" or type == "many_one"
|
395
430
|
firstclass = (type == "one_many") ? instance.class : link
|
396
431
|
secondclass = (type == "one_many") ? link : instance.class
|
@@ -398,10 +433,10 @@ module Ink
|
|
398
433
|
value = instance.method(instance.class.primary_key[0]).call
|
399
434
|
fk_set = (type == "one_many") ? fk : value
|
400
435
|
value_set = (type == "one_many") ? value : fk
|
401
|
-
@db.query "UPDATE #{
|
436
|
+
@db.query "UPDATE #{firstclass.table_name} SET #{secondclass.foreign_key[0]}=#{fk_set} WHERE #{key}=#{value_set};"
|
402
437
|
elsif type == "many_many"
|
403
|
-
tablename1 =
|
404
|
-
tablename2 =
|
438
|
+
tablename1 = instance.class.table_name
|
439
|
+
tablename2 = link.table_name
|
405
440
|
union_class = ((instance.class.name.downcase <=> link.name.downcase) < 0) ? "#{tablename1}_#{tablename2}" : "#{tablename2}_#{tablename1}"
|
406
441
|
value = instance.method(instance.class.primary_key[0]).call
|
407
442
|
@db.query "INSERT INTO #{union_class} (#{instance.class.foreign_key[0]}, #{link.foreign_key[0]}) VALUES (#{value}, #{fk});"
|
data/lib/webink/model.rb
CHANGED
@@ -131,13 +131,14 @@ module Ink
|
|
131
131
|
end
|
132
132
|
if self.class.respond_to? :foreign
|
133
133
|
self.class.foreign.each do |k,v|
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
134
|
+
k_table = self.class.str_to_tablename(k)
|
135
|
+
raise NameError.new("Model cannot use #{k_table} as foreign, it already exists") if self.class.respond_to? k_table.to_sym or k_table == "pk"
|
136
|
+
instance_variable_set("@#{k_table}", nil)
|
137
|
+
self.class.send(:define_method, k_table) do
|
138
|
+
instance_variable_get "@#{k_table}"
|
138
139
|
end
|
139
|
-
self.class.send(:define_method, "#{
|
140
|
-
instance_variable_set "@#{
|
140
|
+
self.class.send(:define_method, "#{k_table}=") do |val|
|
141
|
+
instance_variable_set "@#{k_table}", val
|
141
142
|
end
|
142
143
|
end
|
143
144
|
end
|
@@ -183,12 +184,12 @@ module Ink
|
|
183
184
|
end
|
184
185
|
end
|
185
186
|
if pkvalue
|
186
|
-
response = Ink::Database.database.find self.class
|
187
|
+
response = Ink::Database.database.find self.class, pkvalue
|
187
188
|
if response.length == 1
|
188
|
-
Ink::Database.database.query "UPDATE #{
|
189
|
+
Ink::Database.database.query "UPDATE #{self.class.table_name} SET #{string * ","} #{pkvalue}"
|
189
190
|
elsif response.length == 0
|
190
|
-
Ink::Database.database.query "INSERT INTO #{
|
191
|
-
pk = Ink::Database.database.last_inserted_pk(self.class
|
191
|
+
Ink::Database.database.query "INSERT INTO #{self.class.table_name} (#{keystring * ","}) VALUES (#{valuestring * ","});"
|
192
|
+
pk = Ink::Database.database.last_inserted_pk(self.class)
|
192
193
|
instance_variable_set "@#{self.class.primary_key[0]}", pk.is_a?(Numeric) ? pk : "\'#{pk}\'" if pk
|
193
194
|
end
|
194
195
|
end
|
@@ -221,6 +222,23 @@ module Ink
|
|
221
222
|
Ink::Database.database.remove self.class.name, "WHERE `#{self.class.primary_key[0]}`=#{(pkvalue.is_a?(Numeric)) ? pkvalue : "\'#{pkvalue}\'"};"
|
222
223
|
end
|
223
224
|
|
225
|
+
# Instance method
|
226
|
+
#
|
227
|
+
# Queries the database for foreign keys and attaches them to the
|
228
|
+
# matching foreign accessor
|
229
|
+
# [param foreign_class:] Defines the foreign class name or class
|
230
|
+
def find_references(foreign_class)
|
231
|
+
c = (foreign_class.is_a? Class) ? foreign_class : Ink::Model.classname(foreign_class)
|
232
|
+
relationship = self.class.foreign[c.class_name]
|
233
|
+
if relationship
|
234
|
+
result_array = (relationship == "many_many") ? Ink::Database.database.find_union(self.class, self.pk, c) : Ink::Database.database.find_references(self.class, self.pk, c)
|
235
|
+
instance_variable_set("@#{c.table_name}", (relationship =~ /_one$/) ? result_array[0] : result_array)
|
236
|
+
true
|
237
|
+
else
|
238
|
+
false
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
224
242
|
# Class method
|
225
243
|
#
|
226
244
|
# This will create SQL statements for creating the
|
@@ -231,7 +249,7 @@ module Ink
|
|
231
249
|
result = Array.new
|
232
250
|
raise NotImplementedError.new("Cannot create a Database without field definitions") if not self.respond_to? :fields
|
233
251
|
|
234
|
-
string = "CREATE TABLE #{
|
252
|
+
string = "CREATE TABLE #{self.table_name} ("
|
235
253
|
mfk = self.foreign_key
|
236
254
|
fields = self.fields
|
237
255
|
for i in 0...fields.keys.length
|
@@ -246,11 +264,11 @@ module Ink
|
|
246
264
|
for i in 0...foreign.keys.length
|
247
265
|
k = foreign.keys[i]
|
248
266
|
v = foreign[k]
|
249
|
-
fk = Model::classname(k).foreign_key
|
267
|
+
fk = Ink::Model::classname(k).foreign_key
|
250
268
|
string += ",`#{fk[0]}` #{fk[1]}" if fk.length > 0 and (v == "one_many" or (v == "one_one" and (self.name <=> k) < 0))
|
251
269
|
|
252
270
|
if mfk.length > 0 and fk.length > 1 and v == "many_many" and (self.name <=> k) < 0
|
253
|
-
result.push "CREATE TABLE #{
|
271
|
+
result.push "CREATE TABLE #{self.table_name}_#{Ink::Model::str_to_tablename(k)} (#{Ink::Database.database.primary_key_autoincrement*" "}, `#{mfk[0]}` #{mfk[1]}, `#{fk[0]}` #{fk[1]});"
|
254
272
|
end
|
255
273
|
end
|
256
274
|
end
|
@@ -259,6 +277,22 @@ module Ink
|
|
259
277
|
result
|
260
278
|
end
|
261
279
|
|
280
|
+
# Class method
|
281
|
+
#
|
282
|
+
# This will retrieve a string-representation of the model name
|
283
|
+
# [returns:] valid classname
|
284
|
+
def self.class_name
|
285
|
+
self.name
|
286
|
+
end
|
287
|
+
|
288
|
+
# Class method
|
289
|
+
#
|
290
|
+
# This will retrieve a tablename-representation of the model name
|
291
|
+
# [returns:] valid tablename
|
292
|
+
def self.table_name
|
293
|
+
self.str_to_tablename self.name
|
294
|
+
end
|
295
|
+
|
262
296
|
# Class method
|
263
297
|
#
|
264
298
|
# This will check the parent module for existing classnames
|
@@ -266,7 +300,11 @@ module Ink
|
|
266
300
|
# [param str:] some string
|
267
301
|
# [returns:] valid classname or nil
|
268
302
|
def self.str_to_classname(str)
|
269
|
-
|
303
|
+
res = []
|
304
|
+
str.scan(/((^|_)([a-z0-9]+))/) { |s|
|
305
|
+
res.push(s[2][0].upcase + ((s[2].length > 1) ? s[2][1,s[2].length] : "")) if s.length > 0
|
306
|
+
}
|
307
|
+
((Module.const_get res.join).is_a? Class) ? res.join : nil
|
270
308
|
end
|
271
309
|
|
272
310
|
# Class method
|
@@ -277,7 +315,11 @@ module Ink
|
|
277
315
|
# [param str:] some string
|
278
316
|
# [returns:] valid tablename or nil
|
279
317
|
def self.str_to_tablename(str)
|
280
|
-
|
318
|
+
res = []
|
319
|
+
str.scan(/([A-Z][a-z0-9]*)/) { |s|
|
320
|
+
res.push (res.length>0) ? "_" + s.join.downcase : s.join.downcase
|
321
|
+
}
|
322
|
+
((Module.const_get str).is_a? Class) ? res.join : nil
|
281
323
|
end
|
282
324
|
|
283
325
|
# Class method
|
@@ -288,7 +330,15 @@ module Ink
|
|
288
330
|
# [param str:] some string
|
289
331
|
# [returns:] valid class or nil
|
290
332
|
def self.classname(str)
|
291
|
-
|
333
|
+
res = []
|
334
|
+
if str[0] =~ /^[a-z]/
|
335
|
+
str.scan(/((^|_)([a-z0-9]+))/) { |s|
|
336
|
+
res.push(s[2][0].upcase + ((s[2].length > 1) ? s[2][1,s[2].length] : "")) if s.length > 0
|
337
|
+
}
|
338
|
+
else
|
339
|
+
res.push str
|
340
|
+
end
|
341
|
+
((Module.const_get res.join).is_a? Class) ? (Module.const_get res.join) : nil
|
292
342
|
end
|
293
343
|
|
294
344
|
# Class method
|
@@ -317,7 +367,7 @@ module Ink
|
|
317
367
|
# [returns:] Array of the form: key name, key type or empty
|
318
368
|
def self.foreign_key
|
319
369
|
pk = self.primary_key
|
320
|
-
return (pk) ? ["#{self.
|
370
|
+
return (pk) ? ["#{self.table_name}_#{pk[0]}", pk[1]] : []
|
321
371
|
end
|
322
372
|
|
323
373
|
end
|
metadata
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
name: webink
|
3
3
|
version: !ruby/object:Gem::Version
|
4
4
|
prerelease:
|
5
|
-
version: 1.
|
5
|
+
version: 1.3.0
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Matthias Geier
|
@@ -10,7 +10,7 @@ autorequire:
|
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
12
|
|
13
|
-
date: 2012-
|
13
|
+
date: 2012-09-14 00:00:00 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: fcgi
|
@@ -51,7 +51,7 @@ files:
|
|
51
51
|
- lib/webink/controller.rb
|
52
52
|
- bin/webink_database
|
53
53
|
- bin/rfcgi
|
54
|
-
homepage:
|
54
|
+
homepage: https://github.com/matthias-geier/WebInk
|
55
55
|
licenses: []
|
56
56
|
|
57
57
|
post_install_message:
|