turntables 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (48) hide show
  1. checksums.yaml +7 -0
  2. data/.document +3 -0
  3. data/.gitignore +6 -0
  4. data/.rspec +1 -0
  5. data/.travis.yml +6 -0
  6. data/.yardopts +1 -0
  7. data/ChangeLog.rdoc +10 -0
  8. data/Gemfile +3 -0
  9. data/LICENSE.txt +20 -0
  10. data/README.rdoc +141 -0
  11. data/Rakefile +33 -0
  12. data/bin/turntables +12 -0
  13. data/lib/turntables/constants/repository_constants.rb +6 -0
  14. data/lib/turntables/db_registry.rb +83 -0
  15. data/lib/turntables/repository.rb +148 -0
  16. data/lib/turntables/sql_modules/db_registry_sql.rb +7 -0
  17. data/lib/turntables/sql_modules/version_history_sql.rb +30 -0
  18. data/lib/turntables/transaction.rb +39 -0
  19. data/lib/turntables/turntable.rb +40 -0
  20. data/lib/turntables/turntable_exception.rb +7 -0
  21. data/lib/turntables/version.rb +4 -0
  22. data/lib/turntables/version_history.rb +90 -0
  23. data/lib/turntables.rb +2 -0
  24. data/spec/data/locations/.gitkeep +0 -0
  25. data/spec/data/locations/herp.db +0 -0
  26. data/spec/data/locations/loc1/.gitkeep +0 -0
  27. data/spec/data/malformed-dir/malformed.txt +1 -0
  28. data/spec/data/sql-just-monolithic/mono/1.sql +6 -0
  29. data/spec/data/sql-just-monolithic/seq/.gitkeep +0 -0
  30. data/spec/data/sql-just-sequential/mono/.gitkeep +0 -0
  31. data/spec/data/sql-just-sequential/seq/1.sql +6 -0
  32. data/spec/data/sql-just-sequential/seq/2.sql +7 -0
  33. data/spec/data/sql-just-sequential/seq/3.sql +9 -0
  34. data/spec/data/sql-seq-and-mono/mono/3.sql +24 -0
  35. data/spec/data/sql-seq-and-mono/seq/1.sql +6 -0
  36. data/spec/data/sql-seq-and-mono/seq/2.sql +7 -0
  37. data/spec/data/sql-seq-and-mono/seq/3.sql +9 -0
  38. data/spec/db_registry_sql_spec.rb +9 -0
  39. data/spec/repository_constants_spec.rb +13 -0
  40. data/spec/repository_spec.rb +39 -0
  41. data/spec/spec_helper.rb +4 -0
  42. data/spec/turntable_exception_spec.rb +16 -0
  43. data/spec/turntable_spec.rb +71 -0
  44. data/spec/turntables_spec.rb +8 -0
  45. data/spec/version_history_spec.rb +55 -0
  46. data/spec/version_history_sql_spec.rb +31 -0
  47. data/turntables.gemspec +26 -0
  48. metadata +184 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: f3b7cb827f0bb39e3cc31e2ead6a8d271e3068bf
