azahara_schema 0.1.0

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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 61ff56bbd9eaed8a0b8d15ec62d66ab8db5b9787
4
+ data.tar.gz: 7e6e1b03f11c923226b13a35aa03627a0babe333
5
+ SHA512:
6
+ metadata.gz: cde121ff79ff55d690a52577d50bd602ab8e75008106c831dd3f850883dfa90fd650ff247532a34b8bb2f6a3cad46c333a96bb0a3eb564f645cd419c041e7e6c
7
+ data.tar.gz: c3497a02dfe5b6aa4236341dc0021e84d926d59fc75dd3342298e61736be3ef3b4d23938dddbd9238ecbdc08bc9a7d9977415d84b25abf1bee3428d704108d07
data/MIT-LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright 2017 Ondřej Ezr
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.md ADDED
@@ -0,0 +1,28 @@
1
+ # AzaharaSchema
2
+
3
+
4
+ ## Usage
5
+ How to use my plugin.
6
+
7
+ ## Installation
8
+ Add this line to your application's Gemfile:
9
+
10
+ ```ruby
11
+ gem 'azahara_schema'
12
+ ```
13
+
14
+ And then execute:
15
+ ```bash
16
+ $ bundle
17
+ ```
18
+
19
+ Or install it yourself as:
20
+ ```bash
21
+ $ gem install azahara_schema
22
+ ```
23
+
24
+ ## Contributing
25
+ Contribution directions go here.
26
+
27
+ ## License
28
+ The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,26 @@
1
+ begin
2
+ require 'bundler/setup'
3
+ rescue LoadError
4
+ puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
5
+ end
6
+
7
+ require 'rdoc/task'
8
+
9
+ RDoc::Task.new(:rdoc) do |rdoc|
10
+ rdoc.rdoc_dir = 'rdoc'
11
+ rdoc.title = 'AzaharaSchema'
12
+ rdoc.options << '--line-numbers'
13
+ rdoc.rdoc_files.include('README.md')
14
+ rdoc.rdoc_files.include('lib/**/*.rb')
15
+ end
16
+
17
+ APP_RAKEFILE = File.expand_path("../spec/dummy/Rakefile", __FILE__)
18
+ load 'rails/tasks/engine.rake'
19
+
20
+
21
+ load 'rails/tasks/statistics.rake'
22
+
23
+
24
+
25
+ require 'bundler/gem_tasks'
26
+
@@ -0,0 +1,2 @@
1
+ //= link_directory ../javascripts/azahara_schema .js
2
+ //= link_directory ../stylesheets/azahara_schema .css
@@ -0,0 +1,13 @@
1
+ // This is a manifest file that'll be compiled into application.js, which will include all the files
2
+ // listed below.
3
+ //
4
+ // Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
5
+ // or any plugin's vendor/assets/javascripts directory can be referenced here using a relative path.
6
+ //
7
+ // It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
8
+ // compiled file. JavaScript code in this file should be added after the last require_* statement.
9
+ //
10
+ // Read Sprockets README (https://github.com/rails/sprockets#sprockets-directives) for details
11
+ // about supported directives.
12
+ //
13
+ //= require_tree .
@@ -0,0 +1,30 @@
1
+ $ = jQuery
2
+
3
+ class Filter
4
+ constructor: (@name, @operatorEl, @valueEl)->
5
+ that = this
6
+ @hiddenEl = $('<input>', {name: @valueEl.attr('name'), type: 'hidden'}).insertAfter(@valueEl)
7
+ chngFnc = (evt)->
8
+ that.hiddenEl.val(that.shortValue())
9
+
10
+ @operatorEl.change(chngFnc)
11
+ @valueEl.change(chngFnc)
12
+ chngFnc()
13
+
14
+ shortValue: ()->
15
+ if @valueEl.val() != ''
16
+ @operatorEl.val() + '|' + @valueEl.val()
17
+ else
18
+ ''
19
+
20
+
21
+ $.widget 'azahara_schema.filters',
22
+ options:
23
+ nil: null
24
+ _create: ()->
25
+ that = this
26
+ @filters = []
27
+ @element.find('.row').each ()->
28
+ that.filters.push new Filter($(this).data('name'), $(this).find('.operator-field'), $(this).find('.value-field'))
29
+
30
+ @form = @element.closest('form')
@@ -0,0 +1,13 @@
1
+ /*
2
+ * This is a manifest file that'll be compiled into application.css, which will include all the files
3
+ * listed below.
4
+ *
5
+ * Any CSS and SCSS file within this directory, lib/assets/stylesheets, vendor/assets/stylesheets,
6
+ * or any plugin's vendor/assets/stylesheets directory can be referenced here using a relative path.
7
+ *
8
+ * You're free to add application-wide styles to this file and they'll appear at the bottom of the
9
+ * compiled file so the styles you add here take precedence over styles defined in any other CSS/SCSS
10
+ * files in this directory. Styles in this file should be added after the last require_* statement.
11
+ * It is generally better to create a new file per style scope.
12
+ *
13
+ */
@@ -0,0 +1,34 @@
1
+ // .form-control {
2
+ // border-top: none;
3
+ // border-left: none;
4
+ // border-right: none;
5
+ // border-radius: 0;
6
+ // }
7
+
8
+ .schema-options {
9
+ .form-actions {
10
+ text-align: center;
11
+ margin: 15px 0;
12
+ }
13
+ }
14
+
15
+ .schema-filters {
16
+ @include media-breakpoint-up(md) {
17
+ .filter {
18
+ height: $input-height;
19
+ margin-bottom: 1.5rem;
20
+ .control-label {
21
+ // text-align: right;
22
+ padding-top: $input-padding-y;
23
+ }
24
+ }
25
+ }
26
+ .collapse-actions {
27
+ .chevron:after {
28
+ content: "\f077";
29
+ }
30
+ .collapsed .chevron:after {
31
+ content: "\f078";
32
+ }
33
+ }
34
+ }
@@ -0,0 +1,5 @@
1
+ module AzaharaSchema
2
+ class ApplicationController < ActionController::Base
3
+ protect_from_forgery with: :exception
4
+ end
5
+ end
@@ -0,0 +1,26 @@
1
+ module AzaharaSchema
2
+ module ApplicationHelper
3
+
4
+ def operators_for_select(schema, filter_name)
5
+ schema.operators_for(filter_name).collect{|o| [o, o]}
6
+ end
7
+
8
+ def filter_field(schema, filter)
9
+ case filter.format.format_name
10
+ when 'list'
11
+ select :f, filter.filter_name, options_for_select( list_values_for_select(filter), schema.value_for(filter.filter_name) ), {include_blank: true}, class: 'form-control value-field'
12
+ else
13
+ text_field :f, filter.filter_name, value: schema.value_for(filter.filter_name), class: 'form-control value-field'
14
+ end
15
+ end
16
+
17
+ # translates values to list_values
18
+ # TODO: not needed to do it for every value - for example districts are not translatable
19
+ def list_values_for_select(attribute)
20
+ attribute.available_values.collect do |l, val|
21
+ [t(l, scope: [:activerecord, :attributes, attribute.model.model_name.i18n_key, attribute.name.to_s.pluralize], default: l.to_s), val]
22
+ end
23
+ end
24
+
25
+ end
26
+ end
@@ -0,0 +1,4 @@
1
+ module AzaharaSchema
2
+ class ApplicationJob < ActiveJob::Base
3
+ end
4
+ end
@@ -0,0 +1,6 @@
1
+ module AzaharaSchema
2
+ class ApplicationMailer < ActionMailer::Base
3
+ default from: 'from@example.com'
4
+ layout 'mailer'
5
+ end
6
+ end
@@ -0,0 +1,5 @@
1
+ module AzaharaSchema
2
+ class ApplicationRecord < ActiveRecord::Base
3
+ self.abstract_class = true
4
+ end
5
+ end
@@ -0,0 +1,46 @@
1
+ <div id="filters" class="schema-filters">
2
+ <div id="filters_uncollapsable">
3
+ <% schema.uncollapsable_filters.each do |name, filter| %>
4
+ <div class="form-group row filter" data-name="<%= name %>">
5
+ <div class="col-md-2 control-label"><%= label_tag "f[#{name}]", t('activerecord.attributes.'+schema.model.name.underscore+'.'+name, default: name.humanize) %></div>
6
+ <% if schema.operators_for(name).count > 1 %>
7
+ <div class="col-md-2"><%= select_tag "f[#{name}]", options_for_select(operators_for_select(schema, name), schema.operator_for(name)), class: 'form-control operator-field' %></div>
8
+ <div class="col-md-8">
9
+ <%= filter_field(schema, filter) %>
10
+ </div>
11
+ <% else %>
12
+ <div class="col-md-10">
13
+ <%= hidden_field_tag "f[#{name}]", schema.operators_for(name).first, class: 'operator-field' %>
14
+ <%= filter_field(schema, filter) %>
15
+ </div>
16
+ <% end %>
17
+ </div>
18
+ <% end %>
19
+ </div>
20
+ <% if schema.collapsable_filters.any? || lookup_context.template_exists?("#{schema.model.model_name.plural}/_additional_filters") %>
21
+ <div id="filters_collapsable" class="collapse">
22
+ <% schema.collapsable_filters.each do |name, filter| %>
23
+ <div class="form-group row filter" data-name="<%= name %>">
24
+ <div class="col-md-2 control-label"><%= label_tag "f[#{name}]", t('activerecord.attributes.'+schema.model.name.underscore+'.'+name, default: name.humanize) %></div>
25
+ <% if schema.operators_for(name).count > 1 %>
26
+ <div class="col-md-2"><%= select_tag "f[#{name}]", options_for_select(operators_for_select(schema, name), schema.operator_for(name)), class: 'form-control operator-field' %></div>
27
+ <div class="col-md-8">
28
+ <%= filter_field(schema, filter) %>
29
+ </div>
30
+ <% else %>
31
+ <div class="col-md-10">
32
+ <%= hidden_field_tag "f[#{name}]", schema.operators_for(name).first, class: 'operator-field' %>
33
+ <%= filter_field(schema, filter) %>
34
+ </div>
35
+ <% end %>
36
+ </div>
37
+ <% end %>
38
+ <% if lookup_context.template_exists?("#{schema.model.model_name.plural}/_additional_filters") %>
39
+ <%= render "#{schema.model.model_name.plural}/additional_filters", schema: schema %>
40
+ <% end %>
41
+ </div>
42
+ <div class="collapse-actions" style="text-align: center;">
43
+ <a class="btn btn-sm collapsed" data-toggle="collapse" href="#filters_collapsable"><i class="fa chevron"></i></a>
44
+ </div>
45
+ <% end %>
46
+ </div>
@@ -0,0 +1,10 @@
1
+ <%= form_tag(polymorphic_path(schema.model), method: 'get', class: 'schema-options', style: "margin-bottom: 10px") do |f| %>
2
+ <%= render 'azahara_schema/filters', schema: schema %>
3
+ <div class="form-actions">
4
+ <%= submit_tag t(:label_use_setting), class: 'btn btn-primary' %>
5
+ </div>
6
+ <% end %>
7
+
8
+ <script type="text/javascript">
9
+ $('#filters').filters()
10
+ </script>
@@ -0,0 +1,14 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <title>Action schema</title>
5
+ <%= stylesheet_link_tag "azahara_schema/application", media: "all" %>
6
+ <%= javascript_include_tag "azahara_schema/application" %>
7
+ <%= csrf_meta_tags %>
8
+ </head>
9
+ <body>
10
+
11
+ <%= yield %>
12
+
13
+ </body>
14
+ </html>
@@ -0,0 +1,5 @@
1
+ ---
2
+ cs:
3
+ label_filters: Filtry
4
+ label_advance_filters: Rozšířené
5
+ label_use_setting: Zobrazit
data/config/routes.rb ADDED
@@ -0,0 +1,2 @@
1
+ AzaharaSchema::Engine.routes.draw do
2
+ end
@@ -0,0 +1,5 @@
1
+ require "azahara_schema/engine"
2
+
3
+ module AzaharaSchema
4
+ # Your code goes here...
5
+ end
@@ -0,0 +1,62 @@
1
+ # Author:: Ondřej Ezr (mailto:oezr@msp.justice.cz)
2
+ # Copyright:: Copyright (c) 2017 Ministry of Justice
3
+ # License:: Distributes under license Open Source Licence pro Veřejnou Správu a Neziskový Sektor v.1
4
+
5
+ module AzaharaSchema
6
+
7
+ # The class is attribute for associated record, it is used for working with related records.
8
+ # ---
9
+ # TODO: better way of joining the association - mandatory as +joins+ others as left outer, but not includes.
10
+ # ---
11
+ #
12
+ # The class holds schema for related entity.
13
+ class AssociationAttribute < Attribute
14
+
15
+ attr_reader :attribute, :schema
16
+
17
+ delegate :association, to: :schema
18
+
19
+ def initialize(association_schema, attribute)
20
+ @schema = association_schema
21
+ @attribute = attribute
22
+ super(association.klass, association.name.to_s+'-'+attribute.name, attribute.type)
23
+ end
24
+
25
+ def available_values
26
+ attribute.available_values
27
+ end
28
+
29
+ def arel_field
30
+ attribute.arel_field
31
+ end
32
+
33
+ def path
34
+ association.name.to_s+'.'+attribute.path
35
+ end
36
+
37
+ def column?
38
+ association.macro == :belongs_to
39
+ end
40
+
41
+ def value(parent)
42
+ parent.public_send(association.name).to_s
43
+ end
44
+
45
+ def add_join(scope)
46
+ if attribute.is_a?(AzaharaSchema::AssociationAttribute)
47
+ scope.includes(association.name => attribute.association.name).references(association.name => attribute.association.name)
48
+ else
49
+ scope.includes(association.name).references(association.name)
50
+ end
51
+ end
52
+
53
+ def add_statement(scope, operator, values)
54
+ super(add_join(scope), operator, values)
55
+ end
56
+
57
+ def add_sort(scope, order)
58
+ super(add_join(scope), order)
59
+ end
60
+
61
+ end
62
+ end
@@ -0,0 +1,73 @@
1
+ module AzaharaSchema
2
+ class Attribute
3
+ attr_accessor :name, :format, :model
4
+
5
+ def initialize(model, name, type)
6
+ @name, @model = name, model
7
+ @format = AzaharaSchema::FieldFormat.find(type)
8
+ end
9
+
10
+ def available_operators
11
+ format.available_operators
12
+ end
13
+
14
+ def available_values
15
+ case type
16
+ when 'list'
17
+ @model.try(name.to_s.pluralize)
18
+ else
19
+ nil
20
+ end
21
+ end
22
+
23
+ def type
24
+ format.format_name
25
+ end
26
+
27
+ def arel_field
28
+ model.arel_table[filter_name]
29
+ end
30
+
31
+ def arel_sort_field
32
+ arel_field
33
+ end
34
+
35
+ def filter_name
36
+ name
37
+ end
38
+
39
+ def path
40
+ name
41
+ end
42
+
43
+ def column?
44
+ true
45
+ end
46
+
47
+ def filter?
48
+ true
49
+ end
50
+
51
+ def value(record)
52
+ record.public_send(name)
53
+ end
54
+
55
+ def add_statement(scope, operator, values)
56
+ case operator
57
+ when '='
58
+ scope.where( arel_field.eq(values) )
59
+ when '~'
60
+ scope.where( arel_field.matches("%#{values}%") )
61
+ when '>='
62
+ scope.where( arel_field.gteq(values) )
63
+ when '<='
64
+ scope.where( arel_field.lteq(values) )
65
+ end
66
+ end
67
+
68
+ def add_sort(scope, order)
69
+ scope.order( arel_sort_field.public_send(order) )
70
+ end
71
+
72
+ end
73
+ end
@@ -0,0 +1,22 @@
1
+ require 'azahara_schema/field_format'
2
+ require 'azahara_schema/attribute'
3
+ require 'azahara_schema/association_attribute'
4
+ require 'azahara_schema/outputs'
5
+ require 'azahara_schema/output'
6
+ require 'azahara_schema/schema'
7
+ require 'azahara_schema/model_schema'
8
+
9
+ module AzaharaSchema
10
+ class Engine < ::Rails::Engine
11
+ isolate_namespace AzaharaSchema
12
+
13
+ config.generators do |g|
14
+ g.test_framework :rspec
15
+ g.fixture_replacement :factory_girl, :dir => 'spec/factories'
16
+ end
17
+
18
+ config.to_prepare do
19
+ ::ApplicationController.helper(AzaharaSchema::ApplicationHelper)
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,91 @@
1
+ module AzaharaSchema
2
+ module FieldFormat
3
+ def self.add(name, klass)
4
+ all[name.to_s] = klass.instance
5
+ end
6
+
7
+ def self.delete(name)
8
+ all.delete(name.to_s)
9
+ end
10
+
11
+ def self.all
12
+ @formats ||= Hash.new(Base.instance)
13
+ end
14
+
15
+ def self.available_formats
16
+ all.keys
17
+ end
18
+
19
+ def self.find(name)
20
+ all[name.to_s]
21
+ end
22
+
23
+ # Return an array of custom field formats which can be used in select_tag
24
+ def self.as_select(class_name=nil)
25
+ formats = all.values.select do |format|
26
+ format.class.customized_class_names.nil? || format.class.customized_class_names.include?(class_name)
27
+ end
28
+ formats.map {|format| [::I18n.t(format.label), format.name] }.sort_by(&:first)
29
+ end
30
+
31
+ class Base
32
+ include Singleton
33
+
34
+ class_attribute :format_name
35
+ self.format_name = nil
36
+
37
+ def self.add(name)
38
+ self.format_name = name
39
+ AzaharaSchema::FieldFormat.add(name, self)
40
+ end
41
+ private_class_method :add
42
+
43
+ def available_operators
44
+ ['=']
45
+ end
46
+ end
47
+
48
+ class NumberFormat < Base
49
+ def available_operators
50
+ super.concat(['>=','<=', '><'])
51
+ end
52
+ end
53
+
54
+ class IntegerFormat < NumberFormat
55
+ add 'integer'
56
+ end
57
+
58
+ class FloatFormat < NumberFormat
59
+ add 'float'
60
+ end
61
+
62
+ class BooleanFormat < Base
63
+ add 'boolean'
64
+ end
65
+
66
+ class StringFormat < Base
67
+ add 'string'
68
+
69
+ def available_operators
70
+ super.concat(['~'])
71
+ end
72
+ end
73
+
74
+ class ListFormat < StringFormat
75
+ add 'list'
76
+
77
+ def available_operators
78
+ ['=']
79
+ end
80
+ end
81
+
82
+ class DateFormat < Base
83
+ add 'date'
84
+ end
85
+
86
+ class DateTimeFormat < Base
87
+ add 'datetime'
88
+ end
89
+
90
+ end
91
+ end
@@ -0,0 +1,25 @@
1
+ module AzaharaSchema
2
+ class ModelSchema < Schema
3
+ def initialize(**attrs)
4
+ super(model, attrs)
5
+ end
6
+
7
+ def always_visible_filters
8
+ []
9
+ end
10
+
11
+ def model
12
+ @model ||= self.class.name.sub(/Schema/, '').constantize
13
+ end
14
+
15
+ # dummy implementations for rewrite
16
+ def uncollapsable_filters
17
+ available_filters.select{|name, filter| always_visible_filters.include?(name) }
18
+ end
19
+
20
+ def collapsable_filters
21
+ available_filters.select{|name, filter| !always_visible_filters.include?(name) }
22
+ end
23
+
24
+ end
25
+ end
@@ -0,0 +1,27 @@
1
+ module AzaharaSchema
2
+ class Output
3
+
4
+ attr_reader :schema
5
+
6
+ def self.key
7
+ self.name.split('::').last.underscore
8
+ end
9
+
10
+ def initialize(schema)
11
+ @schema = schema
12
+ end
13
+
14
+ def model
15
+ @schema.model
16
+ end
17
+
18
+ def model_name
19
+ model.model_name
20
+ end
21
+
22
+ def model_i18n_key
23
+ model_name.i18n_key
24
+ end
25
+
26
+ end
27
+ end
@@ -0,0 +1,30 @@
1
+ module AzaharaSchema
2
+ class Outputs
3
+
4
+ def self.registered_outputs
5
+ @registered_outputs ||= {}
6
+ end
7
+
8
+ def self.register(klass)
9
+ key = klass.key
10
+ registered_outputs[key] = klass
11
+ define_method(key) do
12
+ output(key)
13
+ end
14
+ true
15
+ end
16
+
17
+ def self.output_class(output)
18
+ registered_outputs[output]
19
+ end
20
+
21
+ def initialize(schema)
22
+ @schema = schema
23
+ end
24
+
25
+ def output(output)
26
+ self.class.output_class(output).new(@schema)
27
+ end
28
+
29
+ end
30
+ end
@@ -0,0 +1,194 @@
1
+ module AzaharaSchema
2
+ class Schema
3
+
4
+ def self.schema_for(klass, *attributes)
5
+ schema_klass = "#{klass.name}Schema".safe_constantize
6
+ if schema_klass
7
+ schema_klass.new(*attributes)
8
+ else
9
+ AzaharaSchema::Schema.new(klass, *attributes)
10
+ end
11
+ end
12
+
13
+ def self.enabled_filters(*filter_names)
14
+ @enabled_filters = filter_names if filter_names.any?
15
+ @enabled_filters ||= []
16
+ end
17
+
18
+ def self.operators_for_filters
19
+ @operators_for_filters ||= {}
20
+ end
21
+
22
+ def self.filter_operators(filter, operators)
23
+ operators_for_filters[filter] = operators
24
+ end
25
+
26
+ attr_accessor :model, :association
27
+
28
+ def initialize(model, **attributes)
29
+ @model = model
30
+ @association = attributes[:association]
31
+ @column_names = attributes[:columns]
32
+ end
33
+
34
+ def column_names
35
+ @column_names ||= default_columns
36
+ end
37
+
38
+ def columns
39
+ @columns ||= available_attributes.select{|attribute| attribute.column? && column_names.include?(attribute.name) }
40
+ end
41
+
42
+ def filters
43
+ @filters ||= {}
44
+ end
45
+
46
+ def sort
47
+ @sort ||= {}
48
+ end
49
+
50
+ # DEFAULTS
51
+
52
+ def default_columns
53
+ [main_attribute_name]
54
+ end
55
+
56
+ # just a dummy implementation
57
+ def main_attribute_name
58
+ available_attributes.detect{|att| att.name != 'id' }.name
59
+ end
60
+
61
+ # ACCESSORS
62
+
63
+ def add_short_filter(name, str)
64
+ attrs = str.split('|')
65
+ if attrs.size == 2
66
+ add_filter(name, attrs.first, attrs.second)
67
+ elsif attrs.size == 1
68
+ add_filter(name, '=', attrs.first)
69
+ end
70
+ end
71
+
72
+ def add_filter(name, operator, values)
73
+ raise 'filter ('+name+') is not defined!' unless available_filters.key?(name)
74
+ filters[name] = { o: operator, v: values }
75
+ end
76
+
77
+ def add_sort(name, order=:asc)
78
+ sort[name] = order
79
+ end
80
+
81
+ def operator_for(fname)
82
+ filters[fname] && filters[fname][:o]
83
+ end
84
+
85
+ def value_for(fname)
86
+ filters[fname] && filters[fname][:v]
87
+ end
88
+
89
+ def operators_for(filter_name)
90
+ operators = available_filters[filter_name] && available_filters[filter_name].available_operators
91
+ operators &= self.class.operators_for_filters[filter_name] if operators && self.class.operators_for_filters[filter_name]
92
+ operators
93
+ end
94
+
95
+ def attribute(name)
96
+ available_attributes.detect{|att| att.name == name}
97
+ end
98
+
99
+ def available_attributes
100
+ unless @available_attributes
101
+ initialize_available_attributes
102
+ end
103
+ @available_attributes
104
+ end
105
+
106
+ def available_columns
107
+ @available_columns ||= available_attributes.select{|att| att.column? }
108
+ end
109
+
110
+ def enabled_filters
111
+ if self.class.enabled_filters.any?
112
+ self.class.enabled_filters.collect{|f_name| available_attributes.detect{|attr| attr.name == f_name } }.compact
113
+ else
114
+ available_attributes
115
+ end
116
+ end
117
+
118
+ def available_filters
119
+ @available_filters ||= enabled_filters.select{|att| att.filter? }.collect{|att| [att.filter_name, att] }.to_h
120
+ end
121
+
122
+ def available_associations
123
+ return [] if @association #only first level of association - would need to solve circular dependency first to add next level
124
+ @available_associations ||= model.reflect_on_all_associations.collect do |association|
125
+ AzaharaSchema::Schema.schema_for(association.klass, association: association)
126
+ end
127
+ end
128
+
129
+ def attribute_for_column(col)
130
+ Attribute.new(model, col.name, col.type)
131
+ end
132
+
133
+ def initialize_available_attributes
134
+ @available_attributes ||= []
135
+ model.columns.each do |col|
136
+ @available_attributes << attribute_for_column(col)
137
+ end
138
+ available_associations.each do |asoc_schema|
139
+ asoc_schema.available_attributes.each do |asoc_attribute|
140
+ @available_attributes << AssociationAttribute.new(asoc_schema, asoc_attribute)
141
+ end
142
+ end
143
+ end
144
+
145
+ def outputs
146
+ Outputs.new(self)
147
+ end
148
+
149
+ def entities
150
+ scope = model.respond_to?(:visible) ? model.visible : model.all
151
+ filters.each do |name, attrs|
152
+ scope = available_filters[name].add_statement(scope, attrs[:o], attrs[:v])
153
+ end
154
+ sort.each do |name, order|
155
+ att = attribute(name)
156
+ scope = att.add_sort(scope, order) if att
157
+ end
158
+ scope
159
+ end
160
+
161
+
162
+ #serialization
163
+ def from_params(params)
164
+ if params[:f]
165
+ filter_params = params[:f].permit(available_filters.keys).to_h
166
+ filter_params.each{|name, short_filter| add_short_filter(name, short_filter) }
167
+ end
168
+ if params[:sort]
169
+ @sort = nil
170
+ params[:sort].each do |k, sort|
171
+ add_sort(sort[:path], sort['desc'] == 'true' ? :desc : :asc )
172
+ end
173
+ end
174
+ end
175
+
176
+ def to_param
177
+ params = {}
178
+ params[:f] = {}
179
+ filters.each do |fname, attrs|
180
+ params[:f][fname] = "#{attrs[:o]}|#{attrs[:v]}"
181
+ end
182
+ params
183
+ end
184
+
185
+ def uncollapsable_filters
186
+ {}
187
+ end
188
+
189
+ def collapsable_filters
190
+ available_filters
191
+ end
192
+
193
+ end
194
+ end
@@ -0,0 +1,3 @@
1
+ module AzaharaSchema
2
+ VERSION = '0.1.0'
3
+ end
@@ -0,0 +1,4 @@
1
+ # desc "Explaining what the task does"
2
+ # task :azahara_schema do
3
+ # # Task goes here
4
+ # end
metadata ADDED
@@ -0,0 +1,102 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: azahara_schema
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Ondřej Ezr
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2017-09-06 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rails
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: '5.0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: '5.0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: sqlite3
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ description: This gem should provide complete tools for quick developement of easy
42
+ registry app in RoR.
43
+ email:
44
+ - oezr@msp.justice.cz
45
+ executables: []
46
+ extensions: []
47
+ extra_rdoc_files: []
48
+ files:
49
+ - MIT-LICENSE
50
+ - README.md
51
+ - Rakefile
52
+ - app/assets/config/azahara_schema_manifest.js
53
+ - app/assets/javascripts/azahara_schema/application.js
54
+ - app/assets/javascripts/azahara_schema/azahara_schema.coffee
55
+ - app/assets/stylesheets/azahara_schema/application.scss
56
+ - app/assets/stylesheets/azahara_schema/schema_options.scss
57
+ - app/controllers/azahara_schema/application_controller.rb
58
+ - app/helpers/azahara_schema/application_helper.rb
59
+ - app/jobs/azahara_schema/application_job.rb
60
+ - app/mailers/action_schema/application_mailer.rb
61
+ - app/models/action_schema/application_record.rb
62
+ - app/views/azahara_schema/_filters.html.erb
63
+ - app/views/azahara_schema/_index_form.html.erb
64
+ - app/views/layouts/action_schema/application.html.erb
65
+ - config/locales/cs.yml
66
+ - config/routes.rb
67
+ - lib/azahara_schema.rb
68
+ - lib/azahara_schema/association_attribute.rb
69
+ - lib/azahara_schema/attribute.rb
70
+ - lib/azahara_schema/engine.rb
71
+ - lib/azahara_schema/field_format.rb
72
+ - lib/azahara_schema/model_schema.rb
73
+ - lib/azahara_schema/output.rb
74
+ - lib/azahara_schema/outputs.rb
75
+ - lib/azahara_schema/schema.rb
76
+ - lib/azahara_schema/version.rb
77
+ - lib/tasks/azahara_schema_tasks.rake
78
+ homepage: http://git.justice.cz/libraries/azahara_schema
79
+ licenses:
80
+ - MIT
81
+ metadata: {}
82
+ post_install_message:
83
+ rdoc_options: []
84
+ require_paths:
85
+ - lib
86
+ required_ruby_version: !ruby/object:Gem::Requirement
87
+ requirements:
88
+ - - ">="
89
+ - !ruby/object:Gem::Version
90
+ version: '0'
91
+ required_rubygems_version: !ruby/object:Gem::Requirement
92
+ requirements:
93
+ - - ">="
94
+ - !ruby/object:Gem::Version
95
+ version: '0'
96
+ requirements: []
97
+ rubyforge_project:
98
+ rubygems_version: 2.5.2
99
+ signing_key:
100
+ specification_version: 4
101
+ summary: Gem to support developement of rails application with schema over an entity
102
+ test_files: []