Compare commits

...

48 Commits
3 ... 4.1.1

Author SHA1 Message Date
Guy Sartorelli 283ca6a664
Merge pull request #736 from silverstripeltd/bugfix/icons-in-add-gridfield
Remove icons from gridfield add button
2023-12-20 13:01:58 +13:00
Mohamed Alsharaf b2f0d12dd6 Remove icons from gridfield add button 2023-12-19 14:10:15 +13:00
Guy Sartorelli 1e982c8f31
Merge pull request #734 from creative-commoners/pulls/4.1/docblock
MNT Update @methods on class docblocks
2023-12-15 12:45:23 +13:00
Steve Boyd 33da9d042d MNT Update @methods on class docblocks 2023-12-14 15:08:00 +13:00
Guy Sartorelli 99d74f9c43
Merge pull request #730 from creative-commoners/pulls/4.1/remove-todo
MNT Remove TODO comments
2023-10-30 12:20:52 +13:00
Sabina Talipova 7d15e3cc68 MNT Remove TODO comments 2023-10-26 09:14:16 +13:00
github-actions fe638a0ccb Merge branch '4.0' into 4.1 2023-09-30 12:28:25 +00:00
github-actions 38bad2d658 Merge branch '3' into 4.0 2023-09-30 12:28:24 +00:00
github-actions f4ae122351 Merge branch '4.0' into 4 2023-08-29 22:25:36 +00:00
Guy Sartorelli 0f93f6a842
Merge pull request #726 from creative-commoners/pulls/4.0/module-standardiser-1693278479
MNT Run module-standardiser
2023-08-29 17:02:53 +12:00
Steve Boyd 7964baa544 MNT Run module-standardiser 2023-08-29 15:07:59 +12:00
github-actions ca5dfb4ed3 Merge branch '4.0' into 4 2023-08-26 12:28:30 +00:00
github-actions 81c661caf2 Merge branch '3' into 4.0 2023-08-26 12:28:28 +00:00
github-actions[bot] 1f3878bc3f
DEP Update JS dependencies (#725)
Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
2023-08-24 11:48:42 +12:00
Guy Sartorelli b9c535ac67
Merge pull request #720 from 3Dgoo/4
Replace deprecated sort rand with shuffle
2023-08-19 11:02:43 +12:00
Guy Sartorelli e9390c3525
ENH Update translations (#722) 2023-08-17 18:15:20 +12:00
Guy Sartorelli 29ca438a9f
Merge pull request #719 from creative-commoners/pulls/4/module-standardiser-1691549948
MNT Run module-standardiser
2023-08-15 12:09:04 +12:00
Steve Boyd 6f3b32264e MNT Run module-standardiser 2023-08-14 15:43:42 +12:00
3Dgoo bcbb40e08d
Replace deprecated sort rand with shuffle 2023-08-10 12:31:45 +09:30
3Dgoo 7189427bf3
Replace deprecated sort rand with shuffle 2023-08-10 12:20:25 +09:30
dependabot[bot] c93566f7a8
Merge pull request #718 from silverstripe/dependabot/npm_and_yarn/word-wrap-1.2.4 2023-08-03 05:25:35 +00:00
dependabot[bot] 23fd31c105
Bump word-wrap from 1.2.3 to 1.2.4
Bumps [word-wrap](https://github.com/jonschlinkert/word-wrap) from 1.2.3 to 1.2.4.
- [Release notes](https://github.com/jonschlinkert/word-wrap/releases)
- [Commits](https://github.com/jonschlinkert/word-wrap/compare/1.2.3...1.2.4)

---
updated-dependencies:
- dependency-name: word-wrap
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-07-19 02:03:25 +00:00
Sabina Talipova 1514d0b982
DEP Update eslint module (#716) 2023-07-12 11:04:37 +12:00
Sabina Talipova 84b815d0a0
MNT ESLint issues (#714) 2023-07-10 09:47:20 +12:00
Steve Boyd 3f4b87489c Merge branch '4.0' into 4 2023-06-16 11:38:35 +12:00
Steve Boyd 7f86285552 Merge branch '3' into 4.0 2023-06-16 11:37:59 +12:00
Guy Sartorelli f2388c6408
Merge pull request #712 from creative-commoners/pulls/4/tx-1686703251
ENH Update translations
2023-06-14 15:17:34 +12:00
Steve Boyd 7cbeb90280 ENH Update translations 2023-06-14 12:40:51 +12:00
Steve Boyd 08cee006fc Merge branch '4.0' into 4 2023-05-31 14:42:18 +12:00
Steve Boyd 058e2aced6 Merge branch '3' into 4.0 2023-05-31 14:42:02 +12:00
Steve Boyd d8be9212cd Merge branch '4.0' into 4 2023-05-04 13:27:32 +12:00
Guy Sartorelli dbeefc15c7
Merge branch '3' into 4.0 2023-04-27 14:45:17 +12:00
Sabina Talipova 0f8f0ac0cb
Merge pull request #707 from creative-commoners/pulls/4.0/cms5-readme
DOC Update README.md for CMS 5
2023-04-21 15:24:03 +12:00
Guy Sartorelli 05ed7e3be7
DOC Update README.md for CMS 5 2023-04-19 16:00:33 +12:00
Maxime Rainville 262b66dffd
Merge pull request #706 from creative-commoners/pulls/4.0/devjs
MNT Update dev JS
2023-04-03 15:32:14 +12:00
Steve Boyd 692c8fc390 MNT Update dev JS 2023-04-03 14:28:32 +12:00
Steve Boyd 008b2d4816 Merge branch '4.0' into 4 2023-03-30 13:31:11 +13:00
Steve Boyd 631fb53713 Merge branch '3' into 4.0 2023-03-30 13:30:34 +13:00
Steve Boyd fb7ba28a24 Merge branch '4.0' into 4 2023-03-08 12:24:35 +13:00
Steve Boyd 85f8f32736 Merge branch '3' into 4.0 2023-03-08 12:24:25 +13:00
Guy Sartorelli ffea8acb0e
DEP Upgrade frontend build stack (#697) 2023-02-07 13:35:34 +13:00
Steve Boyd f01d421ee2 Merge branch '3' into 4 2023-02-03 10:12:51 +13:00
Guy Sartorelli 624444e136
Merge pull request #699 from creative-commoners/pulls/4/broken-builds
MNT Broken builds
2023-01-25 12:46:17 +13:00
Steve Boyd 9b49e1bfcc MNT Broken builds 2023-01-24 15:41:55 +13:00
Maxime Rainville d24ea64be2
Merge pull request #698 from creative-commoners/pulls/4/remove-legacy-upgrader
MNT Remove legacy upgrader config
2023-01-23 10:39:10 +13:00
Steve Boyd 57b81dbbe3 MNT Remove legacy upgrader config 2023-01-20 17:14:18 +13:00
Maxime Rainville 0f1da8c938
Merge pull request #693 from creative-commoners/pulls/4/upgrade-cms5
DEP PHP Support in CMS5
2023-01-13 10:51:29 +13:00
Sabina Talipova 29f0b39271 DEP PHP Support in CMS5 2023-01-13 10:18:14 +13:00
29 changed files with 4583 additions and 7030 deletions

View File

@ -1,10 +1,10 @@
name: Keepalive
on:
workflow_dispatch:
# The 4th of every month at 10:50am UTC
# At 2:10 AM UTC, on day 11 of the month
schedule:
- cron: '50 10 4 * *'
- cron: '10 2 11 * *'
workflow_dispatch:
jobs:
keepalive:

17
.github/workflows/merge-up.yml vendored Normal file
View File

@ -0,0 +1,17 @@
name: Merge-up
on:
# At 12:20 PM UTC, only on Saturday
schedule:
- cron: '20 12 * * 6'
workflow_dispatch:
jobs:
merge-up:
name: Merge-up
# Only run cron on the silverstripe account
if: (github.event_name == 'schedule' && github.repository_owner == 'silverstripe') || (github.event_name != 'schedule')
runs-on: ubuntu-latest
steps:
- name: Merge-up
uses: silverstripe/gha-merge-up@v1

View File

@ -4,7 +4,7 @@ on:
workflow_dispatch:
# Run on a schedule of once per quarter
schedule:
- cron: '0 0 1 */3 *'
- cron: '10 2 1 */3 *'
jobs:
update-js:

2
.nvmrc
View File

@ -1 +1 @@
10
18

View File

@ -1,33 +0,0 @@
mappings:
GridFieldCategorisationConfig: SilverStripe\Blog\Admin\GridFieldCategorisationConfig
GridFieldFormAction: SilverStripe\Blog\Admin\GridFieldFormAction
GridFieldMergeAction: SilverStripe\Blog\Admin\GridFieldMergeAction
BlogCommentExtension: SilverStripe\Blog\Model\BlogCommentExtension
BlogFilter: SilverStripe\Blog\Model\BlogFilter
BlogFilter_GridField: SilverStripe\Blog\Model\BlogFilter\BlogFilterGridField
BlogMemberExtension: SilverStripe\Blog\Model\BlogMemberExtension
BlogPostFilter: SilverStripe\Blog\Model\BlogPostFilter
BlogPostNotifications: SilverStripe\Blog\Model\BlogPostNotifications
Blog: SilverStripe\Blog\Model\Blog
Blog_Controller: SilverStripe\Blog\Model\BlogController
BlogController: SilverStripe\Blog\Model\BlogController
BlogCategory: SilverStripe\Blog\Model\BlogCategory
BlogPost: SilverStripe\Blog\Model\BlogPost
BlogPost_Controller: SilverStripe\Blog\Model\BlogPostController
BlogPostController: SilverStripe\Blog\Model\BlogPostController
BlogTag: SilverStripe\Blog\Model\BlogTag
CategorisationObject: SilverStripe\Blog\Model\CategorisationObject
BlogAdminSidebar: SilverStripe\Blog\Forms\BlogAdminSidebar
GridFieldAddByDBField: SilverStripe\Blog\Forms\GridField\GridFieldAddByDBField
GridFieldBlogPostState: SilverStripe\Blog\Forms\GridField\GridFieldBlogPostState
GridFieldConfig_BlogPost: SilverStripe\Blog\Forms\GridField\GridFieldConfigBlogPost
BlogArchiveWidget: SilverStripe\Blog\Widgets\BlogArchiveWidget
BlogArchiveWidget_Controller: SilverStripe\Blog\Widgets\BlogArchiveWidgetController
BlogCategoriesWidget: SilverStripe\Blog\Widgets\BlogCategoriesWidget
BlogCategoriesWidget_Controller: SilverStripe\Blog\Widgets\BlogCategoriesWidgetController
BlogRecentPostsWidget: SilverStripe\Blog\Widgets\BlogRecentPostsWidget
BlogRecentPostsWidget_Controller: SilverStripe\Blog\Widgets\BlogRecentPostsWidgetController
BlogTagsCloudWidget: SilverStripe\Blog\Widgets\BlogTagsCloudWidget
BlogTagsCloudWidget_Controller: SilverStripe\Blog\Widgets\BlogTagsCloudWidgetController
BlogTagsWidget: SilverStripe\Blog\Widgets\BlogTagsWidget
BlogTagsWidget_Controller: SilverStripe\Blog\Widgets\BlogTagsWidgetController

View File

View File

@ -8,16 +8,6 @@
* [User guide](docs/en/userguide/index.md)
* [Developer documentation](docs/en/index.md)
## Requirements
* Silverstripe CMS 4.0+
* Silverstripe Lumberjack Module 2.0+
* Silverstripe Tag Field Module 2.0+
* Silverstripe Assets 1.0+
* Silverstripe Asset Admin Module 1.0+
Note: this version is compatible with Silverstripe 4. For Silverstripe 3, please see [the 2.x release line](https://github.com/silverstripe/silverstripe-blog/tree/2).
### Suggested Modules
* Silverstripe Widgets Module
@ -28,13 +18,3 @@ Note: this version is compatible with Silverstripe 4. For Silverstripe 3, please
```
composer require silverstripe/blog
```
## Upgrading
### Upgrading from 2.x to 3.x
Aside from the framework and CMS upgrades required the blog module should not require anything extra to be completed.
### Upgrading legacy blog to 2.x
If you're upgrading from blog version 1.0 to 2.x you will need to run the `BlogMigrationTask`. Run the task using `dev/tasks/BlogMigrationTask` either via the browser or sake CLI to migrate your legacy blog to the new version data structure.

View File

@ -1,14 +0,0 @@
---
Name: bloglegacy
---
SilverStripe\ORM\DatabaseAdmin:
classname_value_remapping:
Blog: SilverStripe\Blog\Model\Blog
BlogCategory: SilverStripe\Blog\Model\BlogCategory
BlogPost: SilverStripe\Blog\Model\BlogPost
BlogTag: SilverStripe\Blog\Model\BlogTag
BlogArchiveWidget: SilverStripe\Blog\Widgets\BlogArchiveWidget
BlogCategoriesWidget: SilverStripe\Blog\Widgets\BlogCategoriesWidget
BlogRecentPostsWidget: SilverStripe\Blog\Widgets\BlogRecentPostsWidget
BlogTagsCloudWidget: SilverStripe\Blog\Widgets\BlogTagsCloudWidget
BlogTagsWidget: SilverStripe\Blog\Widgets\BlogTagsWidget

6
babel.config.json Normal file
View File

@ -0,0 +1,6 @@
{
"presets": [
"@babel/preset-env",
"@babel/preset-react"
]
}

View File

@ -1 +1 @@
!function(t){function e(i){if(n[i])return n[i].exports;var o=n[i]={i:i,l:!1,exports:{}};return t[i].call(o.exports,o,o.exports,e),o.l=!0,o.exports}var n={};e.m=t,e.c=n,e.i=function(t){return t},e.d=function(t,n,i){e.o(t,n)||Object.defineProperty(t,n,{configurable:!1,enumerable:!0,get:i})},e.n=function(t){var n=t&&t.__esModule?function(){return t.default}:function(){return t};return e.d(n,"a",n),n},e.o=function(t,e){return Object.prototype.hasOwnProperty.call(t,e)},e.p="",e(e.s="./client/src/main.js")}({"./client/src/bundles/cms.js":function(t,e,n){"use strict";var i=n(0);n.n(i).a.entwine("ss",function(t){t(".cms-content-fields > #Form_EditForm_error").entwine({onadd:function(){var e=t(".blog-admin-outer");1===e.length&&e.prepend(this)}}),t(".toggle-description").entwine({onadd:function(){var e=t(this);if(!e.hasClass("toggle-description-enabled")){e.addClass("toggle-description-enabled");var n=!1,i=e.closest(".field").find(".form-text");e.on("click",function(){i[n?"hide":"show"](),e.toggleClass("toggle-description-shown"),n=!n}),i.hide(),e.parent().addClass("toggle-description-correct-right"),e.parent().prev(".middleColumn").addClass("toggle-description-correct-middle"),e.parent().next(".description").addClass("toggle-description-correct-description")}}}),t(".MergeAction").entwine({onadd:function(){var e=t(this);e.on("click","select",function(){return!1}),e.children("button").each(function(e,n){var i=t(n),o=i.prev("select");i.before('<input type="hidden" name="'+i.attr("data-target")+'" value="'+o.val()+'" />')}),e.on("change","select",function(e){var n=t(e.target);n.next("input").val(n.val())}),e.children("button, select").hide(),e.on("click",".MergeActionReveal",function(e){var n=t(e.target);return n.parent().children("button, select").show(),n.hide(),!1})}}),t(".blog-admin-sidebar.cms-panel").entwine({MinInnerWidth:620,onadd:function(){var e=this;this._super(),this.updateLayout(),!this.hasClass("collapsed")&&t(".blog-admin-outer").width()<this.getMinInnerWidth()&&this.collapsePanel();var n=function(){e.updateLayout()};n.bind(this),window.onresize=n},togglePanel:function(t,e){this._super(t,e),this.updateLayout()},updateLayout:function(){t(this).css("height","100%");var e=t(this).outerHeight(),n=t(".cms-content-actions").eq(0).outerHeight();t(this).css("height",e-n+"px"),t(this).css("bottom",n+"px"),t(".cms-container").updateLayoutOptions({minContentWidth:820+this.width()})}})})},"./client/src/bundles/gridfieldaddbydbfield.js":function(t,e,n){"use strict";var i=n(0);n.n(i).a.entwine("ss",function(t){t(".add-existing-autocompleter input.text").entwine({onkeydown:function(e){13===e.which&&(t(this).parents(".add-existing-autocompleter").find('button[type="submit"]').click(),e.preventDefault())}})})},"./client/src/main.js":function(t,e,n){"use strict";Object.defineProperty(e,"__esModule",{value:!0}),n("./client/src/bundles/cms.js"),n("./client/src/bundles/gridfieldaddbydbfield.js")},0:function(t,e){t.exports=jQuery}});
!function(){"use strict";var t={949:function(t,e,n){var i;((i=n(311))&&i.__esModule?i:{default:i}).default.entwine("ss",(t=>{t(".cms-content-fields > #Form_EditForm_error").entwine({onadd(){const e=t(".blog-admin-outer");1===e.length&&e.prepend(this)}}),t(".toggle-description").entwine({onadd(){const e=t(this);if(e.hasClass("toggle-description-enabled"))return;e.addClass("toggle-description-enabled");let n=!1;const i=e.closest(".field").find(".form-text");e.on("click",(()=>{i[n?"hide":"show"](),e.toggleClass("toggle-description-shown"),n=!n})),i.hide(),e.parent().addClass("toggle-description-correct-right"),e.parent().prev(".middleColumn").addClass("toggle-description-correct-middle"),e.parent().next(".description").addClass("toggle-description-correct-description")}}),t(".MergeAction").entwine({onadd(){const e=t(this);e.on("click","select",(()=>!1)),e.children("button").each(((e,n)=>{const i=t(n),s=i.prev("select");i.before(`<input type="hidden" name="${i.attr("data-target")}" value="${s.val()}" />`)})),e.on("change","select",(e=>{const n=t(e.target);n.next("input").val(n.val())})),e.children("button, select").hide(),e.on("click",".MergeActionReveal",(e=>{const n=t(e.target);return n.parent().children("button, select").show(),n.hide(),!1}))}}),t(".blog-admin-sidebar.cms-panel").entwine({MinInnerWidth:620,onadd(){this._super(),this.updateLayout(),!this.hasClass("collapsed")&&t(".blog-admin-outer").width()<this.getMinInnerWidth()&&this.collapsePanel();const e=()=>{this.updateLayout()};e.bind(this),window.onresize=e},togglePanel(t,e){this._super(t,e),this.updateLayout()},updateLayout(){t(this).css("height","100%");const e=t(this).outerHeight(),n=t(".cms-content-actions").eq(0).outerHeight();t(this).css("height",e-n+"px"),t(this).css("bottom",`${n}px`),t(".cms-container").updateLayoutOptions({minContentWidth:820+this.width()})}})}))},997:function(t,e,n){var i;((i=n(311))&&i.__esModule?i:{default:i}).default.entwine("ss",(t=>{t(".add-existing-autocompleter input.text").entwine({onkeydown(e){if(13===e.which){t(this).parents(".add-existing-autocompleter").find('button[type="submit"]').click(),e.preventDefault()}}})}))},311:function(t){t.exports=jQuery}},e={};function n(i){var s=e[i];if(void 0!==s)return s.exports;var o=e[i]={exports:{}};return t[i](o,o.exports,n),o.exports}n(949),n(997)}();

View File

@ -1 +1 @@
.no-sidebar .content-container.size3of4{width:75%}.blog-entry .post-image img{width:98.75%}.blog-sidebar .WidgetHolder ul{margin-left:0}.blog-sidebar .WidgetHolder ul li,ul.blogTagCloud{list-style-type:none}ul.blogTagCloud{clear:both}ul.blogTagCloud li{float:left;display:inline;padding-right:8px}ul.blogTagCloud li a span{float:left;line-height:30px;text-align:center;padding:0}ul.blogTagCloud .tagCount10{font-size:26pt}ul.blogTagCloud .tagCount9{font-size:24pt}ul.blogTagCloud .tagCount8{font-size:22pt}ul.blogTagCloud .tagCount7{font-size:20pt}ul.blogTagCloud .tagCount6{font-size:18pt}ul.blogTagCloud .tagCount5{font-size:16pt}ul.blogTagCloud .tagCount4{font-size:14pt}ul.blogTagCloud .tagCount3{font-size:12pt}ul.blogTagCloud .tagCount2{font-size:10pt}ul.blogTagCloud .tagCount1{font-size:8pt}#FeaturedImage .middleColumn{clear:none;float:left}.has-panel .cms-content-tools.blog-admin-sidebar{width:280px;border-right:0;border-left:1px solid #c0c0c2;position:absolute!important;right:0;top:0;height:100%}.has-panel .cms-content-tools.blog-admin-sidebar .cms-panel-toggle a{text-align:left;margin:0}.has-panel .cms-content-tools.blog-admin-sidebar .cms-panel-toggle.south{border-top:1px solid #aaa}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer{width:100%;padding-right:280px;position:absolute;height:100%;overflow-y:hidden;overflow-x:hidden;-webkit-box-sizing:border-box;box-sizing:border-box}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset{position:relative;overflow:auto;height:100%;width:100%}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title label{float:none}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title .middleColumn,.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title input{width:100%;max-width:100%;margin-left:0}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field+.field{margin-top:10px}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.urlsegment .preview{padding-top:0;line-height:25px}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.urlsegment .edit{float:right}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn>.date{width:60%}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn>.time{width:36%;float:right}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn .middleColumn,.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn input{width:100%}.has-panel .cms-content-tools.blog-admin-sidebar.collapsed~.blog-admin-outer{padding-right:41px}.has-panel .cms-content-tools.blog-admin-sidebar.collapsed~.blog-admin-outer #Root_Main{margin-right:15px}.has-panel .cms-content-tools.blog-admin-sidebar.cms-content-tools .cms-panel-content{width:auto}.toggle-description{display:inline-block;font-size:1.2rem;width:20px;height:20px;margin-top:1px;cursor:pointer}.middleColumn.toggle-description-correct-middle{margin-left:0;float:left;width:416px}.tab-content .field p.toggle-description-correct-right{display:inline-block;margin-left:0;padding-left:0;clear:none;float:left}.description.toggle-description-correct-description{width:416px;padding:12px 0}.custom-summary .ui-accordion-content,.custom-summary .ui-accordion-content .field{padding:0}.custom-summary .ui-icon-triangle-1-e{background-position:-16px -128px}.cms table.ss-gridfield-table tr td.MergeAction{width:225px}.cms table.ss-gridfield-table tr td.MergeAction a{display:block;height:100%;width:100%}.cms table.ss-gridfield-table tr td.MergeAction select{width:150px}.blog-cms-categorisation .toolbar--content{margin-top:0}.blog-cms-categorisation .MergeActionReveal:after{content:"@";font-family:silverstripe;display:inline-block;position:relative;margin-left:10px;top:3px}.blog-cms-categorisation .blog-merge-action{margin-top:5px}
.no-sidebar .content-container.size3of4{width:75%}.blog-entry .post-image img{width:98.75%}.blog-sidebar .WidgetHolder ul{margin-left:0}.blog-sidebar .WidgetHolder ul li{list-style-type:none}ul.blogTagCloud{list-style-type:none;clear:both}ul.blogTagCloud li{float:left;display:inline;padding-right:8px}ul.blogTagCloud li a span{float:left;line-height:30px;text-align:center;padding:0}ul.blogTagCloud .tagCount10{font-size:26pt}ul.blogTagCloud .tagCount9{font-size:24pt}ul.blogTagCloud .tagCount8{font-size:22pt}ul.blogTagCloud .tagCount7{font-size:20pt}ul.blogTagCloud .tagCount6{font-size:18pt}ul.blogTagCloud .tagCount5{font-size:16pt}ul.blogTagCloud .tagCount4{font-size:14pt}ul.blogTagCloud .tagCount3{font-size:12pt}ul.blogTagCloud .tagCount2{font-size:10pt}ul.blogTagCloud .tagCount1{font-size:8pt}#FeaturedImage .middleColumn{clear:none;float:left}.has-panel .cms-content-tools.blog-admin-sidebar{width:280px;border-right:0;border-left:1px solid #c0c0c2;position:absolute !important;right:0;top:0;height:100%}.has-panel .cms-content-tools.blog-admin-sidebar .cms-panel-toggle a{text-align:left;margin:0}.has-panel .cms-content-tools.blog-admin-sidebar .cms-panel-toggle.south{border-top:1px solid #aaa}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer{width:100%;padding-right:280px;position:absolute;height:100%;overflow-y:hidden;overflow-x:hidden;box-sizing:border-box}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset{position:relative;overflow:auto;height:100%;width:100%}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title label{float:none}.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title .middleColumn,.has-panel .cms-content-tools.blog-admin-sidebar~.blog-admin-outer>.ss-tabset #Title input{width:100%;max-width:100%;margin-left:0}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field+.field{margin-top:10px}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.urlsegment .preview{padding-top:0;line-height:25px}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.urlsegment .edit{float:right}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn>.date{width:60%}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn>.time{width:36%;float:right}.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn .middleColumn,.has-panel .cms-content-tools.blog-admin-sidebar .cms-content-view>.field.datetime>.middleColumn input{width:100%}.has-panel .cms-content-tools.blog-admin-sidebar.collapsed~.blog-admin-outer{padding-right:41px}.has-panel .cms-content-tools.blog-admin-sidebar.collapsed~.blog-admin-outer #Root_Main{margin-right:15px}.has-panel .cms-content-tools.blog-admin-sidebar.cms-content-tools .cms-panel-content{width:auto}.toggle-description{display:inline-block;font-size:1.2rem;width:20px;height:20px;margin-top:1px;cursor:pointer}.middleColumn.toggle-description-correct-middle{margin-left:0;float:left;width:416px}.tab-content .field p.toggle-description-correct-right{display:inline-block;margin-left:0;padding-left:0;clear:none;float:left}.description.toggle-description-correct-description{width:416px;padding:12px 0}.custom-summary .ui-accordion-content,.custom-summary .ui-accordion-content .field{padding:0}.custom-summary .ui-icon-triangle-1-e{background-position:-16px -128px}.cms table.ss-gridfield-table tr td.MergeAction{width:225px}.cms table.ss-gridfield-table tr td.MergeAction a{display:block;height:100%;width:100%}.cms table.ss-gridfield-table tr td.MergeAction select{width:150px}.blog-cms-categorisation .toolbar--content{margin-top:0}.blog-cms-categorisation .MergeActionReveal:after{content:"@";font-family:silverstripe;display:inline-block;position:relative;margin-left:10px;top:3px}.blog-cms-categorisation .blog-merge-action{margin-top:5px}

View File

@ -2,141 +2,141 @@
import jQuery from 'jquery';
jQuery.entwine('ss', ($) => {
/**
/**
* The page success/error message sits outside of the html block
* containing the sidebar and cms fields. This means it overflows
* underneath the sidebar.
*
* @see https://github.com/silverstripe/silverstripe-blog/issues/210
*/
$('.cms-content-fields > #Form_EditForm_error').entwine({
onadd() {
const $target = $('.blog-admin-outer');
if ($target.length === 1) {
$target.prepend(this);
}
}
});
$('.cms-content-fields > #Form_EditForm_error').entwine({
onadd() {
const $target = $('.blog-admin-outer');
if ($target.length === 1) {
$target.prepend(this);
}
}
});
/**
/**
* Register expandable help text functions with fields.
*/
$('.toggle-description').entwine({
onadd() {
const $this = $(this);
$('.toggle-description').entwine({
onadd() {
const $this = $(this);
/**
/**
* Prevent multiple events being added.
*/
if ($this.hasClass('toggle-description-enabled')) {
return;
}
if ($this.hasClass('toggle-description-enabled')) {
return;
}
$this.addClass('toggle-description-enabled');
$this.addClass('toggle-description-enabled');
/**
/**
* Toggle next description when button is clicked.
*/
let shown = false;
const $helpInfo = $this.closest('.field').find('.form-text');
let shown = false;
const $helpInfo = $this.closest('.field').find('.form-text');
$this.on('click', () => {
$helpInfo[shown ? 'hide' : 'show']();
$this.toggleClass('toggle-description-shown');
shown = !shown;
});
$this.on('click', () => {
$helpInfo[shown ? 'hide' : 'show']();
$this.toggleClass('toggle-description-shown');
shown = !shown;
});
/**
/**
* Hide next description by default.
*/
$helpInfo.hide();
$helpInfo.hide();
/**
/**
* Add classes to correct inherited layout issues in a small context.
*/
$this.parent().addClass('toggle-description-correct-right');
$this.parent().prev('.middleColumn').addClass('toggle-description-correct-middle');
$this.parent().next('.description').addClass('toggle-description-correct-description');
}
});
$this.parent().addClass('toggle-description-correct-right');
$this.parent().prev('.middleColumn').addClass('toggle-description-correct-middle');
$this.parent().next('.description').addClass('toggle-description-correct-description');
}
});
/**
/**
* Custom merge actions for tags and categories
*/
$('.MergeAction').entwine({
onadd() {
const $this = $(this);
$('.MergeAction').entwine({
onadd() {
const $this = $(this);
$this.on('click', 'select', () => false);
$this.on('click', 'select', () => false);
$this.children('button').each((i, button) => {
const $button = $(button);
const $select = $button.prev('select');
$this.children('button').each((i, button) => {
const $button = $(button);
const $select = $button.prev('select');
$button.before(`<input type="hidden" name="${$button.attr('data-target')}" value="${$select.val()}" />`);
});
$button.before(`<input type="hidden" name="${$button.attr('data-target')}" value="${$select.val()}" />`);
});
$this.on('change', 'select', (e) => {
const $target = $(e.target);
$this.on('change', 'select', (e) => {
const $target = $(e.target);
$target.next('input').val($target.val());
});
$target.next('input').val($target.val());
});
$this.children('button, select').hide();
$this.children('button, select').hide();
$this.on('click', '.MergeActionReveal', (e) => {
const $target = $(e.target);
$this.on('click', '.MergeActionReveal', (e) => {
const $target = $(e.target);
$target.parent().children('button, select').show();
$target.hide();
$target.parent().children('button, select').show();
$target.hide();
return false;
});
}
});
return false;
});
}
});
/**
/**
* Customise the cms-panel behaviour for blog sidebar
*
* see LeftAndMain.Panel.js for base behaviour
*/
$('.blog-admin-sidebar.cms-panel').entwine({
MinInnerWidth: 620,
onadd() {
this._super();
this.updateLayout();
$('.blog-admin-sidebar.cms-panel').entwine({
MinInnerWidth: 620,
onadd() {
this._super();
this.updateLayout();
// Contract panel if it's open and the left hand column is smaller than the minimum
if (!this.hasClass('collapsed') && ($('.blog-admin-outer').width() < this.getMinInnerWidth())) {
this.collapsePanel();
}
// Contract panel if it's open and the left hand column is smaller than the minimum
if (!this.hasClass('collapsed') && ($('.blog-admin-outer').width() < this.getMinInnerWidth())) {
this.collapsePanel();
}
const onresize = () => {
this.updateLayout();
};
onresize.bind(this);
const onresize = () => {
this.updateLayout();
};
onresize.bind(this);
window.onresize = onresize;
},
togglePanel(bool, silent) {
this._super(bool, silent);
this.updateLayout();
},
/**
window.onresize = onresize;
},
togglePanel(bool, silent) {
this._super(bool, silent);
this.updateLayout();
},
/**
* Adjust minimum width of content to account for extra panel
*
* @returns {undefined}
*/
updateLayout() {
$(this).css('height', '100%');
const currentHeight = $(this).outerHeight();
const bottomHeight = $('.cms-content-actions').eq(0).outerHeight();
$(this).css('height', `${currentHeight - bottomHeight}px`);
$(this).css('bottom', `${bottomHeight}px`);
updateLayout() {
$(this).css('height', '100%');
const currentHeight = $(this).outerHeight();
const bottomHeight = $('.cms-content-actions').eq(0).outerHeight();
$(this).css('height', `${currentHeight - bottomHeight}px`);
$(this).css('bottom', `${bottomHeight}px`);
$('.cms-container').updateLayoutOptions({
minContentWidth: 820 + this.width()
});
}
});
$('.cms-container').updateLayoutOptions({
minContentWidth: 820 + this.width()
});
}
});
});

View File

@ -1,16 +1,16 @@
import jQuery from 'jquery';
jQuery.entwine('ss', ($) => {
/**
/**
* Prevent the CMS hijacking the return key
*/
$('.add-existing-autocompleter input.text').entwine({
onkeydown(e) {
if (e.which === 13) {
const $parent = $(this).parents('.add-existing-autocompleter');
$parent.find('button[type="submit"]').click();
e.preventDefault();
}
}
});
$('.add-existing-autocompleter input.text').entwine({
onkeydown(e) {
if (e.which === 13) {
const $parent = $(this).parents('.add-existing-autocompleter');
$parent.find('button[type="submit"]').click();
e.preventDefault();
}
}
});
});

View File

@ -8,19 +8,19 @@
],
"type": "silverstripe-vendormodule",
"require": {
"php": "^7.4 || ^8.0",
"silverstripe/cms": "^4.0",
"silverstripe/lumberjack": "^2.0",
"silverstripe/tagfield": "^2.0",
"silverstripe/assets": "^1.0",
"silverstripe/asset-admin": "^1.0"
"php": "^8.1",
"silverstripe/cms": "^5",
"silverstripe/lumberjack": "^3.0",
"silverstripe/tagfield": "^3.0",
"silverstripe/assets": "^2.0",
"silverstripe/asset-admin": "^2.0"
},
"require-dev": {
"silverstripe/recipe-testing": "^2",
"squizlabs/php_codesniffer": "^3.0",
"silverstripe/widgets": "^2",
"silverstripe/comments": "^3.7",
"silverstripe/content-widget": "^2"
"silverstripe/recipe-testing": "^3",
"squizlabs/php_codesniffer": "^3",
"silverstripe/widgets": "^3",
"silverstripe/comments": "^4",
"silverstripe/content-widget": "^3"
},
"extra": {
"expose": [

View File

@ -8,7 +8,7 @@ en:
Add: 'Add {name}'
AddFail: 'Unable to save {class} to the database.'
ButtonName: '{name}'
PermissionFail: 'You don''t have permission to create a {class}.'
PermissionFail: "You don't have permission to create a {class}."
SilverStripe\Blog\Forms\GridField\GridFieldBlogPostState:
Draft: 'Saved as Draft on {date}'
Modified: Modified
@ -47,7 +47,7 @@ en:
PostedIn: 'Posted in'
PostsByUser: 'Posts by {firstname} {surname} for {title}'
PostsPerPage: 'Posts Per Page'
ReadMoreAbout: 'Read more about ''{title}''...'
ReadMoreAbout: "Read more about '{title}'..."
SINGULARNAME: Blog
Tag: Tag
Tagged: Tagged
@ -85,7 +85,7 @@ en:
SilverStripe\Blog\Model\BlogPost:
AUTHOR: Author
AdditionalCredits: 'Additional Credits'
AdditionalCredits_Description: 'If some authors of this post don''t have CMS access, enter their name(s) here. You can separate multiple names with a comma.'
AdditionalCredits_Description: "If some authors of this post don't have CMS access, enter their name(s) here. You can separate multiple names with a comma."
Authors: Authors
CUSTOMSUMMARY: 'Add A Custom Summary'
Categories: Categories

View File

@ -1,9 +1,8 @@
{
"name": "silverstripe-blog",
"version": "3.0.0",
"description": "A fresh take on blogging in Silverstripe set out to tackle the issue of a cluttered Site Tree",
"scripts": {
"build": "yarn && yarn lint && NODE_ENV=production webpack -p --bail --progress",
"build": "yarn && yarn lint && rm -rf client/dist/* && NODE_ENV=production webpack --mode production --bail --progress",
"dev": "NODE_ENV=development webpack --progress",
"watch": "NODE_ENV=development webpack --watch --progress",
"css": "WEBPACK_CHILD=css npm run build",
@ -28,11 +27,16 @@
},
"homepage": "https://github.com/silverstripe/silverstripe-blog#readme",
"dependencies": {},
"peerDependencies": {
"jquery": "^3"
},
"devDependencies": {
"@silverstripe/eslint-config": "^0.0.5",
"@silverstripe/webpack-config": "^1.3"
}
"@silverstripe/eslint-config": "^1.1.0",
"@silverstripe/webpack-config": "^2.0.0",
"webpack": "^5.74.0",
"webpack-cli": "^5.0.0"
},
"resolutions": {
"colors": "1.4.0"
},
"browserslist": [
"defaults"
]
}

View File

@ -226,7 +226,6 @@ class GridFieldAddByDBField implements GridField_ActionProvider, GridField_HTMLP
'add',
'add'
);
$addAction->setAttribute('data-icon', 'add');
$addAction->addExtraClass('btn btn-primary');
$forTemplate = ArrayData::create([]);

View File

@ -31,11 +31,11 @@ use SilverStripe\View\Requirements;
/**
* Blog Holder
*
* @method HasManyList Tags() List of tags in this blog
* @method HasManyList Categories() List of categories in this blog
* @method ManyManyList Editors() List of editors
* @method ManyManyList Writers() List of writers
* @method ManyManyList Contributors() List of contributors
* @method HasManyList<BlogCategory> Categories()
* @method ManyManyList<Member> Contributors()
* @method ManyManyList<Member> Editors()
* @method HasManyList<BlogTag> Tags()
* @method ManyManyList<Member> Writers()
*/
class Blog extends Page implements PermissionProvider
{

View File

@ -8,11 +8,12 @@ use SilverStripe\ORM\DataObject;
* A blog category for generalising blog posts.
*
*
* @method Blog Blog()
*
* @property string $Title
* @property string $URLSegment
* @property int $BlogID
* @method Blog Blog()
* @method SilverStripe\ORM\ManyManyList<BlogPost> BlogPosts()
*/
class BlogCategory extends DataObject implements CategorisationObject
{

View File

@ -17,6 +17,8 @@ use SilverStripe\View\Requirements;
/**
* This class is responsible for add Blog specific behaviour to Members.
*
* @method SilverStripe\ORM\ManyManyList<BlogPost> BlogPosts()
* @method Image BlogProfileImage()
*/
class BlogMemberExtension extends DataExtension
{

View File

@ -31,17 +31,15 @@ use SilverStripe\View\Requirements;
/**
* An individual blog post.
*
* @method ManyManyList Categories()
* @method ManyManyList Tags()
* @method ManyManyList Authors()
* @method Blog Parent()
* @method Image FeaturedImage()
*
* @property string $PublishDate
* @property string $AuthorNames
* @property string $Summary
* @property int $ParentID
* @property int $FeaturedImageID
* @method ManyManyList<Member> Authors()
* @method ManyManyList<BlogCategory> Categories()
* @method Image FeaturedImage()
* @method ManyManyList<BlogTag> Tags()
*/
class BlogPost extends Page
{
@ -334,8 +332,6 @@ class BlogPost extends Page
? $parent->Tags()
: BlogTag::get();
// @todo: Reimplement the sidebar
// $options = BlogAdminSidebar::create(
$fields->addFieldsToTab(
'Root.PostOptions',
[
@ -360,9 +356,6 @@ class BlogPost extends Page
$authorNames
]
);
// )->setTitle('Post Options');
// $options->setName('blog-admin-sidebar');
// $fields->insertBefore($options, 'Root');
$fields->fieldByName('Root.PostOptions')
->setTitle(_t(__CLASS__ . '.PostOptions', 'Post Options'));

View File

@ -7,12 +7,11 @@ use SilverStripe\ORM\DataObject;
/**
* A blog tag for keyword descriptions of a blog post.
*
*
* @method Blog Blog()
*
* @property string $Title
* @property string $URLSegment
* @property int $BlogID
* @method Blog Blog()
* @method SilverStripe\ORM\ManyManyList<BlogPost> BlogPosts()
*/
class BlogTag extends DataObject implements CategorisationObject
{

View File

@ -84,7 +84,7 @@ class BlogFeaturedPostsWidget extends Widget
return $blog->getBlogPosts()
->filter('ID:not', Director::get_current_page()->ID)
->filter('FeaturedInWidget', true)
->sort('RAND()')
->shuffle()
->limit($this->NumberOfPosts);
}

View File

@ -9,6 +9,7 @@ use SilverStripe\ORM\ArrayList;
use SilverStripe\ORM\DataObject;
use SilverStripe\ORM\DB;
use SilverStripe\Widgets\Model\Widget;
use SilverStripe\Control\Controller;
if (!class_exists(Widget::class)) {
return;
@ -98,7 +99,7 @@ class BlogTagsCloudWidget extends Widget
foreach ($records as $record) {
$tag = DataObject::create();
$tag->TagName = $record['Title'];
$link = $bloglink.'tag/'.$record['URLSegment'];
$link = Controller::join_links($bloglink, 'tag', $record['URLSegment']);
$tag->Link = $link;
if ($record['TagCount'] > $maxTagCount) {
$maxTagCount = $record['TagCount'];

View File

@ -47,7 +47,7 @@ Feature: Create a blog
And I press the "Log in as someone else" button
Scenario: Create a blog post
Given I am logged in as a member of "EDITOR" group
# Create a new blog post called "New Post"
When I go to "/admin/pages"
@ -65,8 +65,8 @@ Feature: Create a blog
# Add categories and tags
And I click the "Post Options" CMS tab
And I add "My Category" to the "Categories" tag field
And I add "My Tag" to the "Tags" tag field
And I add "My Category" to the "#Form_EditForm_Categories_Holder" tag field
And I add "My Tag" to the "#Form_EditForm_Tags_Holder" tag field
# Publish the blog post and logout
And I press the "Publish" button

View File

@ -11,8 +11,6 @@ class BlogFunctionalTest extends FunctionalTest
{
protected static $fixture_file = 'BlogFunctionalTest.yml';
protected static $use_draft_site = true;
protected function setUp(): void
{
Config::modify()->set(URLSegmentFilter::class, 'default_allow_multibyte', true);
@ -23,14 +21,16 @@ class BlogFunctionalTest extends FunctionalTest
public function testBlogWithMultibyteUrl()
{
$result = $this->get(rawurlencode('آبید'));
$this->logInWithPermission('VIEW_DRAFT_CONTENT');
$result = $this->get(rawurlencode('آبید') . '?stage=Stage');
$this->assertEquals(200, $result->getStatusCode());
}
public function testMemberProfileWithMultibyteUrlAndName()
{
$result = $this->get(rawurlencode('آبید') . '/profile/' . rawurlencode('عبّاس-آبان'));
$this->logInWithPermission('VIEW_DRAFT_CONTENT');
$result = $this->get(rawurlencode('آبید') . '/profile/' . rawurlencode('عبّاس-آبان') . '?stage=Stage');
$this->assertEquals(200, $result->getStatusCode());
$this->assertStringContainsString('My Blog Post', $result->getBody());
@ -38,7 +38,8 @@ class BlogFunctionalTest extends FunctionalTest
public function testMemberProfileWithMultibyteUrlAndEnglishName()
{
$result = $this->get(rawurlencode('آبید') . '/profile/bob-jones');
$this->logInWithPermission('VIEW_DRAFT_CONTENT');
$result = $this->get(rawurlencode('آبید') . '/profile/bob-jones' . '?stage=Stage');
$this->assertEquals(200, $result->getStatusCode());
$this->assertStringContainsString('My Blog Post', $result->getBody());

View File

@ -11,8 +11,6 @@ class BlogControllerFunctionalTest extends FunctionalTest
{
protected static $fixture_file = 'BlogControllerFunctionalTest.yml';
protected static $use_draft_site = true;
protected function setUp(): void
{
Config::modify()->set(URLSegmentFilter::class, 'default_allow_multibyte', true);
@ -23,7 +21,8 @@ class BlogControllerFunctionalTest extends FunctionalTest
public function testGetCategoriesWithMultibyteUrl()
{
$result = $this->get('my-blog/category/' . rawurlencode('آبید'));
$this->logInWithPermission('VIEW_DRAFT_CONTENT');
$result = $this->get('my-blog/category/' . rawurlencode('آبید') . '?stage=Stage');
$this->assertEquals(200, $result->getStatusCode());
$this->assertStringContainsString('آبید', $result->getBody());
@ -31,7 +30,8 @@ class BlogControllerFunctionalTest extends FunctionalTest
public function testGetTagsWithMultibyteUrl()
{
$result = $this->get('my-blog/tag/' . rawurlencode('برتراند'));
$this->logInWithPermission('VIEW_DRAFT_CONTENT');
$result = $this->get('my-blog/tag/' . rawurlencode('برتراند') . '?stage=Stage');
$this->assertEquals(200, $result->getStatusCode());
$this->assertStringContainsString('برتراند', $result->getBody());

View File

@ -1,55 +1,31 @@
const Path = require('path');
const webpack = require('webpack');
// Import the core config
const webpackConfig = require('@silverstripe/webpack-config');
const {
resolveJS,
externalJS,
moduleJS,
pluginJS,
moduleCSS,
pluginCSS,
} = webpackConfig;
const { JavascriptWebpackConfig, CssWebpackConfig } = require('@silverstripe/webpack-config');
const ENV = process.env.NODE_ENV;
const PATHS = {
ROOT: Path.resolve(),
MODULES: 'node_modules',
FILES_PATH: '../',
THIRDPARTY: 'thirdparty',
SRC: Path.resolve('client/src'),
DIST: Path.resolve('client/dist'),
};
const config = [
{
name: 'bundle',
entry: {
main: `${PATHS.SRC}/main.js`
},
output: {
path: PATHS.DIST,
filename: 'js/[name].bundle.js',
},
devtool: (ENV !== 'production') ? 'source-map' : '',
resolve: resolveJS(ENV, PATHS),
externals: externalJS(ENV, PATHS),
module: moduleJS(ENV, PATHS),
plugins: pluginJS(ENV, PATHS),
},
{
name: 'bundle',
entry: {
main: `${PATHS.SRC}/main.scss`
},
output: {
path: PATHS.DIST,
filename: 'styles/[name].css'
},
devtool: (ENV !== 'production') ? 'source-map' : '',
module: moduleCSS(ENV, PATHS),
plugins: pluginCSS(ENV, PATHS),
},
// Main JS bundle
new JavascriptWebpackConfig('js', PATHS, 'silverstripe/blog')
.setEntry({
main: `${PATHS.SRC}/main.js`
})
.mergeConfig({
output: {
filename: 'js/[name].bundle.js',
},
})
.getConfig(),
// sass to css
new CssWebpackConfig('css', PATHS)
.setEntry({
main: `${PATHS.SRC}/main.scss`
})
.getConfig(),
];
module.exports = config;

11137
yarn.lock

File diff suppressed because it is too large Load Diff