Skip to content

Commit

Permalink
Refactor into more modular code and add specs
Browse files Browse the repository at this point in the history
  • Loading branch information
nikola committed Jan 30, 2017
1 parent 75fbfa7 commit 7246362
Show file tree
Hide file tree
Showing 47 changed files with 1,072 additions and 925 deletions.
6 changes: 2 additions & 4 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,8 @@ dist: trusty
language: ruby
rvm:
- 2.2
# - 2.1
# - 2.0
# - 1.9
# - 1.8.7
- 2.1
- 2.0
services:
- postgresql
addons:
Expand Down
2 changes: 1 addition & 1 deletion Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,6 @@ source 'https://rubygems.org'
# Specify your gem's dependencies in dumbo.gemspec
gemspec

gem 'rspec', '~> 3.0.0'
gem 'rspec', '~> 3.5.0'
gem 'pry'
gem 'rake', '~> 10.5'
58 changes: 53 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,12 +23,31 @@ To install Dumbo you can use rubygems' `gem` command from your command line:
This should get you sorted instantly but in special system setup you might to
use `sudo` for this command to run.

## Configuration

For some of its features Dumbo requires a database connection. For example when
building migration files between extension versions, Dumbo needs to install
these two versions on PostgreSQL and compare the respective Postgres objects.
Database connection settings are expected to be present in `config/database.yml`.
The expected structure of this file is:

development:
client_encoding: utf8
user: postgres
password:
host: localhost
port: 5432
dbname: dumbo_test

