integral 1.0.1 → 1.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +10 -21
- data/app/assets/javascripts/integral/backend.js +1 -1
- data/app/assets/javascripts/integral/support/character_counter.js +2 -1
- data/app/assets/javascripts/integral/support/confirm_modal.coffee +2 -2
- data/app/assets/javascripts/integral/support/gallery.coffee +26 -1
- data/app/assets/stylesheets/integral/support/gallery.sass +10 -2
- data/app/controllers/integral/backend/images_controller.rb +3 -5
- data/app/controllers/integral/backend/lists_controller.rb +7 -13
- data/app/controllers/integral/pages_controller.rb +5 -1
- data/app/helpers/integral/backend/base_helper.rb +8 -2
- data/app/views/devise/sessions/new.haml +1 -1
- data/app/views/integral/backend/images/_grid.haml +1 -1
- data/app/views/integral/backend/lists/_grid.haml +1 -3
- data/app/views/integral/backend/lists/edit.haml +22 -1
- data/app/views/integral/backend/pages/_form.haml +1 -1
- data/app/views/integral/backend/pages/_grid.haml +1 -1
- data/app/views/integral/backend/posts/_grid.haml +1 -1
- data/app/views/integral/backend/static_pages/dashboard.haml +4 -3
- data/app/views/integral/backend/users/_grid.haml +1 -1
- data/app/views/integral/pages/_demo.haml +2 -2
- data/app/views/integral/posts/_collection.haml +4 -0
- data/app/views/integral/shared/gallery/_placeholder.haml +1 -1
- data/config/locales/en.yml +4 -1
- data/db/seeds.rb +1 -1
- data/lib/generators/integral/assets_generator.rb +54 -0
- data/lib/generators/integral/install_generator.rb +36 -2
- data/lib/generators/integral/views_generator.rb +66 -0
- data/lib/generators/templates/routes.rb +7 -0
- data/lib/generators/templates/seeds.rb +2 -0
- data/lib/integral/content_renderer.rb +1 -1
- data/lib/integral/router.rb +1 -1
- data/lib/integral/version.rb +1 -1
- data/lib/integral/widgets/recent_posts.rb +1 -1
- data/public/images/integral/demo/continous-integration.png +0 -0
- data/public/images/integral/demo/foundation-frontend-framework.jpg +0 -0
- data/public/images/integral/demo/heroku.png +0 -0
- data/public/images/integral/demo/integral-cms-without-hassle.jpg +0 -0
- data/public/images/integral/demo/integral-features-activity-tracking.jpg +0 -0
- data/public/images/integral/demo/integral-features-contact-form.png +0 -0
- data/public/images/integral/demo/integral-features-design.jpg +0 -0
- data/public/images/integral/demo/integral-features-dynamic-pages.jpg +0 -0
- data/public/images/integral/demo/integral-features-image-management.jpg +0 -0
- data/public/images/integral/demo/integral-features-integrated-blog.jpg +0 -0
- data/public/images/integral/demo/integral-features-list-management.jpg +0 -0
- data/public/images/integral/demo/integral-features-seo-ready.jpg +0 -0
- data/public/images/integral/demo/integral-features-user-management.jpg +0 -0
- data/public/images/integral/demo/integral-presentation.png +0 -0
- metadata +23 -20
- data/app/assets/stylesheets/integral/wysiwyg.sass +0 -13
- data/app/views/integral/backend/lists/show.haml +0 -26
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1d79cf3d29d5bd42ed2ff312edfba5df092f44f5
|
4
|
+
data.tar.gz: 4e1436dcafb059b53ecd4edbc2f32b875cc4314d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 1cc6755ead403715d6118da43b5e56fec7cc41ba13ab80a4e6eae175e26299b863a443f92335e610e7062d3c3796b21793d9881754b4a9b8ddaed65292d01505
|
7
|
+
data.tar.gz: 67cb53f56c8e07f95a2b2e41eaa7414179d59342a5901913b1bab0c3138183d81e69c290cc9bfac305dfc3508bfacf135dce9c8024d8a3429623f55485b60802
|
data/README.md
CHANGED
@@ -1,6 +1,7 @@
|
|
1
|
-
[![Gem Version](https://badge.fury.io/rb/integral.svg)][version-website]
|
1
|
+
[![Gem Version](https://badge.fury.io/rb/integral.svg)][version-website]
|
2
2
|
[![Current Build Status](https://img.shields.io/circleci/project/github/yamasolutions/integral/master.svg)][ci-website] [![Inline docs](http://inch-ci.org/github/yamasolutions/integral.svg?branch=master)][docs-website]
|
3
3
|
# Integral CMS
|
4
|
+
![Integral CMS Features](https://media.giphy.com/media/LwzTKp4PxFpvKfxMJe/giphy.gif)
|
4
5
|
|
5
6
|
Integral is a CMS for Rails 5+. The aim of Integral is to lower the barrier of entry in creating websites, using Ruby on Rails, with all the bells and whistles that users have now come to expect.
|
6
7
|
Out of the box integral provides;
|
@@ -20,6 +21,10 @@ Out of the box integral provides;
|
|
20
21
|
* Sitemap generation
|
21
22
|
* [Find out more...][integral-cms]
|
22
23
|
|
24
|
+
## Demo Now - Deploy a Sample App
|
25
|
+
|
26
|
+
[![Deploy](https://www.herokucdn.com/deploy/button.svg)](https://heroku.com/deploy?template=https://github.com/yamasolutions/integral-sample)
|
27
|
+
|
23
28
|
## Getting Started
|
24
29
|
|
25
30
|
1. Create a new Rails application
|
@@ -30,29 +35,11 @@ Out of the box integral provides;
|
|
30
35
|
```
|
31
36
|
gem 'integral'
|
32
37
|
```
|
33
|
-
3.
|
34
|
-
```
|
35
|
-
# config/routes.rb
|
36
|
-
mount Integral::Engine, at: "/", as: 'integral'
|
37
|
-
root to: 'integral/static_pages#home'
|
38
|
-
```
|
39
|
-
4. Make sure you're app runs Integral seed data on setup
|
40
|
-
```
|
41
|
-
# db/seeds.rb
|
42
|
-
Integral::Engine.load_seed
|
43
|
-
```
|
44
|
-
5. Setup database - Copy and run necessary migrations
|
45
|
-
```
|
46
|
-
rake integral:install:migrations
|
47
|
-
rake db:create
|
48
|
-
rake db:migrate
|
49
|
-
rake db:setup
|
50
|
-
```
|
51
|
-
6. Run Integral install rake task (adds configuration initializers)
|
38
|
+
3. Run Integral install rake task (adds configuration initializers, installs routes & sets up database)
|
52
39
|
```
|
53
40
|
rails generate integral:install
|
54
41
|
```
|
55
|
-
|
42
|
+
4. Set the default host within the development environment, used for URL generation
|
56
43
|
```
|
57
44
|
# config/environments/development.rb
|
58
45
|
|
@@ -61,6 +48,8 @@ Rails.application.routes.default_url_options[:host] = 'http://localhost:3000'
|
|
61
48
|
|
62
49
|
Voila! Start your rails server and you're ready to go! You can access the user only area at `/admin`
|
63
50
|
|
51
|
+
Integral requires Rails 5.1 or higher and Ruby 2.4.1 or higher.
|
52
|
+
|
64
53
|
## Information
|
65
54
|
|
66
55
|
* [Integral Website][integral-cms]
|
@@ -185,7 +185,7 @@ function ready() {
|
|
185
185
|
I18n.locale = $('body').data('locale') || 'en';
|
186
186
|
|
187
187
|
// CKEditor Initialization
|
188
|
-
// TODO:
|
188
|
+
// TODO: Fork Ckeditor and remove obtrusive JS causing the below to throw warnings
|
189
189
|
for(name in CKEDITOR.instances) {
|
190
190
|
CKEDITOR.instances[name].destroy(true);
|
191
191
|
}
|
@@ -11,8 +11,9 @@ jQuery.fn.characterCounter = function(){
|
|
11
11
|
}
|
12
12
|
|
13
13
|
var itHasLengthAttribute = $input.attr('maxlength') != undefined;
|
14
|
+
var itIsntDisabled = $input.attr('data-character-counter') != 'false';
|
14
15
|
|
15
|
-
if(itHasLengthAttribute){
|
16
|
+
if ((itHasLengthAttribute) && (itIsntDisabled)) {
|
16
17
|
$input.on('input', updateCounter);
|
17
18
|
$input.on('focus', updateCounter);
|
18
19
|
$input.on('blur', removeCounterElement);
|
@@ -16,8 +16,8 @@ $.rails.buildConfirmationDialog = (message, modalId, confirmBtnId, cancelBtnId)
|
|
16
16
|
</div>
|
17
17
|
|
18
18
|
<div class='modal-footer'>
|
19
|
-
<a id='#{cancelBtnId}' class='button secondary hollow'>#{I18n.t('integral.
|
20
|
-
<a id='#{confirmBtnId}' class='button primary'>#{I18n.t('integral.
|
19
|
+
<a id='#{cancelBtnId}' class='button secondary hollow'>#{I18n.t('integral.actions.cancel')}</a>
|
20
|
+
<a id='#{confirmBtnId}' class='button primary'>#{I18n.t('integral.actions.confirm')}</a>
|
21
21
|
</div>
|
22
22
|
<button class='close-button' data-close aria-label='Close modal' type='button'>
|
23
23
|
<span aria-hidden='true'>×</span>
|
@@ -72,7 +72,32 @@ class this.Gallery
|
|
72
72
|
projectGalleryTop.controller.control = projectGalleryThumbs
|
73
73
|
projectGalleryThumbs.controller.control = projectGalleryTop
|
74
74
|
|
75
|
-
#
|
75
|
+
# Set main swiper size
|
76
|
+
revealHeight = gallery.height()
|
77
|
+
thumbSwiperHeight = galleryContent.find('.thumb-swiper').height()
|
78
|
+
revealAvailableHeight = revealHeight - thumbSwiperHeight
|
79
|
+
mainSwiper.height(revealAvailableHeight)
|
80
|
+
|
81
|
+
window.addEventListener 'resize', =>
|
82
|
+
# TODO: Tidy up this duplication
|
83
|
+
revealHeight = gallery.height()
|
84
|
+
thumbSwiperHeight = galleryContent.find('.thumb-swiper').height()
|
85
|
+
revealAvailableHeight = revealHeight - thumbSwiperHeight
|
86
|
+
mainSwiper.height(revealAvailableHeight)
|
87
|
+
|
88
|
+
# Listen for arrow keys
|
89
|
+
$(document).keydown (event) =>
|
90
|
+
return unless gallery.is(':focus')
|
91
|
+
|
92
|
+
switch event.which
|
93
|
+
when 37 # Left
|
94
|
+
projectGalleryThumbs.slidePrev()
|
95
|
+
when 39 # Right
|
96
|
+
projectGalleryThumbs.slideNext()
|
97
|
+
else
|
98
|
+
return # Exit this handler for other keys
|
99
|
+
|
100
|
+
# Show/hide content and placeholder
|
76
101
|
gallery.find('.placeholder').css('display', 'none')
|
77
102
|
galleryContent.css('visibility', 'initial')
|
78
103
|
|
@@ -11,6 +11,10 @@
|
|
11
11
|
font-size: 2em
|
12
12
|
margin-bottom: 0.5em
|
13
13
|
.main-swiper
|
14
|
+
height: 0
|
15
|
+
margin-bottom: 0
|
16
|
+
.swiper-wrapper
|
17
|
+
height: 100%
|
14
18
|
.swiper-button-prev, .swiper-button-next
|
15
19
|
position: absolute
|
16
20
|
top: 40%
|
@@ -22,12 +26,16 @@
|
|
22
26
|
font-size: 1.5em
|
23
27
|
.swiper-slide
|
24
28
|
margin: auto 0
|
29
|
+
text-align: center
|
30
|
+
img
|
31
|
+
max-height: 100%
|
25
32
|
.thumb-swiper
|
26
33
|
height: 9em
|
27
34
|
padding: 0.5em 0
|
35
|
+
margin-bottom: 0
|
28
36
|
.swiper-slide
|
29
|
-
width:
|
30
|
-
height:
|
37
|
+
width: 10em
|
38
|
+
height: 6em
|
31
39
|
cursor: pointer
|
32
40
|
@include breakpoint(small down)
|
33
41
|
width: 8em
|
@@ -44,12 +44,10 @@ module Integral
|
|
44
44
|
flash.now[:error] = notification_message('creation_failure')
|
45
45
|
head :unprocessable_entity
|
46
46
|
end
|
47
|
+
elsif @image.save
|
48
|
+
respond_successfully(notification_message('creation_success'), edit_backend_img_path(@image))
|
47
49
|
else
|
48
|
-
|
49
|
-
respond_successfully(notification_message('creation_success'), edit_backend_img_path(@image))
|
50
|
-
else
|
51
|
-
respond_failure(notification_message('creation_failure'), @image, :new)
|
52
|
-
end
|
50
|
+
respond_failure(notification_message('creation_failure'), @image, :new)
|
53
51
|
end
|
54
52
|
end
|
55
53
|
|
@@ -2,7 +2,7 @@ module Integral
|
|
2
2
|
module Backend
|
3
3
|
# List controller
|
4
4
|
class ListsController < BaseController
|
5
|
-
before_action :set_list, only: %i[edit update destroy
|
5
|
+
before_action :set_list, only: %i[edit update destroy clone]
|
6
6
|
before_action :authorize_with_klass
|
7
7
|
before_action -> { set_grid(Integral::Grids::ListsGrid) }, only: [:index]
|
8
8
|
|
@@ -17,14 +17,6 @@ module Integral
|
|
17
17
|
end
|
18
18
|
end
|
19
19
|
|
20
|
-
# GET /:id
|
21
|
-
def show
|
22
|
-
@list = List.find(params[:id])
|
23
|
-
@list.list_items.order(:priority)
|
24
|
-
|
25
|
-
add_breadcrumb @list.title, :backend_list_path
|
26
|
-
end
|
27
|
-
|
28
20
|
# GET /new
|
29
21
|
# List creation form
|
30
22
|
def new
|
@@ -38,7 +30,7 @@ module Integral
|
|
38
30
|
@list = List.new(list_params)
|
39
31
|
|
40
32
|
if @list.save
|
41
|
-
respond_successfully(notification_message('creation_success'),
|
33
|
+
respond_successfully(notification_message('creation_success'), edit_backend_list_path(@list))
|
42
34
|
else
|
43
35
|
respond_failure(notification_message('creation_failure'), @list, :new)
|
44
36
|
end
|
@@ -47,7 +39,8 @@ module Integral
|
|
47
39
|
# GET /:id/edit
|
48
40
|
# List edit form
|
49
41
|
def edit
|
50
|
-
|
42
|
+
@list = List.find(params[:id])
|
43
|
+
|
51
44
|
add_breadcrumb I18n.t('integral.breadcrumbs.edit'), :edit_backend_list_path
|
52
45
|
end
|
53
46
|
|
@@ -70,9 +63,9 @@ module Integral
|
|
70
63
|
# Updating an list
|
71
64
|
def update
|
72
65
|
if @list.update(list_params)
|
73
|
-
respond_successfully(notification_message('edit_success'),
|
66
|
+
respond_successfully(notification_message('edit_success'), edit_backend_list_path(@list))
|
74
67
|
else
|
75
|
-
respond_failure(notification_message('edit_failure'), @list, :
|
68
|
+
respond_failure(notification_message('edit_failure'), @list, :edit)
|
76
69
|
end
|
77
70
|
end
|
78
71
|
|
@@ -105,6 +98,7 @@ module Integral
|
|
105
98
|
|
106
99
|
def set_list
|
107
100
|
@list = List.find(params[:id])
|
101
|
+
@list.list_items&.order(:priority)
|
108
102
|
end
|
109
103
|
|
110
104
|
def list_params
|
@@ -39,7 +39,11 @@ module Integral
|
|
39
39
|
end
|
40
40
|
|
41
41
|
def canonical_url
|
42
|
-
|
42
|
+
if Settings[:homepage_id]&.to_i == @page.id
|
43
|
+
"#{Rails.application.routes.default_url_options[:host]}"
|
44
|
+
else
|
45
|
+
"#{Rails.application.routes.default_url_options[:host]}#{@page.path}"
|
46
|
+
end
|
43
47
|
end
|
44
48
|
end
|
45
49
|
end
|
@@ -50,22 +50,28 @@ module Integral
|
|
50
50
|
|
51
51
|
# Donut Graph - At a Glance
|
52
52
|
def dataset_dashboard_atg
|
53
|
-
[
|
53
|
+
data = [
|
54
54
|
{ scope: Integral::Page, label: 'Total Pages' },
|
55
55
|
{ scope: Integral::List, label: 'Total Lists' },
|
56
56
|
{ scope: Integral::Image, label: 'Total Images' },
|
57
57
|
{ scope: Integral::User, label: 'Total Users' }
|
58
58
|
]
|
59
|
+
|
60
|
+
data.prepend(scope: Integral::Post, label: 'Total Posts') if Integral.blog_enabled?
|
61
|
+
data
|
59
62
|
end
|
60
63
|
|
61
64
|
# Line graph - Last week
|
62
65
|
def dataset_dashboard_last_week
|
63
|
-
[
|
66
|
+
data = [
|
64
67
|
{ scope: Integral::Page, label: 'Pages' },
|
65
68
|
{ scope: Integral::List, label: 'Lists' },
|
66
69
|
{ scope: Integral::Image, label: 'Images' },
|
67
70
|
{ scope: Integral::User, label: 'Users' }
|
68
71
|
]
|
72
|
+
|
73
|
+
data.prepend(scope: Integral::Post, label: 'Posts') if Integral.blog_enabled?
|
74
|
+
data
|
69
75
|
end
|
70
76
|
end
|
71
77
|
end
|
@@ -8,7 +8,7 @@
|
|
8
8
|
.input-group
|
9
9
|
%span.input-group-label
|
10
10
|
= icon('key')
|
11
|
-
= f.input :password, input_html: { class: 'input-group-field' }, label: false
|
11
|
+
= f.input :password, input_html: { class: 'input-group-field', 'data-character-counter' => 'false' }, label: false
|
12
12
|
= f.input :remember_me, as: :boolean
|
13
13
|
|
14
14
|
.form-actions
|
@@ -10,7 +10,7 @@
|
|
10
10
|
%td.actions
|
11
11
|
= link_to edit_backend_img_url(record) do
|
12
12
|
= icon('edit')
|
13
|
-
= link_to backend_img_url(record), method: :delete, data: { confirm: t('integral.actions.
|
13
|
+
= link_to backend_img_url(record), method: :delete, data: { confirm: t('integral.actions.confirmation.deletion') } do
|
14
14
|
= icon('remove')
|
15
15
|
- else
|
16
16
|
= render partial: 'integral/backend/shared/empty_grid'
|
@@ -6,11 +6,9 @@
|
|
6
6
|
%td= record.title
|
7
7
|
%td= record.description
|
8
8
|
%td.actions
|
9
|
-
= link_to backend_list_url(record) do
|
10
|
-
= icon('eye')
|
11
9
|
= link_to edit_backend_list_url(record) do
|
12
10
|
= icon('edit')
|
13
|
-
= link_to backend_list_url(record), method: :delete, data: { confirm: t('integral.actions.
|
11
|
+
= link_to backend_list_url(record), method: :delete, data: { confirm: t('integral.actions.confirmation.deletion') } do
|
14
12
|
= icon('remove')
|
15
13
|
- else
|
16
14
|
= render partial: 'integral/backend/shared/empty_grid'
|
@@ -1,2 +1,23 @@
|
|
1
|
-
=
|
1
|
+
= simple_form_for [:backend, @list], validate: true, html: { class: 'are-you-sure', 'data-confirm-dirty-form' => true, 'data-list-item-limit' => @list.list_item_limit, id: :list_form } do |f|
|
2
|
+
= f.input :lock_version, as: :hidden
|
3
|
+
.grid-x.grid-padding-x
|
4
|
+
.cell.medium-6.flex-container
|
5
|
+
.card
|
6
|
+
.card-section
|
7
|
+
= f.input :title, hint: false, disabled: f.object.locked?
|
8
|
+
.cell.medium-6.flex-container
|
9
|
+
.card
|
10
|
+
.card-section
|
11
|
+
= f.input :description, hint: false, disabled: f.object.locked?
|
12
|
+
.cell
|
13
|
+
= render partial: 'integral/backend/lists/manager', locals: { f: f, locked: f.object.locked? }
|
14
|
+
.cell
|
15
|
+
= f.button :button
|
16
|
+
|
17
|
+
-# Image Selector
|
18
|
+
= render partial: 'integral/backend/shared/record_selector/modal', locals: { search_path: backend_img_index_path, title: t('integral.prompts.select_image'), name: 'Image', create_modal: '#new_image_modal', initialize: true }
|
19
|
+
= render partial: 'integral/backend/images/create_modal'
|
20
|
+
|
21
|
+
- Integral::ActsAsListable.objects.each do |listable|
|
22
|
+
= render partial: 'integral/backend/shared/record_selector/modal', locals: { search_path: listable.listable_options[:selector_path], title: listable.listable_options[:selector_title], name: listable.to_s.parameterize, initialize: true }
|
2
23
|
|
@@ -18,7 +18,7 @@
|
|
18
18
|
.cell
|
19
19
|
.card
|
20
20
|
.card-section
|
21
|
-
= f.input :body, as: :ckeditor, input_html: { id: 'page_body_editor', ckeditor: {
|
21
|
+
= f.input :body, as: :ckeditor, input_html: { id: 'page_body_editor', ckeditor: { language: current_user.locale }, data: { 'ckeditor-class' => @page.template } }
|
22
22
|
|
23
23
|
.cell.small-12.medium-4.large-3
|
24
24
|
.grid-y
|
@@ -15,7 +15,7 @@
|
|
15
15
|
= link_to edit_backend_page_url(record) do
|
16
16
|
= icon('edit')
|
17
17
|
- if policy(Integral::Page).destroy?
|
18
|
-
= link_to backend_page_url(record), method: :delete, data: { confirm: t('integral.actions.
|
18
|
+
= link_to backend_page_url(record), method: :delete, data: { confirm: t('integral.actions.confirmation.deletion') } do
|
19
19
|
= icon('remove')
|
20
20
|
- else
|
21
21
|
= render partial: 'integral/backend/shared/empty_grid'
|
@@ -19,7 +19,7 @@
|
|
19
19
|
= icon('eye')
|
20
20
|
= link_to edit_backend_post_url(record) do
|
21
21
|
= icon('edit')
|
22
|
-
= link_to backend_post_url(record), method: :delete, data: { confirm: t('integral.actions.
|
22
|
+
= link_to backend_post_url(record), method: :delete, data: { confirm: t('integral.actions.confirmation.deletion') } do
|
23
23
|
= icon('remove')
|
24
24
|
- else
|
25
25
|
= render partial: 'integral/backend/shared/empty_grid'
|
@@ -3,10 +3,11 @@
|
|
3
3
|
.grid-x.grid-padding-x
|
4
4
|
.cell.small-12
|
5
5
|
= render partial: 'integral/backend/shared/cards/welcome'
|
6
|
+
- if Integral.blog_enabled?
|
7
|
+
.cell.small-12.medium-6.flex-container
|
8
|
+
= render partial: 'integral/backend/static_pages/card', locals: { title: t('.recent_post'), record: Integral::Post.published.last }
|
6
9
|
.cell.small-12.medium-6.flex-container
|
7
|
-
= render partial: 'integral/backend/static_pages/card', locals: { title: t('.
|
8
|
-
.cell.small-12.medium-6.flex-container
|
9
|
-
= render partial: 'integral/backend/static_pages/card', locals: { title: t('.recent_page'), record: Integral::Page.first }
|
10
|
+
= render partial: 'integral/backend/static_pages/card', locals: { title: t('.recent_page'), record: Integral::Page.published.last }
|
10
11
|
.cell.large-6
|
11
12
|
.grid-x.grid-padding-x
|
12
13
|
.cell.small-12
|
@@ -13,7 +13,7 @@
|
|
13
13
|
= icon('eye')
|
14
14
|
= link_to edit_backend_user_url(record) do
|
15
15
|
= icon('edit')
|
16
|
-
= link_to backend_user_url(record), method: :delete, data: { confirm: t('integral.actions.
|
16
|
+
= link_to backend_user_url(record), method: :delete, data: { confirm: t('integral.actions.confirmation.deletion') } do
|
17
17
|
= icon('remove')
|
18
18
|
- else
|
19
19
|
= render partial: 'integral/backend/shared/empty_grid'
|
@@ -4,7 +4,7 @@
|
|
4
4
|
.cell.medium-6.large-5
|
5
5
|
%h1 A Rails CMS which just works.
|
6
6
|
%p Create a website (which does stuff) within minutes powered by Rails 5.
|
7
|
-
= link_to '
|
7
|
+
= link_to 'DEPLOY NOW', 'https://heroku.com/deploy?template=https://github.com/yamasolutions/integral-sample', class: 'button', target: :blank
|
8
8
|
%p
|
9
9
|
%small
|
10
10
|
= icon('check', class: 'text-primary')
|
@@ -184,5 +184,5 @@
|
|
184
184
|
.grid-container.text-center
|
185
185
|
%h2 A Rails CMS which will knock your socks off
|
186
186
|
%p Creating a professional website on Rails has never been easier
|
187
|
-
= link_to 'Get Started', 'https://github.com/yamasolutions/integral', class: 'button white hollow', target: :blank
|
187
|
+
= link_to 'Get Started', 'https://heroku.com/deploy?template=https://github.com/yamasolutions/integral-sample', class: 'button white hollow', target: :blank
|
188
188
|
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#gallery-placeholder.reveal.
|
1
|
+
#gallery-placeholder.reveal.full.modal--gallery{ data: {reveal: true }}
|
2
2
|
%button.close-button{ data: { close: '' }, aria: { label: "Close modal" }}
|
3
3
|
%span{ aria: { hidden: true } } ×
|
4
4
|
.content
|
data/config/locales/en.yml
CHANGED
@@ -46,7 +46,7 @@ en:
|
|
46
46
|
forward_enquiry:
|
47
47
|
subject: Website Enquiry
|
48
48
|
actions:
|
49
|
-
|
49
|
+
confirmation:
|
50
50
|
deletion: If you delete this item it will be gone forever. Are you sure you want to proceed?
|
51
51
|
new_page: Add new page
|
52
52
|
new_post: Add new post
|
@@ -75,6 +75,8 @@ en:
|
|
75
75
|
copy_url: Copy URL
|
76
76
|
copied: Copied
|
77
77
|
search: Search
|
78
|
+
confirm: Confirm
|
79
|
+
cancel: Cancel
|
78
80
|
prompts:
|
79
81
|
select_image: Select Image..
|
80
82
|
select_type: Select Type..
|
@@ -101,6 +103,7 @@ en:
|
|
101
103
|
title: Title
|
102
104
|
tags: Tags
|
103
105
|
gallery: Gallery
|
106
|
+
type: Type
|
104
107
|
status:
|
105
108
|
archived: Archived
|
106
109
|
draft: Draft
|
data/db/seeds.rb
CHANGED
@@ -47,7 +47,7 @@ Integral::List.create!({ title: 'Main Menu', list_items: [
|
|
47
47
|
Integral::Link.create!({title: 'Integral', url: '/'}),
|
48
48
|
Integral::Link.create!({title: 'Documentation', url: 'https://github.com/yamasolutions/integral'}),
|
49
49
|
Integral::Link.create!({title: 'Blog', url: '/blog'}),
|
50
|
-
Integral::Link.create!({title: '
|
50
|
+
Integral::Link.create!({title: 'Demo Now', url: 'https://heroku.com/deploy?template=https://github.com/yamasolutions/integral-sample'})
|
51
51
|
]})
|
52
52
|
|
53
53
|
PaperTrail.enabled = true
|
@@ -0,0 +1,54 @@
|
|
1
|
+
module Integral
|
2
|
+
# Integral Generators
|
3
|
+
module Generators
|
4
|
+
# Generates a copy of Integral assets
|
5
|
+
#
|
6
|
+
# @example Generate all Integral assets
|
7
|
+
# rails g integral:assets --assets 'backend frontend email'
|
8
|
+
class AssetsGenerator < Rails::Generators::Base
|
9
|
+
source_root File.expand_path('../../../../app/assets', __FILE__)
|
10
|
+
class_option :asset_list, aliases: '-a', type: :array, default: 'frontend'
|
11
|
+
desc 'Copies Integral assets to your application'
|
12
|
+
|
13
|
+
# Copies over backend assets
|
14
|
+
def copy_backend_assets
|
15
|
+
return unless options['asset_list'].include?('backend')
|
16
|
+
|
17
|
+
file 'javascripts/integral/backend.js'
|
18
|
+
file 'stylesheets/integral/backend.sass'
|
19
|
+
directory 'stylesheets/integral/backend'
|
20
|
+
end
|
21
|
+
|
22
|
+
# Copies over frontend assets
|
23
|
+
def copy_frontend_assets
|
24
|
+
return unless options['asset_list'].include?('frontend')
|
25
|
+
|
26
|
+
file 'javascripts/integral/frontend.js'
|
27
|
+
file 'stylesheets/integral/frontend.sass'
|
28
|
+
directory 'stylesheets/integral/frontend'
|
29
|
+
end
|
30
|
+
|
31
|
+
# Copies over mailer assets
|
32
|
+
def copy_mailer_assets
|
33
|
+
return unless options['asset_list'].include?('email')
|
34
|
+
|
35
|
+
file 'stylesheets/integral/emails.scss'
|
36
|
+
directory 'stylesheets/integral/emails'
|
37
|
+
end
|
38
|
+
|
39
|
+
private
|
40
|
+
|
41
|
+
def directory(source, destination = nil)
|
42
|
+
destination = "app/assets/#{source}" if destination.nil?
|
43
|
+
|
44
|
+
super(source, destination)
|
45
|
+
end
|
46
|
+
|
47
|
+
def file(source, destination = nil)
|
48
|
+
destination = "app/assets/#{source}" if destination.nil?
|
49
|
+
|
50
|
+
copy_file(source, destination)
|
51
|
+
end
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -1,19 +1,53 @@
|
|
1
1
|
module Integral
|
2
2
|
# Integral Generators
|
3
3
|
module Generators
|
4
|
-
#
|
4
|
+
# Runs setup for an Integral Application
|
5
5
|
class InstallGenerator < Rails::Generators::Base
|
6
6
|
source_root File.expand_path('../../templates', __FILE__)
|
7
7
|
desc 'Creates Integral, Carrierwave, CarrierwaveBackgrounder & Sitemap initializers'
|
8
8
|
|
9
9
|
# Copies over necessary initialiser files
|
10
|
-
def
|
10
|
+
def copy_initializer_files
|
11
11
|
copy_file 'integral.rb', 'config/initializers/integral.rb'
|
12
12
|
copy_file 'app.yml', 'config/app.yml'
|
13
13
|
copy_file 'carrierwave.rb', 'config/initializers/carrierwave.rb'
|
14
14
|
copy_file 'carrierwave_backgrounder.rb', 'config/initializers/carrierwave_backgrounder.rb'
|
15
15
|
copy_file 'sitemap.rb', 'config/sitemap.rb'
|
16
16
|
end
|
17
|
+
|
18
|
+
# Copies routes file
|
19
|
+
def copy_routes
|
20
|
+
copy_file 'routes.rb', 'config/routes.rb'
|
21
|
+
end
|
22
|
+
|
23
|
+
# Copies seeding file
|
24
|
+
def copy_seeding
|
25
|
+
copy_file 'seeds.rb', 'db/seeds.rb'
|
26
|
+
end
|
27
|
+
|
28
|
+
# Copy required migrations
|
29
|
+
def copy_migrations
|
30
|
+
rake 'integral:install:migrations'
|
31
|
+
end
|
32
|
+
|
33
|
+
# Create, migrate and run setup on database - setup is incase DB was already present
|
34
|
+
def setup_database
|
35
|
+
rake 'db:create'
|
36
|
+
rake 'db:migrate'
|
37
|
+
rake 'db:setup'
|
38
|
+
end
|
39
|
+
|
40
|
+
# Output successful install message
|
41
|
+
def install_message
|
42
|
+
puts ' --------------------------------------------------------------------'
|
43
|
+
puts ' Integral has successfully installed! '
|
44
|
+
puts
|
45
|
+
puts " The admin backend is located at /#{Integral.backend_namespace}."
|
46
|
+
puts
|
47
|
+
puts " User email : #{Integral::User.first.email}"
|
48
|
+
puts ' User password : password'
|
49
|
+
puts ' --------------------------------------------------------------------'
|
50
|
+
end
|
17
51
|
end
|
18
52
|
end
|
19
53
|
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
module Integral
|
2
|
+
# Integral Generators
|
3
|
+
module Generators
|
4
|
+
# Generates a copy of Integral views
|
5
|
+
#
|
6
|
+
# @example Generate all Integral views
|
7
|
+
# rails g integral:views --views 'backend frontend devise mailer'
|
8
|
+
class ViewsGenerator < Rails::Generators::Base
|
9
|
+
source_root File.expand_path('../../../../app/views', __FILE__)
|
10
|
+
class_option :views, aliases: '-v', type: :array, default: 'frontend'
|
11
|
+
desc 'Copies Integral views to your application'
|
12
|
+
|
13
|
+
# Copies over backend views
|
14
|
+
def copy_backend_views
|
15
|
+
return unless options['views'].include?('backend')
|
16
|
+
|
17
|
+
directory 'integral/backend'
|
18
|
+
directory 'layouts/integral/backend'
|
19
|
+
file 'layouts/integral/backend.html.haml'
|
20
|
+
end
|
21
|
+
|
22
|
+
# Copies over frontend views
|
23
|
+
def copy_frontend_views
|
24
|
+
return unless options['views'].include?('frontend')
|
25
|
+
|
26
|
+
directory 'integral/pages'
|
27
|
+
directory 'integral/posts'
|
28
|
+
directory 'integral/tags'
|
29
|
+
directory 'integral/shared'
|
30
|
+
directory 'layouts/integral/frontend'
|
31
|
+
file 'layouts/integral/frontend.html.haml'
|
32
|
+
end
|
33
|
+
|
34
|
+
# Copies over mailer views
|
35
|
+
def copy_mailer_views
|
36
|
+
return unless options['views'].include?('mailer')
|
37
|
+
|
38
|
+
directory 'integral/contact_mailer'
|
39
|
+
directory 'layouts/integral/mailer'
|
40
|
+
file 'layouts/integral/mailer.html.inky-haml'
|
41
|
+
end
|
42
|
+
|
43
|
+
# Copies over devise views
|
44
|
+
def copy_devise_views
|
45
|
+
return unless options['views'].include?('devise')
|
46
|
+
|
47
|
+
directory 'devise'
|
48
|
+
file 'layouts/integral/login.haml'
|
49
|
+
end
|
50
|
+
|
51
|
+
private
|
52
|
+
|
53
|
+
def directory(source, destination = nil)
|
54
|
+
destination = "app/views/#{source}" if destination.nil?
|
55
|
+
|
56
|
+
super(source, destination)
|
57
|
+
end
|
58
|
+
|
59
|
+
def file(source, destination = nil)
|
60
|
+
destination = "app/views/#{source}" if destination.nil?
|
61
|
+
|
62
|
+
copy_file(source, destination)
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -3,7 +3,7 @@ module Integral
|
|
3
3
|
# A widget could be used to list recent articles from the blog, featured content from a list, etc
|
4
4
|
#
|
5
5
|
# Example Widget Markup
|
6
|
-
# <p class='integral-widget' data-widget-type='recent_posts' data-widget-value-tagged='
|
6
|
+
# <p class='integral-widget' data-widget-type='recent_posts' data-widget-value-tagged='sweet-tag'>
|
7
7
|
class ContentRenderer
|
8
8
|
# Markup defining a widget
|
9
9
|
PLACEHOLDER_SELECTOR = 'p.integral-widget'.freeze
|
data/lib/integral/router.rb
CHANGED
data/lib/integral/version.rb
CHANGED
@@ -32,7 +32,7 @@ module Integral
|
|
32
32
|
|
33
33
|
# Scope of the widget
|
34
34
|
def self.skope(options)
|
35
|
-
skope = Integral::Post.published
|
35
|
+
skope = Integral::Post.published.order(published_at: :desc)
|
36
36
|
skope = skope.tagged_with(options[:tagged].split) if options[:tagged].present?
|
37
37
|
skope.limit(options[:amount])
|
38
38
|
end
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
Binary file
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: integral
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0
|
4
|
+
version: 1.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Patrick Lindsay
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-
|
11
|
+
date: 2018-12-25 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: active_record_union
|
@@ -212,14 +212,14 @@ dependencies:
|
|
212
212
|
requirements:
|
213
213
|
- - "~>"
|
214
214
|
- !ruby/object:Gem::Version
|
215
|
-
version: 4.
|
215
|
+
version: 4.5.0
|
216
216
|
type: :runtime
|
217
217
|
prerelease: false
|
218
218
|
version_requirements: !ruby/object:Gem::Requirement
|
219
219
|
requirements:
|
220
220
|
- - "~>"
|
221
221
|
- !ruby/object:Gem::Version
|
222
|
-
version: 4.
|
222
|
+
version: 4.5.0
|
223
223
|
- !ruby/object:Gem::Dependency
|
224
224
|
name: devise_invitable
|
225
225
|
requirement: !ruby/object:Gem::Requirement
|
@@ -822,20 +822,6 @@ dependencies:
|
|
822
822
|
- - "~>"
|
823
823
|
- !ruby/object:Gem::Version
|
824
824
|
version: '3.4'
|
825
|
-
- !ruby/object:Gem::Dependency
|
826
|
-
name: cane
|
827
|
-
requirement: !ruby/object:Gem::Requirement
|
828
|
-
requirements:
|
829
|
-
- - "~>"
|
830
|
-
- !ruby/object:Gem::Version
|
831
|
-
version: '3.0'
|
832
|
-
type: :development
|
833
|
-
prerelease: false
|
834
|
-
version_requirements: !ruby/object:Gem::Requirement
|
835
|
-
requirements:
|
836
|
-
- - "~>"
|
837
|
-
- !ruby/object:Gem::Version
|
838
|
-
version: '3.0'
|
839
825
|
- !ruby/object:Gem::Dependency
|
840
826
|
name: flay
|
841
827
|
requirement: !ruby/object:Gem::Requirement
|
@@ -1425,7 +1411,6 @@ files:
|
|
1425
1411
|
- app/assets/stylesheets/integral/support/mixins.sass
|
1426
1412
|
- app/assets/stylesheets/integral/support/scroll-to-top.sass
|
1427
1413
|
- app/assets/stylesheets/integral/support/swiper.css
|
1428
|
-
- app/assets/stylesheets/integral/wysiwyg.sass
|
1429
1414
|
- app/controllers/integral/application_controller.rb
|
1430
1415
|
- app/controllers/integral/backend/activities_controller.rb
|
1431
1416
|
- app/controllers/integral/backend/base_controller.rb
|
@@ -1527,7 +1512,6 @@ files:
|
|
1527
1512
|
- app/views/integral/backend/lists/edit.haml
|
1528
1513
|
- app/views/integral/backend/lists/index.haml
|
1529
1514
|
- app/views/integral/backend/lists/new.haml
|
1530
|
-
- app/views/integral/backend/lists/show.haml
|
1531
1515
|
- app/views/integral/backend/pages/_form.haml
|
1532
1516
|
- app/views/integral/backend/pages/_grid.haml
|
1533
1517
|
- app/views/integral/backend/pages/activities.haml
|
@@ -1577,6 +1561,7 @@ files:
|
|
1577
1561
|
- app/views/integral/contact_mailer/forward_enquiry.text.erb
|
1578
1562
|
- app/views/integral/pages/_demo.haml
|
1579
1563
|
- app/views/integral/pages/templates/default.haml
|
1564
|
+
- app/views/integral/posts/_collection.haml
|
1580
1565
|
- app/views/integral/posts/_item.haml
|
1581
1566
|
- app/views/integral/posts/index.haml
|
1582
1567
|
- app/views/integral/posts/templates/default.haml
|
@@ -1669,11 +1654,15 @@ files:
|
|
1669
1654
|
- db/migrate/20180920030236_update_posts_and_pages_null.rb
|
1670
1655
|
- db/migrate/20181011234446_add_preview_image_to_posts.rb
|
1671
1656
|
- db/seeds.rb
|
1657
|
+
- lib/generators/integral/assets_generator.rb
|
1672
1658
|
- lib/generators/integral/install_generator.rb
|
1659
|
+
- lib/generators/integral/views_generator.rb
|
1673
1660
|
- lib/generators/templates/app.yml
|
1674
1661
|
- lib/generators/templates/carrierwave.rb
|
1675
1662
|
- lib/generators/templates/carrierwave_backgrounder.rb
|
1676
1663
|
- lib/generators/templates/integral.rb
|
1664
|
+
- lib/generators/templates/routes.rb
|
1665
|
+
- lib/generators/templates/seeds.rb
|
1677
1666
|
- lib/generators/templates/sitemap.rb
|
1678
1667
|
- lib/integral.rb
|
1679
1668
|
- lib/integral/acts_as_listable.rb
|
@@ -1703,6 +1692,20 @@ files:
|
|
1703
1692
|
- lib/integral/widgets/swiper_list.rb
|
1704
1693
|
- lib/tasks/integral_tasks.rake
|
1705
1694
|
- lib/templates/erb/scaffold/_form.html.erb
|
1695
|
+
- public/images/integral/demo/continous-integration.png
|
1696
|
+
- public/images/integral/demo/foundation-frontend-framework.jpg
|
1697
|
+
- public/images/integral/demo/heroku.png
|
1698
|
+
- public/images/integral/demo/integral-cms-without-hassle.jpg
|
1699
|
+
- public/images/integral/demo/integral-features-activity-tracking.jpg
|
1700
|
+
- public/images/integral/demo/integral-features-contact-form.png
|
1701
|
+
- public/images/integral/demo/integral-features-design.jpg
|
1702
|
+
- public/images/integral/demo/integral-features-dynamic-pages.jpg
|
1703
|
+
- public/images/integral/demo/integral-features-image-management.jpg
|
1704
|
+
- public/images/integral/demo/integral-features-integrated-blog.jpg
|
1705
|
+
- public/images/integral/demo/integral-features-list-management.jpg
|
1706
|
+
- public/images/integral/demo/integral-features-seo-ready.jpg
|
1707
|
+
- public/images/integral/demo/integral-features-user-management.jpg
|
1708
|
+
- public/images/integral/demo/integral-presentation.png
|
1706
1709
|
- public/integral/ckeditor_demo_content.html
|
1707
1710
|
- spec/factories.rb
|
1708
1711
|
- spec/support/image.jpg
|
@@ -1,13 +0,0 @@
|
|
1
|
-
// TODO: Update or Remove
|
2
|
-
.wysiwyg-content, body.cke_editable
|
3
|
-
table.img-container
|
4
|
-
width: auto
|
5
|
-
tbody
|
6
|
-
border: none
|
7
|
-
tbody th, tbody td
|
8
|
-
padding: 0
|
9
|
-
tr:last-of-type td
|
10
|
-
background-color: $light-gray
|
11
|
-
text-align: center
|
12
|
-
padding: .25em
|
13
|
-
font-size: .9em
|
@@ -1,26 +0,0 @@
|
|
1
|
-
-# = icon_link_to 'content_copy', '#clone-modal', class: 'button', data: { tooltip: t('integral.actions.clone') }, icon_classes: 'small'
|
2
|
-
|
3
|
-
= content_for :title, t('.title', title: @list.title)
|
4
|
-
|
5
|
-
= simple_form_for [:backend, @list], validate: true, html: { class: 'are-you-sure', 'data-confirm-dirty-form' => true, 'data-list-item-limit' => @list.list_item_limit, id: :list_form } do |f|
|
6
|
-
= f.input :lock_version, as: :hidden
|
7
|
-
.grid-x.grid-padding-x
|
8
|
-
.cell.medium-6.flex-container
|
9
|
-
.card
|
10
|
-
.card-section
|
11
|
-
= f.input :title, hint: false, disabled: true
|
12
|
-
.cell.medium-6.flex-container
|
13
|
-
.card
|
14
|
-
.card-section
|
15
|
-
= f.input :description, hint: false, disabled: true
|
16
|
-
.cell
|
17
|
-
= render partial: 'integral/backend/lists/manager', locals: { f: f, locked: true }
|
18
|
-
.cell
|
19
|
-
= f.button :button
|
20
|
-
|
21
|
-
-# Image Selector
|
22
|
-
= render partial: 'integral/backend/shared/record_selector/modal', locals: { search_path: backend_img_index_path, title: t('integral.prompts.select_image'), name: 'Image', create_modal: '#new_image_modal', initialize: true }
|
23
|
-
= render partial: 'integral/backend/images/create_modal'
|
24
|
-
|
25
|
-
- Integral::ActsAsListable.objects.each do |listable|
|
26
|
-
= render partial: 'integral/backend/shared/record_selector/modal', locals: { search_path: listable.listable_options[:selector_path], title: listable.listable_options[:selector_title], name: listable.to_s.parameterize, initialize: true }
|