dbagile 0.0.1 → 0.0.2
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/dbagile.rb +2 -2
- data/lib/dbagile/adapter/sequel/data/transaction_driven.rb +1 -0
- data/lib/dbagile/adapter/sequel/schema/concrete_script.rb +18 -0
- data/lib/dbagile/adapter/sequel/schema/table_driven.rb +10 -1
- data/lib/dbagile/adapter/sequel/sequel_tracer.rb +1 -0
- data/lib/dbagile/command/bulk/commons.rb +7 -2
- data/lib/dbagile/command/bulk/export.rb +4 -1
- data/lib/dbagile/command/bulk/import.rb +32 -2
- data/lib/dbagile/command/schema/check.rb +2 -1
- data/lib/dbagile/command/schema/commons.rb +16 -1
- data/lib/dbagile/command/schema/dump.rb +85 -4
- data/lib/dbagile/command/schema/sql_script.rb +1 -0
- data/lib/dbagile/contract/data/dataset.rb +9 -0
- data/lib/dbagile/core/schema/builder.rb +8 -4
- data/lib/dbagile/core/schema/builder/concept_factory.rb +5 -0
- data/lib/dbagile/core/schema/composite.rb +1 -1
- data/lib/dbagile/core/schema/computations/merge.rb +1 -1
- data/lib/dbagile/core/schema/errors.rb +1 -3
- data/lib/dbagile/core/schema/logical.rb +1 -0
- data/lib/dbagile/core/schema/logical/attribute.rb +11 -2
- data/lib/dbagile/core/schema/logical/relview.rb +42 -0
- data/lib/dbagile/core/schema/migrate/abstract_script.rb +2 -0
- data/lib/dbagile/core/schema/migrate/create_view.rb +15 -0
- data/lib/dbagile/core/schema/migrate/drop_view.rb +15 -0
- data/lib/dbagile/core/schema/migrate/operation.rb +8 -6
- data/lib/dbagile/core/schema/migrate/stager.rb +12 -3
- data/lib/dbagile/core/schema/part.rb +0 -49
- data/lib/dbagile/core/schema/schema_object.rb +54 -0
- data/lib/dbagile/environment/repository.rb +2 -2
- data/lib/dbagile/errors.rb +3 -0
- data/lib/dbagile/io.rb +7 -3
- data/lib/dbagile/io/html.rb +48 -0
- data/lib/dbagile/restful.rb +1 -1
- data/lib/dbagile/restful/middleware/one_database.rb +1 -0
- data/lib/dbagile/restful/middleware/post.rb +16 -1
- data/lib/dbagile/tools/tuple.rb +7 -0
- data/test/assumptions/sequel/connect.spec +12 -9
- data/test/assumptions/sequel/test.db +0 -0
- data/test/commands.spec +4 -4
- data/test/commands/bulk/import.spec +26 -3
- data/test/commands/schema/check.spec +20 -13
- data/test/commands/schema/dump.spec +23 -0
- data/test/fixtures/basics/dbagile.idx +7 -7
- data/test/fixtures/basics/robust.db +0 -0
- data/test/fixtures/basics/test.db +0 -0
- data/test/fixtures/empty/dbagile.idx +1 -1
- data/test/restful/get/html_format.ex +12 -0
- data/test/run_all_suite.rb +1 -1
- data/test/spec_helper.rb +0 -2
- data/test/support/be_a_valid_json_string.rb +1 -1
- data/test/support/be_a_valid_yaml_string.rb +1 -1
- data/test/unit/core/schema/fixtures/views.yaml +5 -0
- data/test/unit/core/schema/part_keys.spec +12 -0
- data/test/unit/core/schema/yaml_load.spec +5 -0
- metadata +414 -244
@@ -102,13 +102,11 @@ module DbAgile
|
|
102
102
|
TargetKeyMismatch
|
103
103
|
]
|
104
104
|
MESSAGE_VALUES = [
|
105
|
-
'invalid default value on
|
105
|
+
'invalid default value \'#{schema_object.default_value}\' on #{schema_object}',
|
106
106
|
'relvar #{schema_object.relation_variable.name} has an empty heading (unsupported so far)',
|
107
107
|
'relvar #{schema_object.name} has no primary key',
|
108
108
|
'invalid constraint #{schema_object.name} on #{schema_object.relation_variable.name}',
|
109
|
-
|
110
109
|
'invalid index #{schema_object.name}',
|
111
|
-
|
112
110
|
'no such relvar #{args[:relvar_name]}',
|
113
111
|
'no such attributes #{args[:attributes].join(\',\')}',
|
114
112
|
'no such candidate key #{args[:constraint_name]}',
|
@@ -18,6 +18,7 @@ module DbAgile
|
|
18
18
|
end # module Core
|
19
19
|
end # module DbAgile
|
20
20
|
require 'dbagile/core/schema/logical/relvar'
|
21
|
+
require 'dbagile/core/schema/logical/relview'
|
21
22
|
require 'dbagile/core/schema/logical/heading'
|
22
23
|
require 'dbagile/core/schema/logical/attribute'
|
23
24
|
require 'dbagile/core/schema/logical/constraints'
|
@@ -22,6 +22,10 @@ module DbAgile
|
|
22
22
|
def mandatory?
|
23
23
|
!(definition[:mandatory] == false)
|
24
24
|
end
|
25
|
+
|
26
|
+
def relvar
|
27
|
+
parent.parent
|
28
|
+
end
|
25
29
|
|
26
30
|
############################################################################
|
27
31
|
### Dependency control
|
@@ -38,7 +42,7 @@ module DbAgile
|
|
38
42
|
|
39
43
|
# @see DbAgile::Core::Schema::SchemaObject
|
40
44
|
def _semantics_check(clazz, buffer)
|
41
|
-
unless default_value.nil? or
|
45
|
+
unless default_value.nil? or (domain === default_value)
|
42
46
|
buffer.add_error(self, clazz::InvalidDefaultValue)
|
43
47
|
end
|
44
48
|
end
|
@@ -54,13 +58,18 @@ module DbAgile
|
|
54
58
|
out.map("tag:yaml.org,2002:map", :inline ) do |map|
|
55
59
|
map.add('domain', defn[:domain].to_s)
|
56
60
|
map.add('mandatory', false) unless defn[:mandatory]
|
57
|
-
|
61
|
+
unless defn[:default].nil?
|
58
62
|
map.add('default', defn[:default])
|
59
63
|
end
|
60
64
|
end
|
61
65
|
}
|
62
66
|
end
|
63
67
|
|
68
|
+
# Returns a string representation
|
69
|
+
def to_s
|
70
|
+
"Attribute #{relvar.name}::#{name} #{definition.inspect}"
|
71
|
+
end
|
72
|
+
|
64
73
|
end # class Attribute
|
65
74
|
end # module Logical
|
66
75
|
end # module Schema
|
@@ -0,0 +1,42 @@
|
|
1
|
+
module DbAgile
|
2
|
+
module Core
|
3
|
+
module Schema
|
4
|
+
class Logical
|
5
|
+
class Relview < Schema::Part
|
6
|
+
|
7
|
+
############################################################################
|
8
|
+
### Dependency control
|
9
|
+
############################################################################
|
10
|
+
|
11
|
+
# @see DbAgile::Core::Schema::SchemaObject
|
12
|
+
def dependencies(include_parent = false)
|
13
|
+
include_parent ? [ parent ] : []
|
14
|
+
end
|
15
|
+
|
16
|
+
############################################################################
|
17
|
+
### Check interface
|
18
|
+
############################################################################
|
19
|
+
|
20
|
+
# @see DbAgile::Core::Schema::SchemaObject
|
21
|
+
def _semantics_check(clazz, buffer)
|
22
|
+
end
|
23
|
+
|
24
|
+
############################################################################
|
25
|
+
### About IO
|
26
|
+
############################################################################
|
27
|
+
|
28
|
+
# Delegation pattern on YAML flushing
|
29
|
+
def to_yaml(opts = {})
|
30
|
+
definition.to_yaml(opts)
|
31
|
+
end
|
32
|
+
|
33
|
+
# Returns a string representation
|
34
|
+
def to_s
|
35
|
+
"Relview #{name} #{definition.inspect}"
|
36
|
+
end
|
37
|
+
|
38
|
+
end # class Relview
|
39
|
+
end # module Logical
|
40
|
+
end # module Schema
|
41
|
+
end # module Core
|
42
|
+
end # module DbAgile
|
@@ -33,3 +33,5 @@ require 'dbagile/core/schema/migrate/create_table'
|
|
33
33
|
require 'dbagile/core/schema/migrate/drop_table'
|
34
34
|
require 'dbagile/core/schema/migrate/expand_table'
|
35
35
|
require 'dbagile/core/schema/migrate/collapse_table'
|
36
|
+
require 'dbagile/core/schema/migrate/create_view'
|
37
|
+
require 'dbagile/core/schema/migrate/drop_view'
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module DbAgile
|
2
|
+
module Core
|
3
|
+
module Schema
|
4
|
+
module Migrate
|
5
|
+
class CreateView < Migrate::Operation
|
6
|
+
|
7
|
+
def to_sql92
|
8
|
+
"CREATE VIEW #{table_name} (#{relvar.definition})"
|
9
|
+
end
|
10
|
+
|
11
|
+
end # class CreateView
|
12
|
+
end # module Migrate
|
13
|
+
end # module Schema
|
14
|
+
end # module Core
|
15
|
+
end # module DbAgile
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module DbAgile
|
2
|
+
module Core
|
3
|
+
module Schema
|
4
|
+
module Migrate
|
5
|
+
class DropView < Migrate::Operation
|
6
|
+
|
7
|
+
def to_sql92
|
8
|
+
"DROP VIEW #{table_name}"
|
9
|
+
end
|
10
|
+
|
11
|
+
end # class DropView
|
12
|
+
end # module Migrate
|
13
|
+
end # module Schema
|
14
|
+
end # module Core
|
15
|
+
end # module DbAgile
|
@@ -7,19 +7,21 @@ module DbAgile
|
|
7
7
|
# The sub operations
|
8
8
|
attr_reader :operations
|
9
9
|
|
10
|
-
# Targetted relation variable
|
11
|
-
attr_reader :
|
10
|
+
# Targetted relation variable/view
|
11
|
+
attr_reader :rel_object
|
12
|
+
alias :relvar :rel_object
|
13
|
+
alias :relview :rel_object
|
12
14
|
|
13
15
|
# Returns table name
|
14
16
|
def table_name
|
15
17
|
relvar.name
|
16
18
|
end
|
17
19
|
|
18
|
-
def initialize(
|
19
|
-
unless relvar.
|
20
|
-
raise ArgumentError, "Relvar expected for
|
20
|
+
def initialize(rel_object)
|
21
|
+
unless rel_object.relvar? or rel_object.relview?
|
22
|
+
raise ArgumentError, "Relvar expected for rel_object, got #{rel_object.class}"
|
21
23
|
end
|
22
|
-
@
|
24
|
+
@rel_object = rel_object
|
23
25
|
@operations = []
|
24
26
|
end
|
25
27
|
|
@@ -139,6 +139,11 @@ module DbAgile
|
|
139
139
|
script << Migrate::DropTable.new(relvar)
|
140
140
|
end
|
141
141
|
|
142
|
+
# Collapses a relation view
|
143
|
+
def collapse_relview(relview)
|
144
|
+
script << Migrate::DropView.new(relview)
|
145
|
+
end
|
146
|
+
|
142
147
|
# Collapses a candidate key
|
143
148
|
def collapse_candidate_key(ckey)
|
144
149
|
with_collapse_helper(ckey.relation_variable){|h| h.candidate_key(ckey)}
|
@@ -172,16 +177,16 @@ module DbAgile
|
|
172
177
|
# create the operation
|
173
178
|
exists = relvar_exists?(rv)
|
174
179
|
h = exists ? Migrate::ExpandTable.new(rv) : Migrate::CreateTable.new(rv)
|
175
|
-
|
180
|
+
|
176
181
|
# execute sub operations and save
|
177
182
|
yield(helpers[rv] = h)
|
178
183
|
script << h
|
179
|
-
|
184
|
+
|
180
185
|
# assert that the table now exists
|
181
186
|
unless exists
|
182
187
|
relvar_exists!(rv)
|
183
188
|
end
|
184
|
-
|
189
|
+
|
185
190
|
# remove helper now
|
186
191
|
helpers.delete(rv)
|
187
192
|
end
|
@@ -248,6 +253,10 @@ module DbAgile
|
|
248
253
|
end
|
249
254
|
alias :expand_relvar :expand_relvar_xxx
|
250
255
|
alias :expand_heading :expand_relvar_xxx
|
256
|
+
|
257
|
+
def expand_relview(rv)
|
258
|
+
script << Migrate::CreateView.new(rv)
|
259
|
+
end
|
251
260
|
|
252
261
|
### Parts
|
253
262
|
|
@@ -25,55 +25,6 @@ module DbAgile
|
|
25
25
|
def _semantics_check(clazz, buffer)
|
26
26
|
end
|
27
27
|
|
28
|
-
############################################################################
|
29
|
-
### Schema typing
|
30
|
-
############################################################################
|
31
|
-
|
32
|
-
# Returns true if this object is a logical object, false otherwise
|
33
|
-
def logical?
|
34
|
-
relvar? or attribute? or constraint?
|
35
|
-
end
|
36
|
-
|
37
|
-
# Returns true if this object is a relation variable, false otherwise
|
38
|
-
def relvar?
|
39
|
-
self.kind_of?(Schema::Logical::Relvar)
|
40
|
-
end
|
41
|
-
|
42
|
-
# Returns true if this object is an attribute, false otherwise
|
43
|
-
def attribute?
|
44
|
-
self.kind_of?(Schema::Logical::Attribute)
|
45
|
-
end
|
46
|
-
|
47
|
-
# Returns true if this object is a constraint, false otherwise
|
48
|
-
def constraint?
|
49
|
-
self.kind_of?(Schema::Logical::Constraint)
|
50
|
-
end
|
51
|
-
|
52
|
-
# Returns true if this object is a candidate key, false otherwise
|
53
|
-
def candidate_key?
|
54
|
-
self.kind_of?(Schema::Logical::Constraint::CandidateKey)
|
55
|
-
end
|
56
|
-
|
57
|
-
# Returns true if this object is a primary key, false otherwise
|
58
|
-
def primary_key?
|
59
|
-
self.candidate_key? and self.primary?
|
60
|
-
end
|
61
|
-
|
62
|
-
# Returns true if this object is a foreign key, false otherwise
|
63
|
-
def foreign_key?
|
64
|
-
self.kind_of?(Schema::Logical::Constraint::ForeignKey)
|
65
|
-
end
|
66
|
-
|
67
|
-
# Returns true if this object is a physical object, false otherwise
|
68
|
-
def physical?
|
69
|
-
index?
|
70
|
-
end
|
71
|
-
|
72
|
-
# Returns true if this object is an index, false otherwise
|
73
|
-
def index?
|
74
|
-
self.kind_of?(Schema::Physical::Index)
|
75
|
-
end
|
76
|
-
|
77
28
|
############################################################################
|
78
29
|
### Schema::SchemaObject
|
79
30
|
############################################################################
|
@@ -25,6 +25,60 @@ module DbAgile
|
|
25
25
|
end
|
26
26
|
alias :terminal? :part?
|
27
27
|
|
28
|
+
############################################################################
|
29
|
+
### Schema typing
|
30
|
+
############################################################################
|
31
|
+
|
32
|
+
# Returns true if this object is a logical object, false otherwise
|
33
|
+
def logical?
|
34
|
+
relvar? or relview? or attribute? or constraint?
|
35
|
+
end
|
36
|
+
|
37
|
+
# Returns true if this object is a relation view, false otherwise
|
38
|
+
def relview?
|
39
|
+
self.kind_of?(Schema::Logical::Relview)
|
40
|
+
end
|
41
|
+
|
42
|
+
# Returns true if this object is a relation variable, false otherwise
|
43
|
+
def relvar?
|
44
|
+
self.kind_of?(Schema::Logical::Relvar)
|
45
|
+
end
|
46
|
+
|
47
|
+
# Returns true if this object is an attribute, false otherwise
|
48
|
+
def attribute?
|
49
|
+
self.kind_of?(Schema::Logical::Attribute)
|
50
|
+
end
|
51
|
+
|
52
|
+
# Returns true if this object is a constraint, false otherwise
|
53
|
+
def constraint?
|
54
|
+
self.kind_of?(Schema::Logical::Constraint)
|
55
|
+
end
|
56
|
+
|
57
|
+
# Returns true if this object is a candidate key, false otherwise
|
58
|
+
def candidate_key?
|
59
|
+
self.kind_of?(Schema::Logical::CandidateKey)
|
60
|
+
end
|
61
|
+
|
62
|
+
# Returns true if this object is a primary key, false otherwise
|
63
|
+
def primary_key?
|
64
|
+
self.candidate_key? and self.primary?
|
65
|
+
end
|
66
|
+
|
67
|
+
# Returns true if this object is a foreign key, false otherwise
|
68
|
+
def foreign_key?
|
69
|
+
self.kind_of?(Schema::Logical::ForeignKey)
|
70
|
+
end
|
71
|
+
|
72
|
+
# Returns true if this object is a physical object, false otherwise
|
73
|
+
def physical?
|
74
|
+
index?
|
75
|
+
end
|
76
|
+
|
77
|
+
# Returns true if this object is an index, false otherwise
|
78
|
+
def index?
|
79
|
+
self.kind_of?(Schema::Physical::Index)
|
80
|
+
end
|
81
|
+
|
28
82
|
############################################################################
|
29
83
|
### Schema hierarchy
|
30
84
|
############################################################################
|
@@ -118,7 +118,7 @@ module DbAgile
|
|
118
118
|
def with_current_database
|
119
119
|
raise ArgumentError, "Missing block" unless block_given?
|
120
120
|
db = repository.current_database
|
121
|
-
raise NoDefaultDatabaseError if db.nil?
|
121
|
+
raise DbAgile::NoDefaultDatabaseError, "No default database set (try 'dba use ...' first)" if db.nil?
|
122
122
|
yield(db)
|
123
123
|
end
|
124
124
|
|
@@ -140,7 +140,7 @@ module DbAgile
|
|
140
140
|
raise ArgumentError, "Invalid database name #{db}"
|
141
141
|
end
|
142
142
|
raise NoSuchDatabaseError if db.nil?
|
143
|
-
db.with_connection(&block)
|
143
|
+
db.with_connection(conn_options, &block)
|
144
144
|
end
|
145
145
|
|
146
146
|
#
|
data/lib/dbagile/errors.rb
CHANGED
@@ -27,4 +27,7 @@ module DbAgile
|
|
27
27
|
# Raised when usage of schema files fails because they are not installed
|
28
28
|
class NoSchemaFilesError < DbAgile::Error; end
|
29
29
|
|
30
|
+
# Raised when a candidate key cannot be infered from a given tuple
|
31
|
+
class CandidateKeyNotFoundError < DbAgile::Error; end
|
32
|
+
|
30
33
|
end # module DbAgile
|
data/lib/dbagile/io.rb
CHANGED
@@ -4,6 +4,7 @@ require 'dbagile/io/csv'
|
|
4
4
|
require 'dbagile/io/json'
|
5
5
|
require 'dbagile/io/yaml'
|
6
6
|
require 'dbagile/io/xml'
|
7
|
+
require 'dbagile/io/html'
|
7
8
|
require 'dbagile/io/ruby'
|
8
9
|
require 'dbagile/io/text'
|
9
10
|
module DbAgile
|
@@ -15,10 +16,10 @@ module DbAgile
|
|
15
16
|
}
|
16
17
|
|
17
18
|
# Known IO formats
|
18
|
-
KNOWN_FORMATS = [:yaml, :csv, :json, :ruby, :text, :xml]
|
19
|
+
KNOWN_FORMATS = [:yaml, :csv, :json, :ruby, :text, :xml, :html]
|
19
20
|
|
20
21
|
# Known to_xxx IO formats
|
21
|
-
KNOWN_TO_FORMATS = [:yaml, :csv, :json, :ruby, :text, :xml]
|
22
|
+
KNOWN_TO_FORMATS = [:yaml, :csv, :json, :ruby, :text, :xml, :html]
|
22
23
|
|
23
24
|
# Known from_xxx formats
|
24
25
|
KNOWN_FROM_FORMATS = [:yaml, :csv, :json, :ruby]
|
@@ -30,7 +31,8 @@ module DbAgile
|
|
30
31
|
:json => DbAgile::IO::JSON,
|
31
32
|
:ruby => DbAgile::IO::Ruby,
|
32
33
|
:text => DbAgile::IO::Text,
|
33
|
-
:xml => DbAgile::IO::XML
|
34
|
+
:xml => DbAgile::IO::XML,
|
35
|
+
:html => DbAgile::IO::HTML
|
34
36
|
}
|
35
37
|
|
36
38
|
# Which format for what extension
|
@@ -41,6 +43,7 @@ module DbAgile
|
|
41
43
|
".yaml" => :yaml,
|
42
44
|
".yml" => :yaml,
|
43
45
|
".xml" => :xml,
|
46
|
+
".html" => :html,
|
44
47
|
".ruby" => :ruby,
|
45
48
|
".rb" => :ruby
|
46
49
|
}
|
@@ -52,6 +55,7 @@ module DbAgile
|
|
52
55
|
:json => "application/json",
|
53
56
|
:yaml => "text/yaml",
|
54
57
|
:xml => "text/xml",
|
58
|
+
:html => "text/html",
|
55
59
|
:ruby => "text/plain"
|
56
60
|
}
|
57
61
|
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require "cgi"
|
2
|
+
module DbAgile
|
3
|
+
module IO
|
4
|
+
module HTML
|
5
|
+
|
6
|
+
DEFAULT_OPTIONS = { }
|
7
|
+
|
8
|
+
def with_tag(tag, buffer, indent = 0)
|
9
|
+
buffer << " "*indent << "<#{tag}>\n"
|
10
|
+
yield
|
11
|
+
buffer << " "*indent << "</#{tag}>\n"
|
12
|
+
end
|
13
|
+
module_function :with_tag
|
14
|
+
|
15
|
+
#
|
16
|
+
# Outputs some data as an HTML string
|
17
|
+
#
|
18
|
+
# @return [...] the buffer itself
|
19
|
+
#
|
20
|
+
def to_html(data, columns = nil, buffer = "", options = {})
|
21
|
+
options = DEFAULT_OPTIONS.merge(options)
|
22
|
+
with_tag("table", buffer, 0) {
|
23
|
+
with_tag("thead", buffer, 1) {
|
24
|
+
with_tag("tr", buffer, 2) {
|
25
|
+
columns.each{|column|
|
26
|
+
buffer << " "*3 << "<td>#{CGI::escape(column.to_s)}</td>\n"
|
27
|
+
}
|
28
|
+
}
|
29
|
+
}
|
30
|
+
with_tag("tbody", buffer, 1) {
|
31
|
+
data.each{|row|
|
32
|
+
with_tag("tr", buffer, 2) {
|
33
|
+
columns.each{|column|
|
34
|
+
value = row[column]
|
35
|
+
cssclazz = value.class.name.to_s.downcase
|
36
|
+
buffer << " "*3 << "<td class=\"#{cssclazz}\">#{CGI::escapeHTML(value.to_s)}</td>\n"
|
37
|
+
}
|
38
|
+
}
|
39
|
+
}
|
40
|
+
}
|
41
|
+
}
|
42
|
+
buffer
|
43
|
+
end
|
44
|
+
module_function :to_html
|
45
|
+
|
46
|
+
end # module HTML
|
47
|
+
end # module IO
|
48
|
+
end # module DbAgile
|