4
+ data.tar.gz: bd4970ab7927b33a741e17b331056d03b81e388d
5
+ SHA512:
6
+ metadata.gz: 09104fc43b8e05ca2a45798b0d3742c3f70189e95cfcbfa4779e2dd8ed42b18b49b4a2e9ffe03055133523b53dff4b9d81f258048ad15eadd8986753fd72725e
7
+ data.tar.gz: 32404ef39e95bb8dd4a61e1f1faa5add76b315b9a9607c146615e29b78a9fb8adb525f795e3145d793dd9916ff6fc7d030236e39afbcffb3d4f2d3af0aa619ad
data/.document ADDED
@@ -0,0 +1,3 @@
1
+ -
2
+ ChangeLog.rdoc
3
+ LICENSE.txt
data/.gitignore ADDED
@@ -0,0 +1,6 @@
1
+ *.swp
2
+ .yardoc
3
+ Gemfile.lock
4
+ doc/
5
+ pkg/
6
+ vendor/cache/*.gem
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --colour --format documentation
data/.travis.yml ADDED
@@ -0,0 +1,6 @@
1
+ language: ruby
2
+ rvm:
3
+ - 1.9.3
4
+ - 2.0.0
5
+ script: bundle exec rspec spec
6
+
data/.yardopts ADDED
@@ -0,0 +1 @@
1
+ --markup rdoc --title "turntables Documentation" --protected
data/ChangeLog.rdoc ADDED
@@ -0,0 +1,10 @@
1
+ === 1.0.0 / 2013-07-03
2
+
3
+ * Initial release:
4
+ * Can create db versioning with sequential transactions
5
+ * Can create db versioning with monolithic transactions
6
+ * Can detect malformed dirs / repos of said sql
7
+
8
+ * TODO
9
+ * Want to have a way to set the database name
10
+
data/Gemfile ADDED
@@ -0,0 +1,3 @@
1
+ source :rubygems
2
+
3
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2013 psyomn
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,141 @@
1
+ = turntables {<img src="https://codeclimate.com/github/psyomn/turntables.png" />}[https://codeclimate.com/github/psyomn/turntables] {<img src="https://travis-ci.org/psyomn/turntables.png?branch=master" alt="Build Status" />}[https://travis-ci.org/psyomn/turntables]
2
+
3
+ * {Source}[http://github.com/psyomn/turntables]
4
+ * {Homepage}[https://rubygems.org/gems/turntables]
5
+ * {Documentation}[http://rubydoc.info/gems/turntables/frames]
6
+
7
+ == Description
8
+
9
+ This is not really ready, but putting it out there because I actually need it
10
+ for something else I'm working on. If you can give a hand it will be very
11
+ appreciated (contact me).
12
+
13
+ == Features
14
+
15
+ == Examples
16
+ This is a simple tutorial on how to invoke the database manager.
17
+
18
+ You need a directory structure like this:
19
+
20
+ .
21
+ |-- main.rb
22
+ `-- sql
23
+ |-- mono
24
+ `-- seq
25
+ |-- 1.sql
26
+ |-- 2.sql
27
+ |-- 3.sql
28
+ `-- 4.sql
29
+
30
+ The sql files can be like this for example. The comments that are prepended
31
+ with '--$' are inserted in the version history table within the table manager
32
+ so that if someone needs to diagnose issues on the long run, there are the
33
+ comments there at least (along with a version, and date field).
34
+
35
+ 1.sql:
36
+
37
+ --$ First version will be created with this. The comments to be added in the
38
+ --$ versions history table can be prepended with the '$' sign in order for you
39
+ --$ specify comments (if needed). It's here if you want it.
40
+ -- This is an example file to show how the turntables gem could work maybe
41
+ -- with people. and stuff.
42
+ -- This SQL file adds the person, and work_descriptions entities to the
43
+ -- database.
44
+ CREATE TABLE persons (
45
+ id integer primary key autoincrement,
46
+ name varchar(50),
47
+ surname varchar(50),
48
+ age integer
49
+ );
50
+
51
+ CREATE TABLE work_descriptions (
52
+ id integer primary key autoincrement,
53
+ description text
54
+ );
55
+
56
+ 2.sql:
57
+
58
+ --$ Bump to version 2. This is starting to look good!
59
+ -- And this is for the second revision of the database.
60
+
61
+ CREATE TABLE inventory (
62
+ id integer primary key autoincrement,
63
+ description text
64
+ );
65
+
66
+ 3.sql:
67
+
68
+ --$ We did a mistake. We forgot to add a field to the persons table. The extra
69
+ --$ field to be added is the DOB.
70
+ ALTER TABLE persons ADD COLUMN dob BIGINT;
71
+
72
+ 4.sql:
73
+
74
+ --$ This table is added because now the system requires accounts as well.
75
+ --$ Sat Jul 13 21:45:40 EDT 2013
76
+ -- Table to create accounts for people.
77
+ CREATE TABLE accounts (
78
+ balance float,
79
+ owner_id integer,
80
+ FOREIGN KEY(owner_id) references persons(id)
81
+ );
82
+
83
+ main.rb should be like this:
84
+
85
+ require 'turntables'
86
+
87
+ include Turntables
88
+
89
+ puts "This is to test the library and proof of concept of turntables"
90
+
91
+ # Ideal way of calling this library
92
+ turntable = Turntable.new
93
+
94
+ # sql is a directory containing two subdirs: seq, mono
95
+ # seq contains sequential transactions
96
+ # mono contains monolithic transactions
97
+ turntable.register('sql')
98
+ turntable.make!
99
+
100
+ # Note: There should not be any other calls to the library. We give it the
101
+ # sql repository location, and then it's the responsibility of Turntables to
102
+ # decide whether to take action or not.
103
+
104
+ If you require that the database be made at a specified location, you should use
105
+ the method `make_at!(location)`. To do this, just do what the above code does
106
+ until `make!`. Then you need to call `make_at!` in the following way:
107
+
108
+ turntable.make_at!("path/to/database.db")
109
+
110
+ Right now versions should be marked as the filename. Try to have intergers as
111
+ versions, to avoid odd behaviour. So in this case versions {1,2,3} would
112
+ respectively be in file form {1.sql, 2.sql, 3.sql}.
113
+
114
+ The monolithic transactions should be a combinations of all the versions, up to
115
+ the one it denotes. In other words, version 4 would be the combination of all
116
+ previous ones including itself {1.sql, 2.sql, 3.sql, 4.sql}.
117
+
118
+ == Requirements
119
+
120
+ * I've tested this with Ruby Versions = {2.0, 1.9.3}, though you should not
121
+ really have any issues in theory.
122
+
123
+ * SQLite3 gem
124
+
125
+ == Install
126
+
127
+ $ gem install turntables
128
+
129
+ == Synopsis
130
+
131
+ $ turntables
132
+
133
+ == Copyright
134
+
135
+ Copyright (c) 2013 psyomn
136
+
137
+ == License
138
+
139
+ License is MIT regardless what you may see or find elsewhere; I might have not
140
+ changed it due to lack of time.
141
+
data/Rakefile ADDED
@@ -0,0 +1,33 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+
5
+ begin
6
+ require 'bundler'
7
+ rescue LoadError => e
8
+ warn e.message
9
+ warn "Run `gem install bundler` to install Bundler."
10
+ exit -1
11
+ end
12
+
13
+ begin
14
+ Bundler.setup(:development)
15
+ rescue Bundler::BundlerError => e
16
+ warn e.message
17
+ warn "Run `bundle install` to install missing gems."
18
+ exit e.status_code
19
+ end
20
+
21
+ require 'rake'
22
+
23
+ require 'rspec/core/rake_task'
24
+ RSpec::Core::RakeTask.new
25
+
26
+ task :test => :spec
27
+ task :default => :spec
28
+
29
+ require "bundler/gem_tasks"
30
+
31
+ require 'yard'
32
+ YARD::Rake::YardocTask.new
33
+ task :doc => :yard
data/bin/turntables ADDED
@@ -0,0 +1,12 @@
1
+ #!/usr/bin/env ruby
2
+ require 'turntables'
3
+ include Turntables
4
+
5
+ if ARGV.count > 0
6
+ turntable = Turntable.new
7
+ turntable.register(ARGV[0])
8
+ turntable.make!
9
+ else
10
+ puts "Usage: "
11
+ puts " turtables <repo-dir>"
12
+ end
@@ -0,0 +1,6 @@
1
+ module Turntables
2
+ module RepositoryConstants
3
+ SeqDir = "seq/"
4
+ MonoDir = "mono/"
5
+ end
6
+ end
@@ -0,0 +1,83 @@
1
+ require 'sqlite3'
2
+ require 'singleton'
3
+
4
+ require 'turntables/sql_modules/db_registry_sql'
5
+
6
+ module Turntables
7
+ # Database Registry pattern that connects to an sqlite 3 database.
8
+ # @author Simon Symeonidis
9
+ class DbRegistry
10
+ include Singleton
11
+ include DbRegistrySql
12
+
13
+ # Init with default db name
14
+ # @param dbname is the name of the database is if it not specified
15
+ # TODO we need to be able to set this somehow differently - applications
16
+ # might require to name their database with their own specific name.
17
+ def initialize(dbname="default.db")
18
+ @handle = SQLite3::Database.new(dbname)
19
+ @name = dbname
20
+ end
21
+
22
+ # Execute (any sort) of sql
23
+ # @param sql is the multiple arguments of the function to execute. Usually
24
+ # you should give it first the sql you want that is to be prepared. Then
25
+ # you specify the variables to be set in the query, in the right order.
26
+ # @example Simple usage
27
+ # sql = "INSERT INTO person (name, surname) values (?,?)"
28
+ # DbRegistry.instance.execute(sql,"jon","doe")
29
+ # @return sql data
30
+ def execute(*sql)
31
+ @handle.execute(*sql)
32
+ rescue => ex
33
+ puts ex.message
34
+ puts ex.backtrace
35
+ puts "Offending sql: "
36
+ puts sql
37
+ end
38
+
39
+ # For special queries that may contain multiple statements. For example a
40
+ # query that contains first a 'create table' query, and then some inserts to
41
+ # poppulate that table. Ideally this should be used in order to create the
42
+ # tables in sequence.
43
+ # @param sql is the sql that contains multiple statements
44
+ def execute_batch(sql)
45
+ @handle.execute_batch(sql)
46
+ rescue => ex
47
+ puts ex.message
48
+ puts ex.backtrace
49
+ puts "Offending sql: "
50
+ puts sql
51
+ end
52
+
53
+ # Check if a table exists in the database
54
+ # @param name is the name of the table to check if exists
55
+ # @return true if table exists, false if not
56
+ def table_exists?(name)
57
+ val = @handle.execute(ExistsSql, "table", name)
58
+ 1 == val.flatten[0]
59
+ end
60
+
61
+ # Close the current database.
62
+ # @warn This is mainly here for the rspec testing, and should not be used
63
+ # unless you really know what you're doing.
64
+ def close!
65
+ @handle.close unless @handle.closed?
66
+ end
67
+
68
+ # Open the database, with the name given previously
69
+ # @warn This is mainly here for the rspec testing, and should not be used
70
+ # unless you really know what you're doing.
71
+ def open!
72
+ @handle = SQLite3::Database.new(@name) if @handle.closed?
73
+ end
74
+
75
+ # The database name
76
+ attr_accessor :name
77
+
78
+ private
79
+ # Other classes should not use the database handle directly
80
+ attr :handle
81
+ end
82
+ end
83
+
@@ -0,0 +1,148 @@
1
+ require 'fileutils'
2
+
3
+ # lib
4
+ require 'turntables/transaction'
5
+ require 'turntables/version_history'
6
+ require 'turntables/db_registry'
7
+ require 'turntables/sql_modules/version_history_sql'
8
+ require 'turntables/constants/repository_constants'
9
+
10
+ module Turntables
11
+ # @author Simon Symeonidis
12
+ # A turntables repository. This class is responsible for handling the
13
+ # versioning. This includes tasks such as checking database availability,
14
+ # and pulling up the version history table and modifying where needed (for
15
+ # example when completing a transaction, recording the date, the new version,
16
+ # and comments about said transaction).
17
+ class Repository
18
+ include RepositoryConstants
19
+
20
+ def initialize
21
+ @transactions = Array.new
22
+ @monolithics = Array.new
23
+ end
24
+
25
+ # @param location is the location of the sql repository for now (a directory
26
+ # for now).
27
+ def register(location)
28
+ @relative_dir = location
29
+ @sequential_dir = "#{@relative_dir}/#{SeqDir}/"
30
+ @monolithic_dir = "#{@relative_dir}/#{MonoDir}/"
31
+
32
+ # Initialize the transactions
33
+ init_sequential_transactions!
34
+ init_monolithic_transactions!
35
+ end
36
+
37
+ # Function to call in order to make the database.
38
+ #
39
+ # TODO: Here, it should detect in what state the current database is in, and
40
+ # go from there. In other words, whether it can skip sequential database
41
+ # transactions by loading a monolithic one to exclude previous transactions.
42
+ def make!
43
+ select_transactions!
44
+ @transactions.each do |transaction|
45
+ vh = VersionHistory.new(transaction.version, transaction.comment)
46
+ VersionHistory.insert(vh)
47
+ DbRegistry.instance.execute_batch(transaction.data)
48
+ end
49
+ end
50
+
51
+ # Check to see if the directory structure is malformed.
52
+ # @return true if the directory structure is malformed
53
+ def malformed?
54
+ abs_seq = File.expand_path(@sequential_dir)
55
+ abs_mon = File.expand_path(@monolithic_dir)
56
+ !(File.exists?(abs_seq) && File.exists?(abs_mon))
57
+ end
58
+
59
+ attr_accessor :sequential_dir
60
+ attr_accessor :monolithic_dir
61
+ attr_accessor :relative_dir
62
+ # Array<Turntables::Transaction>
63
+ attr_accessor :transactions
64
+ # Array<Turntables::Transaction>
65
+ attr_accessor :monolithics
66
+
67
+ private
68
+
69
+ # Depending on what has been done before, we need to choose the proper
70
+ # transactions.
71
+ # TODO: This probably can be done cleaner
72
+ def select_transactions!
73
+ check = VersionHistory.check
74
+ if check == :fresh
75
+ # Fresh db means, we create the version history table
76
+ prepend_monolithic_transactions!
77
+ VersionHistory.pull_up!
78
+ else
79
+ last_version = VersionHistory.find_last.version
80
+ @transactions.select!{|tr| tr.version > last_version}
81
+ end
82
+ end
83
+
84
+ # This checks to see if any monolithic transactions exist, which can
85
+ # eliminate previous sequential transactions.
86
+ def prepend_monolithic_transactions!
87
+ max = @monolithics.max_by &:version
88
+ unless max.nil?
89
+ @transactions.select!{|tr| tr.version > max.version}
90
+ @transactions = @transactions.unshift(max)
91
+ end
92
+ end
93
+
94
+ # Find all the transactions that are to be processed sequentially
95
+ # @return nil
96
+ def init_sequential_transactions!
97
+ init_generic_transactions(sequential_files, @transactions)
98
+ end
99
+
100
+ # Find all the transactions that are to be processed only once
101
+ # @return nil
102
+ def init_monolithic_transactions!
103
+ init_generic_transactions(monolithic_files, @monolithics)
104
+ end
105
+
106
+ # this is a generic transaction reader
107
+ # return nil
108
+ def init_generic_transactions(file_list, transaction_holder)
109
+ file_list.each do |path|
110
+ data = File.open(path).read
111
+ filename = path.split(/\//).last
112
+ transaction_holder.push Transaction.new(data,filename)
113
+ end
114
+ nil
115
+ end
116
+
117
+ # Get the sequential transactional files
118
+ def sequential_files
119
+ get_files_in_dir(@sequential_dir)
120
+ end
121
+
122
+ # Get the monolithic transactional files
123
+ def monolithic_files
124
+ get_files_in_dir(@monolithic_dir)
125
+ end
126
+
127
+ # Return the files that are in the given directory
128
+ # @param path is the path to look for files in the directory
129
+ # @return Array<String> of files sorted by stringnum_comparison predicate
130
+ def get_files_in_dir(path)
131
+ Dir["#{path}*"].sort!{|e1,e2| stringnum_comparison(e1,e2)}
132
+ end
133
+
134
+ # Compare two strings with each other by extracting the digits
135
+ def stringnum_comparison(a,b)
136
+ extract_digits(a) <=> extract_digits(b)
137
+ end
138
+
139
+ # Extract the numbers from the string, and convert to Fixnum
140
+ # @param string is the string to extract the numbers from
141
+ # @return the number that was found in the string
142
+ def extract_digits(string)
143
+ string.gsub(/\D/,'').to_i
144
+ end
145
+
146
+ end
147
+ end
148
+
@@ -0,0 +1,7 @@
1
+ module Turntables
2
+ # @author Simon Symeonidis
3
+ # The sql for the db registry.
4
+ module DbRegistrySql
5
+ ExistsSql = "SELECT COUNT(type) from sqlite_master where type=? and name=?"
6
+ end
7
+ end
@@ -0,0 +1,30 @@
1
+ module Turntables
2
+ # @author Simon Symeonidis
3
+ # Some static information factored out to avoid class variables, and to
4
+ # separate concerns.
5
+ module VersionHistorySql
6
+ # Table name of this guy
7
+ TableName = "version_histories"
8
+
9
+ # Table schema for the version history table.
10
+ Create = "CREATE TABLE #{TableName} ("\
11
+ "id INTEGER PRIMARY KEY AUTOINCREMENT, "\
12
+ "version BIGINT, "\
13
+ "date BIGINT, "\
14
+ "comment TEXT)"
15
+
16
+ # Select last inserted transaction
17
+ SelectLast = "SELECT * FROM #{TableName} "\
18
+ " WHERE id=(SELECT MAX(id) FROM #{TableName});"
19
+
20
+ # Select a record by id
21
+ SelectById = "SELECT * FROM #{TableName} WHERE id=?"
22
+
23
+ # Select all the records
24
+ SelectAll = "SELECT * FROM #{TableName}"
25
+
26
+ # Sql to insert a version history into the table
27
+ Insert = "INSERT INTO #{TableName} (version,date,comment)"\
28
+ " values (?,?,?)"
29
+ end
30
+ end
@@ -0,0 +1,39 @@
1
+ module Turntables
2
+ # @author Simon Symeonidis
3
+ # @date Wed Jul 10 19:51:42 EDT 2013
4
+ # This class takes care of a single transaction
5
+ class Transaction
6
+
7
+ # Initialize this object with the contents of the sql file
8
+ # @param sql_file_contents are the contents of the given sql file
9
+ # @param filename is the filename of the given sql file. We use the filenames
10
+ # for the version that it is supposed to upgrade to.
11
+ def initialize(sql_file_contents,filename)
12
+ # Select only the lines that begin with '--$'
13
+ @comment = sql_file_contents.lines.select{|el| el.match(/--\$/)}.join
14
+ @comment.gsub!(/--\$/, '')
15
+ @version = filename.to_i
16
+ @data = sql_file_contents
17
+ end
18
+
19
+ # The version should be obtained from the file name of the respective sql
20
+ # file.
21
+ attr_accessor :version
22
+
23
+ # The comment should be parsed out from the respective sql file. We want to
24
+ # keep the comments in the sql file to keep things organized. We do not want
25
+ # to alter the sql language to fit our needs. Therefore we just require the
26
+ # user to comment lines as '--$ my comment here' in order to parse them out
27
+ # @example How to write comments that are to be parsed
28
+ # --$ author jon doe
29
+ # --$ This sql file will update the schema to version 1.2
30
+ # --$ You should note this and that
31
+ # -- This commen line would be ignored
32
+ #
33
+ # CREATE TABLE accounts ( ... )
34
+ attr_accessor :comment
35
+
36
+ # The sql information to be passed on to the db registry
37
+ attr_accessor :data
38
+ end
39
+ end
@@ -0,0 +1,40 @@
1
+ require 'turntables/db_registry'
2
+ require 'turntables/repository'
3
+ require 'turntables/turntable_exception'
4
+
5
+ module Turntables
6
+ # @author Simon Symeonidis
7
+ # The facade controller to the rest of this library.
8
+ class Turntable
9
+ # Default constructor, that initializes some standard parameters
10
+ def initialize
11
+ @revisions = Array.new
12
+ @repository = Repository.new
13
+ end
14
+
15
+ # Register a revision that needs to be processed later
16
+ # @param repository_root_path is the root path to all the sql.
17
+ def register(repository_root_path)
18
+ @repository.register(repository_root_path)
19
+ end
20
+
21
+ # Make the repository at a specific location instead of default.
22
+ def make_at!(location)
23
+ DbRegistry.instance.close!
24
+ DbRegistry.instance.name = location
25
+ DbRegistry.instance.open!
26
+ make!
27
+ end
28
+
29
+ # Create the tables by going through each revision
30
+ def make!
31
+ if @repository.malformed?
32
+ raise TurntableException, "The directory structure is malformed."
33
+ else
34
+ @repository.make!
35
+ end
36
+ end
37
+
38
+ attr_accessor :repository
39
+ end
40
+ end
@@ -0,0 +1,7 @@
1
+ module Turntables
2
+ # @author Simon Symeonidis
3
+ # library exception. Raise this instead of RuntimeError
4
+ class TurntableException < RuntimeError
5
+ end
6
+ end
7
+
@@ -0,0 +1,4 @@
1
+ module Turntables
2
+ # turntables version
3
+ VERSION = "1.0.1"
4
+ end