pages_core 3.8.1 → 3.9.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Rakefile +35 -0
- data/VERSION +1 -0
- data/app/assets/builds/pages_core/admin-dist.js +7 -7
- data/app/controllers/admin/images_controller.rb +1 -1
- data/app/controllers/concerns/pages_core/error_reporting.rb +2 -0
- data/app/javascript/components/Attachments/Attachment.jsx +2 -2
- data/app/javascript/components/Attachments/AttachmentEditor.jsx +2 -2
- data/app/javascript/components/EditableImage.jsx +1 -1
- data/app/javascript/components/FileUploadButton.jsx +27 -34
- data/app/javascript/components/ImageEditor/Form.jsx +2 -2
- data/app/javascript/components/ImageEditor.jsx +1 -1
- data/app/javascript/components/ImageGrid/GridImage.jsx +1 -1
- data/app/javascript/components/ImageGrid.jsx +1 -1
- data/app/javascript/components/ImageUploader.jsx +1 -1
- data/app/javascript/components/Modal.jsx +1 -1
- data/app/javascript/components/Toast.jsx +1 -1
- data/app/javascript/components.js +1 -0
- data/app/javascript/index.js +1 -0
- data/app/javascript/{components → stores}/ModalStore.jsx +0 -0
- data/app/javascript/{components → stores}/ToastStore.jsx +0 -0
- data/app/javascript/stores.js +2 -0
- data/app/models/concerns/pages_core/page_model/pathable.rb +1 -1
- data/app/models/invite.rb +0 -2
- data/app/models/page_category.rb +0 -1
- data/app/models/page_exporter.rb +2 -2
- data/app/models/password_reset_token.rb +0 -2
- data/app/models/role.rb +6 -16
- data/app/models/tagging.rb +0 -2
- data/lib/pages_core/cache_sweeper.rb +0 -9
- data/lib/pages_core/configuration/base.rb +3 -1
- data/lib/pages_core/pub_sub.rb +1 -2
- data/lib/pages_core/version.rb +3 -1
- metadata +27 -10
@@ -2,8 +2,8 @@ import React from "react";
|
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
import copyToClipboard from "../../lib/copyToClipboard";
|
4
4
|
import AttachmentEditor from "./AttachmentEditor";
|
5
|
-
import ModalStore from "
|
6
|
-
import ToastStore from "
|
5
|
+
import ModalStore from "../../stores/ModalStore";
|
6
|
+
import ToastStore from "../../stores/ToastStore";
|
7
7
|
|
8
8
|
import { useDraggable } from "../drag";
|
9
9
|
|
@@ -1,8 +1,8 @@
|
|
1
1
|
import React, { useState } from "react";
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
import copyToClipboard, { copySupported } from "../../lib/copyToClipboard";
|
4
|
-
import ModalStore from "
|
5
|
-
import ToastStore from "
|
4
|
+
import ModalStore from "../../stores/ModalStore";
|
5
|
+
import ToastStore from "../../stores/ToastStore";
|
6
6
|
import { putJson } from "../../lib/request";
|
7
7
|
|
8
8
|
export default function AttachmentEditor(props) {
|
@@ -1,7 +1,7 @@
|
|
1
1
|
import React, { useState } from "react";
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
import ImageEditor from "./ImageEditor";
|
4
|
-
import ModalStore from "
|
4
|
+
import ModalStore from "../stores/ModalStore";
|
5
5
|
|
6
6
|
export default function EditableImage(props) {
|
7
7
|
const [image, setImage] = useState(props.image);
|
@@ -1,49 +1,42 @@
|
|
1
|
-
import React from "react";
|
1
|
+
import React, { useRef } from "react";
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
|
4
|
-
export default
|
5
|
-
|
6
|
-
super(props);
|
7
|
-
this.inputRef = React.createRef();
|
8
|
-
this.handleChange = this.handleChange.bind(this);
|
9
|
-
this.triggerDialog = this.triggerDialog.bind(this);
|
10
|
-
}
|
4
|
+
export default function FileUploadButton(props) {
|
5
|
+
const inputRef = useRef();
|
11
6
|
|
12
|
-
handleChange(evt) {
|
7
|
+
const handleChange = (evt) => {
|
13
8
|
let fileList = evt.target.files;
|
14
9
|
let files = [];
|
15
10
|
for (var i = 0; i < fileList.length; i++) {
|
16
11
|
files.push(fileList[i]);
|
17
12
|
}
|
18
13
|
if (files.length > 0) {
|
19
|
-
|
14
|
+
props.callback(files);
|
20
15
|
}
|
21
|
-
}
|
16
|
+
};
|
22
17
|
|
23
|
-
|
24
|
-
return (
|
25
|
-
<div className="upload-button">
|
26
|
-
<span>
|
27
|
-
Drag and drop {this.props.type || "file"}
|
28
|
-
{this.props.multiple && "s"} here, or
|
29
|
-
{this.props.multiline && <br />}
|
30
|
-
<button onClick={this.triggerDialog}>
|
31
|
-
choose a file
|
32
|
-
</button>
|
33
|
-
</span>
|
34
|
-
<input type="file"
|
35
|
-
onChange={this.handleChange}
|
36
|
-
ref={this.inputRef}
|
37
|
-
style={{ display: "none" }}
|
38
|
-
multiple={this.props.multiple || false} />
|
39
|
-
</div>
|
40
|
-
);
|
41
|
-
}
|
42
|
-
|
43
|
-
triggerDialog(evt) {
|
18
|
+
const triggerDialog = (evt) => {
|
44
19
|
evt.preventDefault();
|
45
|
-
|
46
|
-
}
|
20
|
+
inputRef.current.click();
|
21
|
+
};
|
22
|
+
|
23
|
+
return (
|
24
|
+
<div className="upload-button">
|
25
|
+
<span>
|
26
|
+
Drag and drop {props.type || "file"}
|
27
|
+
{props.multiple && "s"} here, or
|
28
|
+
{props.multiline && <br />}
|
29
|
+
<button onClick={triggerDialog}>
|
30
|
+
choose a file
|
31
|
+
</button>
|
32
|
+
</span>
|
33
|
+
<input type="file"
|
34
|
+
onChange={handleChange}
|
35
|
+
ref={inputRef}
|
36
|
+
style={{ display: "none" }}
|
37
|
+
multiple={props.multiple || false} />
|
38
|
+
</div>
|
39
|
+
);
|
47
40
|
}
|
48
41
|
|
49
42
|
FileUploadButton.propTypes = {
|
@@ -1,7 +1,7 @@
|
|
1
1
|
import React from "react";
|
2
2
|
import PropTypes from "prop-types";
|
3
|
-
import ModalStore from "
|
4
|
-
import ToastStore from "
|
3
|
+
import ModalStore from "../../stores/ModalStore";
|
4
|
+
import ToastStore from "../../stores/ToastStore";
|
5
5
|
import copyToClipboard, { copySupported } from "../../lib/copyToClipboard";
|
6
6
|
|
7
7
|
export default function Form(props) {
|
@@ -1,6 +1,6 @@
|
|
1
1
|
import React, { useState } from "react";
|
2
2
|
import PropTypes from "prop-types";
|
3
|
-
import ModalStore from "
|
3
|
+
import ModalStore from "../stores/ModalStore";
|
4
4
|
import { putJson } from "../lib/request";
|
5
5
|
|
6
6
|
import ImageCropper, { useCrop, cropParams } from "./ImageCropper";
|
@@ -2,7 +2,7 @@ import React, { useEffect, useState } from "react";
|
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
import copyToClipboard from "../../lib/copyToClipboard";
|
4
4
|
import EditableImage from "../EditableImage";
|
5
|
-
import ToastStore from "
|
5
|
+
import ToastStore from "../../stores/ToastStore";
|
6
6
|
import Placeholder from "./Placeholder";
|
7
7
|
|
8
8
|
import { useDraggable } from "../drag";
|
@@ -4,7 +4,7 @@ import FileUploadButton from "./FileUploadButton";
|
|
4
4
|
import DragElement from "./ImageGrid/DragElement";
|
5
5
|
import FilePlaceholder from "./ImageGrid/FilePlaceholder";
|
6
6
|
import GridImage from "./ImageGrid/GridImage";
|
7
|
-
import ToastStore from "
|
7
|
+
import ToastStore from "../stores/ToastStore";
|
8
8
|
import { post } from "../lib/request";
|
9
9
|
|
10
10
|
import { createDraggable,
|
@@ -2,7 +2,7 @@ import React, { useState } from "react";
|
|
2
2
|
import PropTypes from "prop-types";
|
3
3
|
import EditableImage from "./EditableImage";
|
4
4
|
import FileUploadButton from "./FileUploadButton";
|
5
|
-
import ToastStore from "
|
5
|
+
import ToastStore from "../stores/ToastStore";
|
6
6
|
import { post } from "../lib/request";
|
7
7
|
|
8
8
|
function getFiles(dt) {
|
@@ -1,6 +1,7 @@
|
|
1
1
|
export { default as Attachments } from "./components/Attachments";
|
2
2
|
export { default as DateRangeSelect } from "./components/DateRangeSelect";
|
3
3
|
export { default as EditableImage } from "./components/EditableImage";
|
4
|
+
export { default as FileUploadButton } from "./components/FileUploadButton";
|
4
5
|
export { default as ImageCropper } from "./components/ImageCropper";
|
5
6
|
export { default as ImageGrid } from "./components/ImageGrid";
|
6
7
|
export { default as ImageUploader } from "./components/ImageUploader";
|
data/app/javascript/index.js
CHANGED
File without changes
|
File without changes
|
data/app/models/invite.rb
CHANGED
data/app/models/page_category.rb
CHANGED
data/app/models/page_exporter.rb
CHANGED
@@ -74,7 +74,7 @@ class PageExporter
|
|
74
74
|
|
75
75
|
def page_file_name(page)
|
76
76
|
[page.path_segment,
|
77
|
-
page.to_param[0..250]].
|
77
|
+
page.to_param[0..250]].compact_blank.first
|
78
78
|
end
|
79
79
|
|
80
80
|
def page_path_segment(page)
|
@@ -95,6 +95,6 @@ class PageExporter
|
|
95
95
|
|
96
96
|
def write_file(path, data)
|
97
97
|
FileUtils.mkdir_p(File.dirname(path))
|
98
|
-
File.
|
98
|
+
File.binwrite(path, data)
|
99
99
|
end
|
100
100
|
end
|
@@ -5,8 +5,6 @@ class PasswordResetToken < ApplicationRecord
|
|
5
5
|
before_create :ensure_token
|
6
6
|
before_create :ensure_expiration
|
7
7
|
|
8
|
-
validates :user_id, presence: true
|
9
|
-
|
10
8
|
scope :active, -> { where("expires_at >= ?", Time.now.utc) }
|
11
9
|
scope :expired, -> { where("expires_at < ?", Time.now.utc) }
|
12
10
|
|
data/app/models/role.rb
CHANGED
@@ -7,17 +7,15 @@ class Role < ApplicationRecord
|
|
7
7
|
uniqueness: { scope: :user_id },
|
8
8
|
inclusion: { in: proc { Role.roles.map(&:name) } }
|
9
9
|
|
10
|
+
RoleDefinition = Struct.new(:name, :description, :default)
|
11
|
+
|
10
12
|
class << self
|
11
13
|
def define(name, description, default: false)
|
12
14
|
if roles.map(&:name).include?(name.to_s)
|
13
15
|
raise ArgumentError, "Tried to define role :#{role}, " \
|
14
16
|
"but a role by that name already exists"
|
15
17
|
else
|
16
|
-
roles <<
|
17
|
-
name: name.to_s,
|
18
|
-
description: description,
|
19
|
-
default: default
|
20
|
-
)
|
18
|
+
roles << RoleDefinition.new(name.to_s, description, default)
|
21
19
|
end
|
22
20
|
end
|
23
21
|
|
@@ -39,21 +37,13 @@ class Role < ApplicationRecord
|
|
39
37
|
return [] unless File.exist?(config_file)
|
40
38
|
|
41
39
|
YAML.load_file(config_file).map do |key, opts|
|
42
|
-
|
43
|
-
description: opts["description"],
|
44
|
-
default: opts["default"])
|
40
|
+
RoleDefinition.new(key.to_s, opts["description"], opts["default"])
|
45
41
|
end
|
46
42
|
end
|
47
43
|
|
48
44
|
def default_roles
|
49
|
-
[
|
50
|
-
|
51
|
-
name: "users", description: "Can manage users", default: false
|
52
|
-
),
|
53
|
-
OpenStruct.new(
|
54
|
-
name: "pages", description: "Can manage pages", default: true
|
55
|
-
)
|
56
|
-
]
|
45
|
+
[RoleDefinition.new("users", "Can manage users", false),
|
46
|
+
RoleDefinition.new("pages", "Can manage pages", true)]
|
57
47
|
end
|
58
48
|
end
|
59
49
|
|
data/app/models/tagging.rb
CHANGED
@@ -4,10 +4,8 @@ class Tagging < ApplicationRecord
|
|
4
4
|
belongs_to :tag
|
5
5
|
belongs_to :taggable, polymorphic: true, touch: true
|
6
6
|
|
7
|
-
validates :taggable_id, presence: true
|
8
7
|
validates :taggable_type, presence: true
|
9
8
|
validates :tag_id,
|
10
|
-
presence: true,
|
11
9
|
uniqueness: { scope: %i[taggable_type taggable_id] }
|
12
10
|
|
13
11
|
def self.tagged_class(taggable)
|
@@ -16,15 +16,6 @@ module PagesCore
|
|
16
16
|
disable(&block)
|
17
17
|
PagesCore::StaticCache.handler.sweep!
|
18
18
|
end
|
19
|
-
|
20
|
-
def config
|
21
|
-
ActiveSupport::Deprecation.warn(
|
22
|
-
"PagesCore::CacheSweeper.config is no longer used."
|
23
|
-
)
|
24
|
-
configuration = OpenStruct.new(patterns: [])
|
25
|
-
yield configuration if block_given?
|
26
|
-
configuration
|
27
|
-
end
|
28
19
|
end
|
29
20
|
|
30
21
|
self.enabled ||= true
|
@@ -5,12 +5,14 @@ module PagesCore
|
|
5
5
|
class Base
|
6
6
|
class InvalidConfigurationKey < StandardError; end
|
7
7
|
|
8
|
+
SettingStruct = Struct.new(:type, :default)
|
9
|
+
|
8
10
|
def self.settings
|
9
11
|
@settings ||= {}
|
10
12
|
end
|
11
13
|
|
12
14
|
def self.setting(key, type, default = nil)
|
13
|
-
settings[key] =
|
15
|
+
settings[key] = SettingStruct.new(type, default)
|
14
16
|
|
15
17
|
define_method key do |*args|
|
16
18
|
args.any? ? set(key, *args) : get(key)
|
data/lib/pages_core/pub_sub.rb
CHANGED
@@ -4,9 +4,8 @@ module PagesCore
|
|
4
4
|
module PubSub
|
5
5
|
class << self
|
6
6
|
def publish(name, payload = {})
|
7
|
-
payload_struct = OpenStruct.new(payload)
|
8
7
|
subscribers.select { |s| s.name == name }
|
9
|
-
.each { |s| s.call(
|
8
|
+
.each { |s| s.call(payload) }
|
10
9
|
end
|
11
10
|
|
12
11
|
def subscribe(name, &block)
|
data/lib/pages_core/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pages_core
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.
|
4
|
+
version: 3.9.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Inge Jørgensen
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-01-14 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: capybara
|
@@ -94,6 +94,20 @@ dependencies:
|
|
94
94
|
- - ">="
|
95
95
|
- !ruby/object:Gem::Version
|
96
96
|
version: 3.8.1
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: semantic
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - ">="
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '0'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - ">="
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '0'
|
97
111
|
- !ruby/object:Gem::Dependency
|
98
112
|
name: shoulda-matchers
|
99
113
|
requirement: !ruby/object:Gem::Requirement
|
@@ -126,16 +140,16 @@ dependencies:
|
|
126
140
|
name: timecop
|
127
141
|
requirement: !ruby/object:Gem::Requirement
|
128
142
|
requirements:
|
129
|
-
- - "
|
143
|
+
- - ">="
|
130
144
|
- !ruby/object:Gem::Version
|
131
|
-
version: 0
|
145
|
+
version: '0'
|
132
146
|
type: :development
|
133
147
|
prerelease: false
|
134
148
|
version_requirements: !ruby/object:Gem::Requirement
|
135
149
|
requirements:
|
136
|
-
- - "
|
150
|
+
- - ">="
|
137
151
|
- !ruby/object:Gem::Version
|
138
|
-
version: 0
|
152
|
+
version: '0'
|
139
153
|
- !ruby/object:Gem::Dependency
|
140
154
|
name: rails
|
141
155
|
requirement: !ruby/object:Gem::Requirement
|
@@ -495,6 +509,7 @@ extra_rdoc_files: []
|
|
495
509
|
files:
|
496
510
|
- README.md
|
497
511
|
- Rakefile
|
512
|
+
- VERSION
|
498
513
|
- app/assets/builds/pages_core/admin-dist.js
|
499
514
|
- app/assets/images/pages/admin/drag-icon.png
|
500
515
|
- app/assets/images/pages/admin/icon.png
|
@@ -621,7 +636,6 @@ files:
|
|
621
636
|
- app/javascript/components/ImageGrid/Placeholder.jsx
|
622
637
|
- app/javascript/components/ImageUploader.jsx
|
623
638
|
- app/javascript/components/Modal.jsx
|
624
|
-
- app/javascript/components/ModalStore.jsx
|
625
639
|
- app/javascript/components/PageDates.jsx
|
626
640
|
- app/javascript/components/PageFiles.jsx
|
627
641
|
- app/javascript/components/PageImages.jsx
|
@@ -634,7 +648,6 @@ files:
|
|
634
648
|
- app/javascript/components/TagEditor/AddTagForm.jsx
|
635
649
|
- app/javascript/components/TagEditor/Tag.jsx
|
636
650
|
- app/javascript/components/Toast.jsx
|
637
|
-
- app/javascript/components/ToastStore.jsx
|
638
651
|
- app/javascript/components/drag.js
|
639
652
|
- app/javascript/components/drag/draggedOrder.js
|
640
653
|
- app/javascript/components/drag/useDragCollection.js
|
@@ -651,6 +664,9 @@ files:
|
|
651
664
|
- app/javascript/lib/copyToClipboard.js
|
652
665
|
- app/javascript/lib/readyHandler.js
|
653
666
|
- app/javascript/lib/request.js
|
667
|
+
- app/javascript/stores.js
|
668
|
+
- app/javascript/stores/ModalStore.jsx
|
669
|
+
- app/javascript/stores/ToastStore.jsx
|
654
670
|
- app/jobs/pages_core/autopublish_job.rb
|
655
671
|
- app/jobs/pages_core/sweep_cache_job.rb
|
656
672
|
- app/mailers/admin_mailer.rb
|
@@ -817,7 +833,8 @@ files:
|
|
817
833
|
- vendor/assets/stylesheets/ReactCrop.css
|
818
834
|
homepage: ''
|
819
835
|
licenses: []
|
820
|
-
metadata:
|
836
|
+
metadata:
|
837
|
+
rubygems_mfa_required: 'true'
|
821
838
|
post_install_message:
|
822
839
|
rdoc_options: []
|
823
840
|
require_paths:
|
@@ -833,7 +850,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
833
850
|
- !ruby/object:Gem::Version
|
834
851
|
version: '0'
|
835
852
|
requirements: []
|
836
|
-
rubygems_version: 3.
|
853
|
+
rubygems_version: 3.3.3
|
837
854
|
signing_key:
|
838
855
|
specification_version: 4
|
839
856
|
summary: Pages Core
|