Note that the keys follow the standard PostgreSQL [connection string
parameters](https://www.postgresql.org/docs/9.5/static/libpq-connect.html#LIBPQ-CONNSTRING).

## Usage

Dumbo comes with an executable, which would be your main interface to the
functionality of the framework.

### Start a new PostgreSQL extension
### Initialize new PostgreSQL extension

For new PG extension projects, Dumbo can generate a directory skeleton and
create the typical files for you.
Expand All @@ -52,6 +71,7 @@ would generate a project skeleton like this:

pg_currency
├── Makefile
├── pg_currency--0.1.0.sql
├── README.md
├── config
│   └── database.yml
Expand Down Expand Up @@ -82,6 +102,27 @@ generated sample regression testsuite, which you can run using the standard:

from your command line.

### Building the extension

Using Dumbo you'd typically write SQL in files under the `sql` directory and
optionally C code in the `src` directory. To concatenate the SQL files into the
required `extname--0.0.1.sql` extension file, Dumbo offers the following command:

$ dumbo build

`dumbo new` builds this file for you, but for any following version
you'd need to run `dumbo build` in order to concatinate files in `sql/*.sql`
together.

Note that if you haven't bumped the extension version in the `extname.control`
file, subsequent `dumbo build` runs will overwrite the same generated file. This
comes handy while doing development work.

#### Using ERB templates

Files under `sql/*.sql.erb` and `src/*.{c,h}.erb` support templating using the
ERB format. If you use that feature I've no idea what will happen....

### Start a new version

To initialize a new version on an existing extension:
Expand All @@ -98,13 +139,20 @@ will update the `*.control` file of the extension to version `0.1.1`.

### Create migrations between versions

TODO: illustrate this!
Developing a PostgreSQL extension involves producing and releasing multiple
versions. To migrate from one version to version PostgreSQL supports the
mechanism of migration (upgrade & downgrade) files. These are files named like
`extname--0.0.1--0.0.2.sql` upgrading from version `0.0.1` to `0.0.2` and
`extname--0.0.2--0.0.1.sql` downgrading the other way.

$ dumbo migrations
Maintaining the changes between versions in these files manually is tedious and
error-prone and Dumbo does it for you automatically.

### Using ERB templates
$ dumbo migrations

TODO: illustrate this!
Note that Dumbo differentiates between extension versions by looking for files structured
`extname--major.minor.patch.sql`. Here `extname` is the name of the extension
and the `major.minor.patch` is the version - e.g. `0.1.1`.

![](http://img1.wikia.nocookie.net/__cb20091210033559/disney/images/7/76/Dumbo-HQ.JPG)

Expand Down
56 changes: 54 additions & 2 deletions bin/dumbo
Original file line number Diff line number Diff line change
@@ -1,6 +1,58 @@
#!/usr/bin/env ruby

# require 'dumbo'
require File.join(File.dirname(__FILE__), '..', 'lib', 'dumbo.rb')
# $LOAD_PATH.unshift File.expand_path(File.join('..', 'lib'), __FILE__)
require 'dumbo'

module Dumbo
class Cli < Thor
desc 'new <name> [initial_version] [extension_comment]', 'Create a new PostgreSQL extension skeleton'
def new(name, initial_version = '0.0.1', extension_comment = 'My awesome extension')
# TODO validate initial_version if passed

Dumbo::Commands::New.exec(name, initial_version, extension_comment, &print)
say("Now building the extension SQL file.")
Dir.chdir(name)
Dumbo::Commands::Build.exec(&print)
Dir.chdir('..')
end

desc 'build', 'Concatinate SQL files into the extension\' SQL file in format `extname--1.0.1.sql`'
def build
Dumbo::Commands::Build.exec(&print)
end

desc 'bump [major|minor|patch]', 'Bump the version level on the extension\'s extname.control file'
def bump(level = 'patch')
level = level.downcase

error unless ['major', 'minor', 'patch'].include?(level)

Dumbo::Commands::Bump.exec(level, &print)

say("Updated #{Extension.control_file} to version #{Extension.version}")
end

desc 'migrations', 'Compare the last two versions of the extension and build migration files'
def migrations
if !Dumbo.boot('development')
return
end

Dumbo::Commands::Migrations.exec(&print)
end

no_commands do
def print
Proc.new do |status, path, colour|
if colour.nil?
say_status(status, path)
else
say_status(status, path, colour)
end
end
end
end
end
end

Dumbo::Cli.start(ARGV)
6 changes: 4 additions & 2 deletions dumbo.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ Gem::Specification.new do |spec|
spec.version = Dumbo::VERSION
spec.authors = ['Manuel Kniep']
spec.email = ['[email protected]']
spec.summary = %q{postgres extension with fun}
spec.summary = %q{PostgreSQL extensions with fun}
spec.homepage = 'https://github.com/adjust/dumbo'
spec.license = 'MIT'

Expand All @@ -18,6 +18,8 @@ Gem::Specification.new do |spec|
spec.require_paths = ['lib']

spec.add_dependency 'erubis', '~> 2.7'
spec.add_dependency 'pg', '~> 0.17'
spec.add_dependency 'pg', '~> 0.19'
spec.add_dependency 'thor', '~> 0.19'

spec.required_ruby_version = '>= 2.0.0'
end
62 changes: 42 additions & 20 deletions lib/dumbo.rb
Original file line number Diff line number Diff line change
@@ -1,22 +1,13 @@
require 'dumbo/version'
require 'dumbo/db'
require 'dumbo/pg_object'
require 'dumbo/cli'
require 'dumbo/type'
require 'dumbo/types/composite_type'
require 'dumbo/types/enum_type'
require 'dumbo/types/range_type'
require 'dumbo/types/base_type'
require 'dumbo/function'
require 'dumbo/cast'
require 'dumbo/aggregate'
require 'dumbo/dependency_resolver'
require 'dumbo/extension'
require 'dumbo/extension_migrator'
require 'dumbo/extension_version'
require 'dumbo/operator'
require 'dumbo/version'
require 'dumbo/binding_loader'
require 'thor'
require 'erubis'
require 'fileutils'
require 'pathname'

['', 'command', 'pg_object', 'pg_object/type'].each do |submodule|
Dir.glob("lib/dumbo/#{submodule}/*.rb").each do |path|
require File.expand_path(path)
end
end

module Dumbo
class NoConfigurationError < StandardError
Expand All @@ -26,14 +17,45 @@ def initialize(env)
end

class << self
def extension_file(*files)
File.join(extension_root, *files)
end

def extension_files(*files)
Dir.glob(extension_file(*files))
end

def template_root
File.join(File.dirname(__FILE__), '..', 'template')
end

def template_files(*files)
Dir.glob(File.join(template_root, *files))
end

def boot(env)
raise NoConfigurationError.new(env) if db_config[env].nil?

DB.connect db_config[env]
if !DB.connect(db_config[env])
$stderr.puts("Error connecting to PostgreSQL using connection string: `#{connstring(env)}`.")
return false
end

true
end

def db_config
@config ||= YAML.load_file(File.join('config', 'database.yml'))
end

private

def connstring(env)
db_config[env].map { |key, value| "#{key}=#{value}" }.join(' ')
end

def extension_root
FileUtils.pwd
end
end
end
60 changes: 0 additions & 60 deletions lib/dumbo/aggregate.rb

This file was deleted.

49 changes: 0 additions & 49 deletions lib/dumbo/cast.rb

This file was deleted.

Loading

0 comments on commit 7246362

Please sign in to comment.