schematic 0.6.2 → 0.7.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +14 -8
- data/.travis.yml +17 -0
- data/Gemfile +6 -1
- data/LICENSE +1 -1
- data/README.md +106 -0
- data/Rakefile +3 -8
- data/lib/schematic.rb +3 -42
- data/lib/schematic/exceptions.rb +13 -0
- data/lib/schematic/generator/column.rb +17 -11
- data/lib/schematic/generator/namespaces.rb +3 -3
- data/lib/schematic/generator/restrictions/base.rb +5 -5
- data/lib/schematic/generator/restrictions/custom.rb +3 -2
- data/lib/schematic/generator/restrictions/enumeration.rb +5 -2
- data/lib/schematic/generator/restrictions/length.rb +4 -2
- data/lib/schematic/generator/restrictions/numericality.rb +3 -1
- data/lib/schematic/generator/restrictions/pattern.rb +4 -3
- data/lib/schematic/generator/sandbox.rb +4 -1
- data/lib/schematic/generator/types.rb +14 -13
- data/lib/schematic/generator/uniqueness.rb +7 -8
- data/lib/schematic/generator/xsd.rb +32 -26
- data/lib/schematic/serializers/xsd.rb +6 -6
- data/lib/schematic/version.rb +1 -1
- data/schematic.gemspec +23 -24
- data/spec/schematic/generator/restrictions/custom_spec.rb +15 -18
- data/spec/schematic/generator/restrictions/enumeration_spec.rb +31 -31
- data/spec/schematic/generator/restrictions/length_spec.rb +35 -30
- data/spec/schematic/generator/restrictions/mixin_spec.rb +11 -15
- data/spec/schematic/generator/restrictions/numericality_spec.rb +11 -11
- data/spec/schematic/generator/restrictions/pattern_spec.rb +20 -21
- data/spec/schematic/generator/sandbox_spec.rb +17 -17
- data/spec/schematic/generator/uniqueness_spec.rb +38 -37
- data/spec/schematic/serializers/xsd_extend_spec.rb +11 -11
- data/spec/schematic/serializers/xsd_validation_presence_spec.rb +16 -11
- data/spec/schematic/serializers/xsd_xsd_ignore_methods_spec.rb +3 -3
- data/spec/schematic/serializers/xsd_xsd_methods_spec.rb +27 -24
- data/spec/schematic/serializers/xsd_xsd_minimum_occurrences_for_spec.rb +13 -8
- data/spec/schematic_serializers_xsd_spec.rb +70 -67
- data/spec/spec_helper.rb +8 -113
- data/spec/support/database.rb +9 -0
- data/spec/support/helpers.rb +111 -0
- data/spec/support/with_model.rb +5 -0
- data/spec/{xsd → support/xsd}/XMLSchema.xsd +0 -0
- data/spec/{xsd → support/xsd}/xml.xsd +0 -0
- metadata +54 -69
- data/.rspec +0 -1
- data/.rvmrc +0 -1
- data/README.rdoc +0 -103
- data/spec/support/extensions/active_model/validations/inclusion.rb +0 -69
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 9c76641aa454b778d4e26f79dc681629dcf6ef6a
|
4
|
+
data.tar.gz: dd47b6effb9ca6bc3036f8a71ebc840faba17fa4
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 910d7a63f610016582b3c8d0a9e569e5c0d5cb2846582c7f142dfe6fa693d024d8f149ea37dc812eecf572c8e83bcbf2b635fd6bb84c6ff81f2f91265f99952a
|
7
|
+
data.tar.gz: 0846991be161e75ac8e44c4c22b2f097ad5a2536926c11cf697603314560b6098f2936237c81919fc94af325eced78b1c139d11a423542faa8d47d83fad24710
|
data/.gitignore
CHANGED
@@ -1,11 +1,17 @@
|
|
1
|
-
.pairs
|
2
1
|
*.gem
|
3
|
-
|
4
|
-
.DS_Store
|
2
|
+
*.rbc
|
5
3
|
.bundle
|
6
|
-
.
|
7
|
-
.
|
4
|
+
.config
|
5
|
+
.yardoc
|
8
6
|
Gemfile.lock
|
9
|
-
|
10
|
-
|
11
|
-
|
7
|
+
InstalledFiles
|
8
|
+
_yardoc
|
9
|
+
coverage
|
10
|
+
doc/
|
11
|
+
lib/bundler/man
|
12
|
+
pkg
|
13
|
+
rdoc
|
14
|
+
spec/reports
|
15
|
+
test/tmp
|
16
|
+
test/version_tmp
|
17
|
+
tmp
|
data/.travis.yml
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
language: ruby
|
2
|
+
|
3
|
+
rvm:
|
4
|
+
- "1.9"
|
5
|
+
- "2.0"
|
6
|
+
- "2.1"
|
7
|
+
- "jruby-19mode"
|
8
|
+
- "rbx-2.2"
|
9
|
+
|
10
|
+
env:
|
11
|
+
- ACTIVE_RECORD_BRANCH="master"
|
12
|
+
- ACTIVE_RECORD_VERSION="~> 4.1.0"
|
13
|
+
- ACTIVE_RECORD_VERSION="~> 4.0.0"
|
14
|
+
|
15
|
+
matrix:
|
16
|
+
allow_failures:
|
17
|
+
- env: ACTIVE_RECORD_BRANCH="master"
|
data/Gemfile
CHANGED
@@ -1,4 +1,9 @@
|
|
1
|
-
source
|
1
|
+
source 'https://rubygems.org'
|
2
2
|
|
3
3
|
# Specify your gem's dependencies in schematic.gemspec
|
4
4
|
gemspec
|
5
|
+
|
6
|
+
gem 'activerecord', :github => 'rails', :branch => ENV['ACTIVE_RECORD_BRANCH'] if ENV['ACTIVE_RECORD_BRANCH']
|
7
|
+
gem 'activerecord', ENV['ACTIVE_RECORD_VERSION'] if ENV['ACTIVE_RECORD_VERSION']
|
8
|
+
gem 'activerecord-jdbcsqlite3-adapter', :platforms => :jruby
|
9
|
+
gem 'sqlite3', '1.3.8', :platforms => :ruby
|
data/LICENSE
CHANGED
data/README.md
ADDED
@@ -0,0 +1,106 @@
|
|
1
|
+
# [Schematic](http://github.com/casecommons/schematic/)
|
2
|
+
|
3
|
+
[![Build Status](https://secure.travis-ci.org/Casecommons/schematic.svg?branch=master)](https://travis-ci.org/Casecommons/schematic)
|
4
|
+
[![Code Climate](https://img.shields.io/codeclimate/github/Casecommons/schematic.svg)](https://codeclimate.com/github/Casecommons/schematic)
|
5
|
+
[![Gem Version](https://badge.fury.io/rb/schematic.svg)](https://rubygems.org/gems/schematic)
|
6
|
+
|
7
|
+
Automatic XSD generation for your ActiveRecord models.
|
8
|
+
|
9
|
+
## Installation
|
10
|
+
|
11
|
+
Install as usual: `gem install schematic` or add `gem 'schematic'` to your Gemfile. See `.travis.yml` for supported (tested) Ruby versions.
|
12
|
+
|
13
|
+
## Usage
|
14
|
+
|
15
|
+
```ruby
|
16
|
+
class Post < ActiveRecord::Base
|
17
|
+
end
|
18
|
+
|
19
|
+
Post.to_xsd #=> (a bunch of xml)
|
20
|
+
```
|
21
|
+
|
22
|
+
Validations will automatically add restrictions to the XSD for fields. If a validation has a conditional if or unless option it will be skipped. However if you wish to force the inclusion of the validation in the XSD you can set: `{ :xsd => { :include => true } }` in the options e.g.
|
23
|
+
|
24
|
+
```ruby
|
25
|
+
class Post < ActiveRecord::Base
|
26
|
+
validates :category, :inclusion => { :in => ["foo", "bar"], :xsd => { :include => true } }, :if => lambda { ... }
|
27
|
+
end
|
28
|
+
```
|
29
|
+
|
30
|
+
You can include or exclude additional elements:
|
31
|
+
|
32
|
+
```ruby
|
33
|
+
class Post < ActiveRecord::Base
|
34
|
+
schematic do
|
35
|
+
element :title
|
36
|
+
element :author => [:name, :email, :url]
|
37
|
+
element :blog => { :post => { :category => nil } }
|
38
|
+
ignore :comments
|
39
|
+
ignore :attachments => [:filetype]
|
40
|
+
end
|
41
|
+
end
|
42
|
+
```
|
43
|
+
|
44
|
+
You can also change the name of the root tag:
|
45
|
+
|
46
|
+
```ruby
|
47
|
+
class Post < ActiveRecord::Base
|
48
|
+
schematic do
|
49
|
+
root "blog-post"
|
50
|
+
end
|
51
|
+
end
|
52
|
+
```
|
53
|
+
|
54
|
+
If you want to programatically include or exclude elements use `Post#schematic_sandbox.added_elements` and `Post#schematic_sandbox.ignored_elements`.
|
55
|
+
|
56
|
+
The former is a Hash and the latter is an Array.
|
57
|
+
|
58
|
+
You can define your own custom restrictions by inheriting from the Restrictions Base class:
|
59
|
+
|
60
|
+
```ruby
|
61
|
+
class MyCustomRestriction < Schematic::Generator::Restrictions::Base
|
62
|
+
def generate(builder)
|
63
|
+
for_validator ActiveModel::BlockValidator do |validator|
|
64
|
+
builder.xs(:enumeration, "value" => "foo")
|
65
|
+
builder.xs(:enumeration, "value" => "bar")
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
```
|
70
|
+
|
71
|
+
You can have a custom pattern restriction from a custom validator:
|
72
|
+
|
73
|
+
```ruby
|
74
|
+
class MyValidator < ActiveModel::EachValidator
|
75
|
+
def validate_each(record, attribute, value)
|
76
|
+
# ...
|
77
|
+
end
|
78
|
+
|
79
|
+
def xsd_pattern_restrictions
|
80
|
+
[/foo/, /bar/]
|
81
|
+
end
|
82
|
+
end
|
83
|
+
```
|
84
|
+
|
85
|
+
You can have a custom enumeration restriction from a custom validator:
|
86
|
+
|
87
|
+
```ruby
|
88
|
+
class MyValidator < ActiveModel::EachValidator
|
89
|
+
def validate_each(record, attribute, value)
|
90
|
+
# ...
|
91
|
+
end
|
92
|
+
|
93
|
+
def xsd_field_enumeration_restrictions
|
94
|
+
["foo", "bar"]
|
95
|
+
end
|
96
|
+
end
|
97
|
+
```
|
98
|
+
|
99
|
+
## Requirements
|
100
|
+
|
101
|
+
- ActiveRecord 4.x
|
102
|
+
|
103
|
+
## License
|
104
|
+
|
105
|
+
Copyright © 2010–2014 Case Commons, LLC.
|
106
|
+
Licensed under the MIT license, available in the “LICENSE” file.
|
data/Rakefile
CHANGED
@@ -1,12 +1,7 @@
|
|
1
|
-
require '
|
2
|
-
require 'rspec/core'
|
1
|
+
require 'bundler/gem_tasks'
|
3
2
|
require 'rspec/core/rake_task'
|
4
3
|
|
5
|
-
|
6
|
-
|
4
|
+
desc 'Run specs'
|
5
|
+
RSpec::Core::RakeTask.new
|
7
6
|
|
8
7
|
task :default => :spec
|
9
|
-
|
10
|
-
desc "Run all specs in spec directory (excluding plugin specs)"
|
11
|
-
RSpec::Core::RakeTask.new(:spec)
|
12
|
-
|
data/lib/schematic.rb
CHANGED
@@ -1,44 +1,5 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
def message
|
4
|
-
"This class does not include ActiveModel::Serializers::Xml. You cannot generate an XSD from it."
|
5
|
-
end
|
6
|
-
end
|
7
|
-
|
8
|
-
class ClassMissingAttributes < Exception
|
9
|
-
def message
|
10
|
-
"This class does not implement #attributes. You cannot generate an XSD from it."
|
11
|
-
end
|
12
|
-
end
|
13
|
-
|
14
|
-
module Generator
|
15
|
-
autoload :Sandbox, 'schematic/generator/sandbox'
|
16
|
-
autoload :Xsd, 'schematic/generator/xsd'
|
17
|
-
autoload :Names, 'schematic/generator/names'
|
18
|
-
autoload :Namespaces, 'schematic/generator/namespaces'
|
19
|
-
autoload :Column, 'schematic/generator/column'
|
20
|
-
autoload :ColumnValidator, 'schematic/generator/column_validator'
|
21
|
-
autoload :Types, 'schematic/generator/types'
|
22
|
-
autoload :Uniqueness, 'schematic/generator/uniqueness'
|
23
|
-
|
24
|
-
module Restrictions
|
25
|
-
autoload :Base, 'schematic/generator/restrictions/base'
|
26
|
-
autoload :Custom, 'schematic/generator/restrictions/custom'
|
27
|
-
autoload :Enumeration, 'schematic/generator/restrictions/enumeration'
|
28
|
-
autoload :Length, 'schematic/generator/restrictions/length'
|
29
|
-
autoload :Pattern, 'schematic/generator/restrictions/pattern'
|
30
|
-
autoload :Numericality, 'schematic/generator/restrictions/numericality'
|
31
|
-
end
|
32
|
-
end
|
33
|
-
module Serializers
|
34
|
-
autoload :Xsd, 'schematic/serializers/xsd'
|
35
|
-
end
|
36
|
-
|
37
|
-
autoload :Version, 'schematic/version'
|
38
|
-
end
|
39
|
-
|
40
|
-
require "builder"
|
41
|
-
require 'active_support/inflector/inflections'
|
42
|
-
require 'active_support/inflections'
|
1
|
+
require 'schematic/version'
|
2
|
+
require 'schematic/serializers/xsd'
|
43
3
|
|
4
|
+
require 'active_record/base'
|
44
5
|
ActiveRecord::Base.send(:extend, Schematic::Serializers::Xsd)
|
@@ -0,0 +1,13 @@
|
|
1
|
+
module Schematic
|
2
|
+
class ClassMissingXmlSerializer < Exception
|
3
|
+
def message
|
4
|
+
'This class does not include ActiveModel::Serializers::Xml. You cannot generate an XSD from it.'
|
5
|
+
end
|
6
|
+
end
|
7
|
+
|
8
|
+
class ClassMissingAttributes < Exception
|
9
|
+
def message
|
10
|
+
'This class does not implement #attributes. You cannot generate an XSD from it.'
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
@@ -1,11 +1,17 @@
|
|
1
|
+
require 'active_model/validations/presence'
|
2
|
+
require 'schematic/generator/restrictions/custom'
|
3
|
+
require 'schematic/generator/restrictions/enumeration'
|
4
|
+
require 'schematic/generator/restrictions/length'
|
5
|
+
require 'schematic/generator/restrictions/numericality'
|
6
|
+
require 'schematic/generator/restrictions/pattern'
|
7
|
+
|
1
8
|
module Schematic
|
2
9
|
module Generator
|
3
10
|
class Column
|
4
11
|
attr_accessor :restriction_classes
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
end
|
12
|
+
|
13
|
+
def self.restriction_classes
|
14
|
+
Restrictions::Base.descendants.freeze
|
9
15
|
end
|
10
16
|
|
11
17
|
def initialize(klass, column, additional_methods = {}, ignored_methods = {}, required_methods = [], non_required_methods = [])
|
@@ -21,16 +27,16 @@ module Schematic
|
|
21
27
|
return if skip_generation?
|
22
28
|
|
23
29
|
options = {
|
24
|
-
|
25
|
-
|
26
|
-
|
30
|
+
'name' => @column.name.dasherize,
|
31
|
+
'minOccurs' => minimum_occurrences_for_column.to_s,
|
32
|
+
'maxOccurs' => '1'
|
27
33
|
}
|
28
|
-
options.merge!({
|
34
|
+
options.merge!({'nillable' => 'false'}) if minimum_occurrences_for_column > 0
|
29
35
|
|
30
36
|
builder.xs :element, options do |field|
|
31
37
|
field.xs :complexType do |complex_type|
|
32
38
|
complex_type.xs :simpleContent do |simple_content|
|
33
|
-
simple_content.xs :restriction,
|
39
|
+
simple_content.xs :restriction, 'base' => map_type(@column) do |restriction|
|
34
40
|
self.class.restriction_classes.each do |restriction_class|
|
35
41
|
restriction_class.new(@klass, @column).generate(restriction)
|
36
42
|
end
|
@@ -45,7 +51,7 @@ module Schematic
|
|
45
51
|
return 1 if @required_methods.include?(@column.name.to_sym)
|
46
52
|
return 0 unless @klass.respond_to?(:_validators)
|
47
53
|
@klass._validators[@column.name.to_sym].each do |column_validation|
|
48
|
-
next unless column_validation.is_a?
|
54
|
+
next unless column_validation.is_a? ActiveModel::Validations::PresenceValidator
|
49
55
|
if column_validation.options[:allow_blank] != true &&
|
50
56
|
column_validation.options[:if].nil? &&
|
51
57
|
column_validation.options[:unless].nil?
|
@@ -57,7 +63,7 @@ module Schematic
|
|
57
63
|
end
|
58
64
|
|
59
65
|
def map_type(column)
|
60
|
-
Types::COMPLEX
|
66
|
+
Types::COMPLEX.fetch(column.type)[:complex_type]
|
61
67
|
end
|
62
68
|
|
63
69
|
def skip_generation?
|
@@ -1,13 +1,13 @@
|
|
1
|
+
require 'active_support/descendants_tracker'
|
2
|
+
require 'schematic/generator/column'
|
3
|
+
require 'schematic/generator/column_validator'
|
4
|
+
|
1
5
|
module Schematic
|
2
6
|
module Generator
|
3
7
|
module Restrictions
|
4
8
|
class Base < Schematic::Generator::ColumnValidator
|
5
|
-
|
6
|
-
Schematic::Generator::Column.restriction_classes << klass unless Schematic::Generator::Column.restriction_classes.include?(klass)
|
7
|
-
end
|
9
|
+
extend ActiveSupport::DescendantsTracker
|
8
10
|
end
|
9
11
|
end
|
10
12
|
end
|
11
13
|
end
|
12
|
-
|
13
|
-
|
@@ -1,3 +1,5 @@
|
|
1
|
+
require 'schematic/generator/restrictions/base'
|
2
|
+
|
1
3
|
module Schematic
|
2
4
|
module Generator
|
3
5
|
module Restrictions
|
@@ -6,7 +8,7 @@ module Schematic
|
|
6
8
|
validators_for_column.each do |validator|
|
7
9
|
if validator.respond_to?(:xsd_pattern_restrictions)
|
8
10
|
validator.xsd_pattern_restrictions.each do |restriction|
|
9
|
-
builder.xs(:pattern,
|
11
|
+
builder.xs(:pattern, 'value' => restriction.is_a?(Regexp) ? restriction.source : restriction)
|
10
12
|
end
|
11
13
|
return
|
12
14
|
end
|
@@ -16,4 +18,3 @@ module Schematic
|
|
16
18
|
end
|
17
19
|
end
|
18
20
|
end
|
19
|
-
|
@@ -1,3 +1,6 @@
|
|
1
|
+
require 'active_model/validations/inclusion'
|
2
|
+
require 'schematic/generator/restrictions/base'
|
3
|
+
|
1
4
|
module Schematic
|
2
5
|
module Generator
|
3
6
|
module Restrictions
|
@@ -11,13 +14,13 @@ module Schematic
|
|
11
14
|
valid_values = validator.options[:in]
|
12
15
|
end
|
13
16
|
valid_values.each do |value|
|
14
|
-
builder.xs(:enumeration,
|
17
|
+
builder.xs(:enumeration, 'value' => value)
|
15
18
|
end
|
16
19
|
end
|
17
20
|
enumeration_method = "xsd_#{column.name}_enumeration_restrictions".to_sym
|
18
21
|
if klass.respond_to? enumeration_method
|
19
22
|
klass.send(enumeration_method).each do |enumeration|
|
20
|
-
builder.xs(:enumeration,
|
23
|
+
builder.xs(:enumeration, 'value' => enumeration)
|
21
24
|
end
|
22
25
|
end
|
23
26
|
end
|
@@ -1,11 +1,13 @@
|
|
1
|
+
require 'schematic/generator/restrictions/base'
|
2
|
+
|
1
3
|
module Schematic
|
2
4
|
module Generator
|
3
5
|
module Restrictions
|
4
6
|
class Length < Base
|
5
7
|
def generate(builder)
|
6
8
|
for_validator ActiveModel::Validations::LengthValidator do |validator|
|
7
|
-
builder.xs(:maxLength,
|
8
|
-
builder.xs(:minLength,
|
9
|
+
builder.xs(:maxLength, 'value' => validator.options[:maximum]) if validator.options[:maximum]
|
10
|
+
builder.xs(:minLength, 'value' => validator.options[:minimum]) if validator.options[:minimum]
|
9
11
|
end
|
10
12
|
end
|
11
13
|
end
|
@@ -1,10 +1,12 @@
|
|
1
|
+
require 'schematic/generator/restrictions/base'
|
2
|
+
|
1
3
|
module Schematic
|
2
4
|
module Generator
|
3
5
|
module Restrictions
|
4
6
|
class Numericality < Base
|
5
7
|
def generate(builder)
|
6
8
|
for_validator ActiveModel::Validations::NumericalityValidator do |validator|
|
7
|
-
builder.xs(:pattern,
|
9
|
+
builder.xs(:pattern, 'value' => '\d+')
|
8
10
|
end
|
9
11
|
end
|
10
12
|
end
|
@@ -1,3 +1,6 @@
|
|
1
|
+
require 'active_model/validations/format'
|
2
|
+
require 'schematic/generator/restrictions/base'
|
3
|
+
|
1
4
|
module Schematic
|
2
5
|
module Generator
|
3
6
|
module Restrictions
|
@@ -10,7 +13,7 @@ module Schematic
|
|
10
13
|
value.gsub!(/(?:\$|\\Z|\\z)?$/, '')
|
11
14
|
value.gsub!(/\\\$/, '$')
|
12
15
|
value.gsub!(/\(\?:/, '(')
|
13
|
-
builder.xs(:pattern,
|
16
|
+
builder.xs(:pattern, 'value' => value)
|
14
17
|
end
|
15
18
|
end
|
16
19
|
end
|
@@ -18,5 +21,3 @@ module Schematic
|
|
18
21
|
end
|
19
22
|
end
|
20
23
|
end
|
21
|
-
|
22
|
-
|