panda-cms 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/README.md +73 -0
- data/Rakefile +7 -0
- data/app/assets/builds/panda.cms.css +2808 -0
- data/app/assets/config/panda_cms_manifest.js +4 -0
- data/app/assets/stylesheets/panda/cms/application.tailwind.css +162 -0
- data/app/assets/stylesheets/panda/cms/editor.css +120 -0
- data/app/builders/panda/cms/form_builder.rb +234 -0
- data/app/components/panda/cms/admin/button_component.rb +70 -0
- data/app/components/panda/cms/admin/container_component.html.erb +13 -0
- data/app/components/panda/cms/admin/container_component.rb +13 -0
- data/app/components/panda/cms/admin/flash_message_component.html.erb +31 -0
- data/app/components/panda/cms/admin/flash_message_component.rb +47 -0
- data/app/components/panda/cms/admin/heading_component.rb +45 -0
- data/app/components/panda/cms/admin/panel_component.html.erb +7 -0
- data/app/components/panda/cms/admin/panel_component.rb +13 -0
- data/app/components/panda/cms/admin/slideover_component.html.erb +9 -0
- data/app/components/panda/cms/admin/slideover_component.rb +15 -0
- data/app/components/panda/cms/admin/statistics_component.html.erb +4 -0
- data/app/components/panda/cms/admin/statistics_component.rb +17 -0
- data/app/components/panda/cms/admin/tab_bar_component.html.erb +35 -0
- data/app/components/panda/cms/admin/tab_bar_component.rb +15 -0
- data/app/components/panda/cms/admin/table_component.html.erb +29 -0
- data/app/components/panda/cms/admin/table_component.rb +46 -0
- data/app/components/panda/cms/admin/tag_component.rb +35 -0
- data/app/components/panda/cms/admin/user_activity_component.html.erb +5 -0
- data/app/components/panda/cms/admin/user_activity_component.rb +33 -0
- data/app/components/panda/cms/admin/user_display_component.html.erb +17 -0
- data/app/components/panda/cms/admin/user_display_component.rb +21 -0
- data/app/components/panda/cms/code_component.rb +64 -0
- data/app/components/panda/cms/grid_component.html.erb +6 -0
- data/app/components/panda/cms/grid_component.rb +15 -0
- data/app/components/panda/cms/menu_component.html.erb +6 -0
- data/app/components/panda/cms/menu_component.rb +58 -0
- data/app/components/panda/cms/page_menu_component.html.erb +21 -0
- data/app/components/panda/cms/page_menu_component.rb +38 -0
- data/app/components/panda/cms/rich_text_component.html.erb +6 -0
- data/app/components/panda/cms/rich_text_component.rb +84 -0
- data/app/components/panda/cms/text_component.rb +72 -0
- data/app/constraints/panda/cms/admin_constraint.rb +18 -0
- data/app/controllers/panda/cms/admin/block_contents_controller.rb +52 -0
- data/app/controllers/panda/cms/admin/dashboard_controller.rb +20 -0
- data/app/controllers/panda/cms/admin/files_controller.rb +21 -0
- data/app/controllers/panda/cms/admin/forms_controller.rb +53 -0
- data/app/controllers/panda/cms/admin/menus_controller.rb +30 -0
- data/app/controllers/panda/cms/admin/pages_controller.rb +91 -0
- data/app/controllers/panda/cms/admin/posts_controller.rb +146 -0
- data/app/controllers/panda/cms/admin/sessions_controller.rb +94 -0
- data/app/controllers/panda/cms/admin/settings/bulk_editor_controller.rb +37 -0
- data/app/controllers/panda/cms/admin/settings_controller.rb +20 -0
- data/app/controllers/panda/cms/application_controller.rb +57 -0
- data/app/controllers/panda/cms/errors_controller.rb +33 -0
- data/app/controllers/panda/cms/form_submissions_controller.rb +23 -0
- data/app/controllers/panda/cms/pages_controller.rb +72 -0
- data/app/controllers/panda/cms/posts_controller.rb +13 -0
- data/app/helpers/panda/cms/admin/files_helper.rb +6 -0
- data/app/helpers/panda/cms/admin/pages_helper.rb +6 -0
- data/app/helpers/panda/cms/admin/posts_helper.rb +48 -0
- data/app/helpers/panda/cms/application_helper.rb +120 -0
- data/app/helpers/panda/cms/pages_helper.rb +6 -0
- data/app/helpers/panda/cms/theme_helper.rb +18 -0
- data/app/javascript/panda/cms/@editorjs--editorjs.js +2577 -0
- data/app/javascript/panda/cms/@hotwired--stimulus.js +4 -0
- data/app/javascript/panda/cms/@hotwired--turbo.js +160 -0
- data/app/javascript/panda/cms/@rails--actioncable--src.js +4 -0
- data/app/javascript/panda/cms/application_panda_cms.js +39 -0
- data/app/javascript/panda/cms/controllers/dashboard_controller.js +7 -0
- data/app/javascript/panda/cms/controllers/editor_form_controller.js +77 -0
- data/app/javascript/panda/cms/controllers/editor_iframe_controller.js +320 -0
- data/app/javascript/panda/cms/controllers/index.js +48 -0
- data/app/javascript/panda/cms/controllers/slug_controller.js +87 -0
- data/app/javascript/panda/cms/editor/css_extractor.js +80 -0
- data/app/javascript/panda/cms/editor/editor_js_config.js +177 -0
- data/app/javascript/panda/cms/editor/editor_js_initializer.js +285 -0
- data/app/javascript/panda/cms/editor/plain_text_editor.js +110 -0
- data/app/javascript/panda/cms/editor/resource_loader.js +115 -0
- data/app/javascript/panda/cms/tailwindcss-stimulus-components.js +4 -0
- data/app/jobs/panda/cms/application_job.rb +6 -0
- data/app/jobs/panda/cms/record_visit_job.rb +31 -0
- data/app/mailers/panda/cms/application_mailer.rb +8 -0
- data/app/mailers/panda/cms/form_mailer.rb +21 -0
- data/app/models/action_text/rich_text_version.rb +6 -0
- data/app/models/panda/cms/application_record.rb +7 -0
- data/app/models/panda/cms/block.rb +34 -0
- data/app/models/panda/cms/block_content.rb +18 -0
- data/app/models/panda/cms/block_content_version.rb +8 -0
- data/app/models/panda/cms/breadcrumb.rb +12 -0
- data/app/models/panda/cms/current.rb +17 -0
- data/app/models/panda/cms/form.rb +9 -0
- data/app/models/panda/cms/form_submission.rb +7 -0
- data/app/models/panda/cms/menu.rb +52 -0
- data/app/models/panda/cms/menu_item.rb +58 -0
- data/app/models/panda/cms/page.rb +96 -0
- data/app/models/panda/cms/page_version.rb +8 -0
- data/app/models/panda/cms/post.rb +60 -0
- data/app/models/panda/cms/post_version.rb +8 -0
- data/app/models/panda/cms/redirect.rb +11 -0
- data/app/models/panda/cms/template.rb +124 -0
- data/app/models/panda/cms/template_version.rb +8 -0
- data/app/models/panda/cms/user.rb +31 -0
- data/app/models/panda/cms/version.rb +8 -0
- data/app/models/panda/cms/visit.rb +9 -0
- data/app/services/panda/cms/html_to_editor_js_converter.rb +200 -0
- data/app/views/active_storage/blobs/blobs/_blob.html.erb +14 -0
- data/app/views/layouts/action_text/contents/_content.html.erb +3 -0
- data/app/views/layouts/panda/cms/application.html.erb +41 -0
- data/app/views/layouts/panda/cms/public.html.erb +3 -0
- data/app/views/panda/cms/admin/dashboard/show.html.erb +12 -0
- data/app/views/panda/cms/admin/files/index.html.erb +124 -0
- data/app/views/panda/cms/admin/files/show.html.erb +2 -0
- data/app/views/panda/cms/admin/forms/edit.html.erb +0 -0
- data/app/views/panda/cms/admin/forms/index.html.erb +13 -0
- data/app/views/panda/cms/admin/forms/new.html.erb +15 -0
- data/app/views/panda/cms/admin/forms/show.html.erb +35 -0
- data/app/views/panda/cms/admin/menus/index.html.erb +8 -0
- data/app/views/panda/cms/admin/pages/edit.html.erb +36 -0
- data/app/views/panda/cms/admin/pages/index.html.erb +22 -0
- data/app/views/panda/cms/admin/pages/new.html.erb +15 -0
- data/app/views/panda/cms/admin/pages/show.html.erb +1 -0
- data/app/views/panda/cms/admin/posts/_form.html.erb +29 -0
- data/app/views/panda/cms/admin/posts/edit.html.erb +6 -0
- data/app/views/panda/cms/admin/posts/index.html.erb +18 -0
- data/app/views/panda/cms/admin/posts/new.html.erb +6 -0
- data/app/views/panda/cms/admin/sessions/new.html.erb +17 -0
- data/app/views/panda/cms/admin/settings/bulk_editor/new.html.erb +68 -0
- data/app/views/panda/cms/admin/settings/index.html.erb +21 -0
- data/app/views/panda/cms/admin/settings/insta.html +4 -0
- data/app/views/panda/cms/admin/shared/_breadcrumbs.html.erb +28 -0
- data/app/views/panda/cms/admin/shared/_flash.html.erb +5 -0
- data/app/views/panda/cms/admin/shared/_sidebar.html.erb +41 -0
- data/app/views/panda/cms/form_mailer/notification_email.html.erb +11 -0
- data/app/views/panda/cms/shared/_editor.html.erb +0 -0
- data/app/views/panda/cms/shared/_favicons.html.erb +9 -0
- data/app/views/panda/cms/shared/_footer.html.erb +2 -0
- data/app/views/panda/cms/shared/_header.html.erb +15 -0
- data/app/views/panda/cms/shared/_importmap.html.erb +33 -0
- data/config/importmap.rb +13 -0
- data/config/initializers/inflections.rb +3 -0
- data/config/initializers/panda/cms/form_errors.rb +38 -0
- data/config/initializers/panda/cms/healthcheck_log_silencer.rb +11 -0
- data/config/initializers/panda/cms/paper_trail.rb +7 -0
- data/config/initializers/panda/cms.rb +10 -0
- data/config/initializers/zeitwork.rb +3 -0
- data/config/locales/en.yml +49 -0
- data/config/puma/test.rb +9 -0
- data/config/routes.rb +48 -0
- data/config/tailwind.config.js +37 -0
- data/db/migrate/20240205223709_create_panda_cms_pages.rb +9 -0
- data/db/migrate/20240219213327_create_panda_cms_page_versions.rb +14 -0
- data/db/migrate/20240303002805_create_panda_cms_templates.rb +11 -0
- data/db/migrate/20240303003434_create_panda_cms_template_versions.rb +14 -0
- data/db/migrate/20240303022441_create_panda_cms_blocks.rb +13 -0
- data/db/migrate/20240303024256_create_panda_cms_block_contents.rb +10 -0
- data/db/migrate/20240303024746_create_panda_cms_block_content_versions.rb +14 -0
- data/db/migrate/20240303233238_add_panda_cms_menu_table.rb +10 -0
- data/db/migrate/20240303234724_add_panda_cms_menu_item_table.rb +12 -0
- data/db/migrate/20240304134343_add_parent_id_to_panda_cms_pages.rb +5 -0
- data/db/migrate/20240305000000_convert_html_content_to_editor_js.rb +82 -0
- data/db/migrate/20240315125411_add_status_to_panda_cms_pages.rb +9 -0
- data/db/migrate/20240315125421_add_nested_sets_to_panda_cms_pages.rb +16 -0
- data/db/migrate/20240316212822_add_kind_to_panda_cms_menus.rb +6 -0
- data/db/migrate/20240316221425_add_start_page_to_panda_cms_menus.rb +5 -0
- data/db/migrate/20240316230706_add_nested_to_panda_cms_menu_items.rb +24 -0
- data/db/migrate/20240317010532_create_panda_cms_users.rb +12 -0
- data/db/migrate/20240317161534_add_max_uses_to_panda_cms_template.rb +7 -0
- data/db/migrate/20240317163053_reset_counter_cache_on_panda_cms_template.rb +5 -0
- data/db/migrate/20240317214827_create_panda_cms_redirects.rb +14 -0
- data/db/migrate/20240317230622_create_panda_cms_visits.rb +13 -0
- data/db/migrate/20240324205703_create_active_storage_tables.active_storage.rb +58 -0
- data/db/migrate/20240408084718_default_panda_cms_users_admin_to_false.rb +5 -0
- data/db/migrate/20240701225422_add_service_name_to_active_storage_blobs.active_storage.rb +22 -0
- data/db/migrate/20240701225423_create_active_storage_variant_records.active_storage.rb +28 -0
- data/db/migrate/20240701225424_remove_not_null_on_active_storage_blobs_checksum.active_storage.rb +8 -0
- data/db/migrate/20240804235210_create_panda_cms_forms.rb +11 -0
- data/db/migrate/20240805013612_create_panda_cms_form_submissions.rb +9 -0
- data/db/migrate/20240805121123_create_panda_cms_posts.rb +27 -0
- data/db/migrate/20240805123104_create_panda_cms_post_versions.rb +14 -0
- data/db/migrate/20240806112735_fix_panda_cms_visits_column_names.rb +13 -0
- data/db/migrate/20240806204412_add_completion_path_to_panda_cms_forms.rb +5 -0
- data/db/migrate/20240820081917_change_form_submissions_to_submission_count.rb +5 -0
- data/db/migrate/20240904200605_create_action_text_tables.action_text.rb +24 -0
- data/db/migrate/20240923234535_add_depth_to_panda_cms_menus.rb +11 -0
- data/db/migrate/20241031205109_add_cached_content_to_panda_cms_block_contents.rb +5 -0
- data/db/migrate/20241119214548_convert_post_content_to_editor_js.rb +35 -0
- data/db/migrate/20241119214549_remove_action_text_from_posts.rb +9 -0
- data/db/migrate/20241120000419_remove_post_tag_references.rb +19 -0
- data/db/migrate/20241120110943_add_editor_js_to_posts.rb +27 -0
- data/db/migrate/20241120113859_add_cached_content_to_panda_cms_posts.rb +5 -0
- data/db/migrate/20241123234140_remove_post_tag_id_from_posts.rb +5 -0
- data/db/migrate/migrate +1 -0
- data/db/seeds.rb +5 -0
- data/lib/generators/panda/cms/install_generator.rb +29 -0
- data/lib/panda/cms/bulk_editor.rb +171 -0
- data/lib/panda/cms/demo_site_generator.rb +67 -0
- data/lib/panda/cms/editor_js/blocks/alert.rb +34 -0
- data/lib/panda/cms/editor_js/blocks/base.rb +33 -0
- data/lib/panda/cms/editor_js/blocks/header.rb +15 -0
- data/lib/panda/cms/editor_js/blocks/image.rb +36 -0
- data/lib/panda/cms/editor_js/blocks/list.rb +32 -0
- data/lib/panda/cms/editor_js/blocks/paragraph.rb +15 -0
- data/lib/panda/cms/editor_js/blocks/quote.rb +41 -0
- data/lib/panda/cms/editor_js/blocks/table.rb +50 -0
- data/lib/panda/cms/editor_js/renderer.rb +124 -0
- data/lib/panda/cms/editor_js.rb +16 -0
- data/lib/panda/cms/editor_js_content.rb +21 -0
- data/lib/panda/cms/engine.rb +257 -0
- data/lib/panda/cms/exceptions_app.rb +26 -0
- data/lib/panda/cms/railtie.rb +11 -0
- data/lib/panda/cms/slug.rb +24 -0
- data/lib/panda/cms.rb +0 -0
- data/lib/panda-cms/version.rb +5 -0
- data/lib/panda-cms.rb +81 -0
- data/lib/tasks/panda_cms.rake +54 -0
- data/lib/templates/erb/scaffold/_form.html.erb.tt +43 -0
- data/lib/templates/erb/scaffold/edit.html.erb.tt +8 -0
- data/lib/templates/erb/scaffold/index.html.erb.tt +14 -0
- data/lib/templates/erb/scaffold/new.html.erb.tt +7 -0
- data/lib/templates/erb/scaffold/partial.html.erb.tt +22 -0
- data/lib/templates/erb/scaffold/show.html.erb.tt +15 -0
- data/public/panda-cms-assets/favicons/android-chrome-192x192.png +0 -0
- data/public/panda-cms-assets/favicons/android-chrome-512x512.png +0 -0
- data/public/panda-cms-assets/favicons/apple-touch-icon.png +0 -0
- data/public/panda-cms-assets/favicons/browserconfig.xml +9 -0
- data/public/panda-cms-assets/favicons/favicon-16x16.png +0 -0
- data/public/panda-cms-assets/favicons/favicon-32x32.png +0 -0
- data/public/panda-cms-assets/favicons/favicon.ico +0 -0
- data/public/panda-cms-assets/favicons/mstile-150x150.png +0 -0
- data/public/panda-cms-assets/favicons/safari-pinned-tab.svg +61 -0
- data/public/panda-cms-assets/favicons/site.webmanifest +14 -0
- data/public/panda-cms-assets/panda-logo-screenprint.png +0 -0
- data/public/panda-cms-assets/panda-nav.png +0 -0
- data/public/panda-cms-assets/rich_text_editor.css +568 -0
- metadata +654 -0
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
class CreatePandaCMSBlocks < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_enum :panda_cms_block_kind, ["plain_text", "rich_text", "image", "video", "audio", "file", "code", "iframe", "quote", "list", "table", "form"]
|
|
4
|
+
|
|
5
|
+
create_table :panda_cms_blocks, id: :uuid do |t|
|
|
6
|
+
t.enum :kind, enum_type: :panda_cms_block_kind, default: "plain_text", null: false
|
|
7
|
+
t.string :name
|
|
8
|
+
t.string :key
|
|
9
|
+
t.references :panda_cms_template, type: :uuid, foreign_key: {to_table: :panda_cms_templates}, null: false
|
|
10
|
+
t.timestamps
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
class CreatePandaCMSBlockContents < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_block_contents, id: :uuid do |t|
|
|
4
|
+
t.references :panda_cms_page, null: false, foreign_key: true, type: :uuid
|
|
5
|
+
t.references :panda_cms_block, null: false, foreign_key: true, type: :uuid
|
|
6
|
+
t.jsonb :content, null: false, default: {}
|
|
7
|
+
t.timestamps
|
|
8
|
+
end
|
|
9
|
+
end
|
|
10
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
class CreatePandaCMSBlockContentVersions < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_block_content_versions, id: :uuid do |t|
|
|
4
|
+
t.string :item_type, null: false
|
|
5
|
+
t.string :item_id, null: false
|
|
6
|
+
t.string :event, null: false
|
|
7
|
+
t.string :whodunnit
|
|
8
|
+
t.jsonb :object
|
|
9
|
+
t.jsonb :object_changes
|
|
10
|
+
t.datetime :created_at
|
|
11
|
+
end
|
|
12
|
+
add_index :panda_cms_block_content_versions, %i[item_type item_id]
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
class AddPandaCMSMenuItemTable < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_menu_items, id: :uuid do |t|
|
|
4
|
+
t.string :text, null: false
|
|
5
|
+
t.references :panda_cms_menu, null: false, foreign_key: true, type: :uuid
|
|
6
|
+
t.references :panda_cms_page, null: true, foreign_key: true, type: :uuid
|
|
7
|
+
t.string :external_url, null: true
|
|
8
|
+
t.integer :sort_order, default: 1
|
|
9
|
+
t.timestamps
|
|
10
|
+
end
|
|
11
|
+
end
|
|
12
|
+
end
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
class ConvertHtmlContentToEditorJs < ActiveRecord::Migration[7.1]
|
|
4
|
+
def up
|
|
5
|
+
# First, let's ensure we have the converter available in the migration
|
|
6
|
+
require Panda::CMS::Engine.root.join("app/services/panda/cms/html_to_editor_js_converter")
|
|
7
|
+
|
|
8
|
+
# Check if we have any existing valid EditorJS content
|
|
9
|
+
existing_editor_js = Panda::CMS::BlockContent.find_each.any? do |block_content|
|
|
10
|
+
valid_editor_js_content?(block_content.content)
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
if existing_editor_js
|
|
14
|
+
Rails.logger.warn "Found existing valid EditorJS content. Skipping migration to prevent data loss."
|
|
15
|
+
return
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
Rails.logger.info "Starting conversion of HTML content to EditorJS format..."
|
|
19
|
+
|
|
20
|
+
# Get all block contents that need conversion
|
|
21
|
+
Panda::CMS::BlockContent.find_each do |block_content|
|
|
22
|
+
next if block_content.content.blank?
|
|
23
|
+
|
|
24
|
+
begin
|
|
25
|
+
Rails.logger.info "Converting content for BlockContent ##{block_content.id}"
|
|
26
|
+
|
|
27
|
+
# Convert the content
|
|
28
|
+
editor_js_content = Panda::CMS::HtmlToEditorJsConverter.convert(block_content.content)
|
|
29
|
+
|
|
30
|
+
# Validate the converted content
|
|
31
|
+
unless valid_editor_js_content?(editor_js_content)
|
|
32
|
+
Rails.logger.error "Skipping BlockContent ##{block_content.id}: Conversion resulted in invalid or empty content"
|
|
33
|
+
next
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
# Update the record directly to avoid callbacks
|
|
37
|
+
block_content.update_columns(
|
|
38
|
+
content: editor_js_content,
|
|
39
|
+
updated_at: Time.current
|
|
40
|
+
)
|
|
41
|
+
|
|
42
|
+
Rails.logger.info "Successfully converted BlockContent ##{block_content.id}"
|
|
43
|
+
rescue => e
|
|
44
|
+
Rails.logger.error "Failed to convert BlockContent ##{block_content.id}: #{e.message}"
|
|
45
|
+
# Continue with the next record instead of failing the entire migration
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
Rails.logger.info "Completed conversion to EditorJS format"
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def down
|
|
53
|
+
Rails.logger.warn "This migration cannot be reversed as it would require original HTML content"
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
private
|
|
57
|
+
|
|
58
|
+
def valid_editor_js_content?(content)
|
|
59
|
+
return false unless content.is_a?(Hash)
|
|
60
|
+
return false unless content["blocks"].is_a?(Array)
|
|
61
|
+
return false if content["blocks"].empty?
|
|
62
|
+
|
|
63
|
+
# Check if there are any non-empty blocks
|
|
64
|
+
content["blocks"].any? do |block|
|
|
65
|
+
next false unless block.is_a?(Hash)
|
|
66
|
+
next false unless block["data"].is_a?(Hash)
|
|
67
|
+
|
|
68
|
+
case block["type"]
|
|
69
|
+
when "paragraph"
|
|
70
|
+
block["data"]["text"].present?
|
|
71
|
+
when "header"
|
|
72
|
+
block["data"]["text"].present?
|
|
73
|
+
when "list"
|
|
74
|
+
block["data"]["items"].present? && block["data"]["items"].any?(&:present?)
|
|
75
|
+
when "quote"
|
|
76
|
+
block["data"]["text"].present?
|
|
77
|
+
else
|
|
78
|
+
false
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
end
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
class AddStatusToPandaCMSPages < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
unless column_exists?(:panda_cms_pages, :status)
|
|
4
|
+
create_enum :panda_cms_page_status, ["active", "draft", "hidden", "archived"]
|
|
5
|
+
add_column :panda_cms_pages, :status, :panda_cms_page_status, default: "active", null: false
|
|
6
|
+
add_index :panda_cms_pages, :status
|
|
7
|
+
end
|
|
8
|
+
end
|
|
9
|
+
end
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
class AddNestedSetsToPandaCMSPages < ActiveRecord::Migration[7.1]
|
|
2
|
+
def self.up
|
|
3
|
+
Panda::CMS::Page.where(parent_id: 0).update_all(parent_id: nil)
|
|
4
|
+
add_column :panda_cms_pages, :lft, :integer
|
|
5
|
+
add_column :panda_cms_pages, :rgt, :integer
|
|
6
|
+
|
|
7
|
+
# This is necessary to update :lft and :rgt columns
|
|
8
|
+
Panda::CMS::Page.reset_column_information
|
|
9
|
+
Panda::CMS::Page.rebuild!
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.down
|
|
13
|
+
remove_column :panda_cms_pages, :lft
|
|
14
|
+
remove_column :panda_cms_pages, :rgt
|
|
15
|
+
end
|
|
16
|
+
end
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
class AddNestedToPandaCMSMenuItems < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
add_column :panda_cms_menu_items, :parent_id, :uuid
|
|
4
|
+
add_column :panda_cms_menu_items, :lft, :integer
|
|
5
|
+
add_column :panda_cms_menu_items, :rgt, :integer
|
|
6
|
+
add_column :panda_cms_menu_items, :depth, :integer
|
|
7
|
+
add_column :panda_cms_menu_items, :children_count, :integer, null: false, default: 0
|
|
8
|
+
|
|
9
|
+
add_index :panda_cms_menu_items, :lft
|
|
10
|
+
add_index :panda_cms_menu_items, :rgt
|
|
11
|
+
|
|
12
|
+
Panda::CMS::MenuItem.reset_column_information
|
|
13
|
+
Panda::CMS::MenuItem.rebuild!
|
|
14
|
+
|
|
15
|
+
# Update pages whilst we're at it
|
|
16
|
+
add_column :panda_cms_pages, :depth, :integer
|
|
17
|
+
add_column :panda_cms_pages, :children_count, :integer, null: false, default: 0
|
|
18
|
+
add_index :panda_cms_pages, :lft
|
|
19
|
+
add_index :panda_cms_pages, :rgt
|
|
20
|
+
|
|
21
|
+
Panda::CMS::Page.reset_column_information
|
|
22
|
+
Panda::CMS::Page.rebuild!
|
|
23
|
+
end
|
|
24
|
+
end
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
class CreatePandaCMSUsers < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_users, id: :uuid do |t|
|
|
4
|
+
t.string :firstname
|
|
5
|
+
t.string :lastname
|
|
6
|
+
t.string :email
|
|
7
|
+
t.string :image_url
|
|
8
|
+
t.boolean :admin
|
|
9
|
+
t.timestamps
|
|
10
|
+
end
|
|
11
|
+
end
|
|
12
|
+
end
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
class AddMaxUsesToPandaCMSTemplate < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
add_column :panda_cms_templates, :max_uses, :integer, null: true, default: nil
|
|
4
|
+
add_column :panda_cms_templates, :pages_count, :integer, default: 0
|
|
5
|
+
Panda::CMS::Template.find_by(name: "Homepage")&.update(max_uses: 1)
|
|
6
|
+
end
|
|
7
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
class CreatePandaCMSRedirects < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_redirects, id: :uuid do |t|
|
|
4
|
+
t.string :origin_path, null: true
|
|
5
|
+
t.string :destination_path, null: true
|
|
6
|
+
t.references :origin_panda_cms_page, null: true, foreign_key: {to_table: :panda_cms_pages}, type: :uuid
|
|
7
|
+
t.references :destination_panda_cms_page, null: true, foreign_key: {to_table: :panda_cms_pages}, type: :uuid
|
|
8
|
+
t.integer :status_code, default: 301, null: false
|
|
9
|
+
t.integer :visits, default: 0, null: false
|
|
10
|
+
t.datetime :last_visited_at, null: true
|
|
11
|
+
t.timestamps
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
class CreatePandaCMSVisits < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_visits, id: :uuid do |t|
|
|
4
|
+
t.string :ip_address, null: true
|
|
5
|
+
t.string :user_agent, null: true
|
|
6
|
+
|
|
7
|
+
t.references :panda_cms_page, null: true, foreign_key: true, type: :uuid
|
|
8
|
+
t.references :panda_cms_redirect, null: true, foreign_key: true, type: :uuid
|
|
9
|
+
t.references :panda_cms_user, null: true, foreign_key: true, type: :uuid
|
|
10
|
+
t.timestamps
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
# This migration comes from active_storage (originally 20170806125915)
|
|
2
|
+
class CreateActiveStorageTables < ActiveRecord::Migration[7.0]
|
|
3
|
+
def change
|
|
4
|
+
# Use Active Record's configured type for primary and foreign keys
|
|
5
|
+
primary_key_type, foreign_key_type = primary_and_foreign_key_types
|
|
6
|
+
|
|
7
|
+
create_table :active_storage_blobs, id: primary_key_type do |t|
|
|
8
|
+
t.string :key, null: false
|
|
9
|
+
t.string :filename, null: false
|
|
10
|
+
t.string :content_type
|
|
11
|
+
t.text :metadata
|
|
12
|
+
t.string :service_name, null: false
|
|
13
|
+
t.bigint :byte_size, null: false
|
|
14
|
+
t.string :checksum
|
|
15
|
+
|
|
16
|
+
if connection.supports_datetime_with_precision?
|
|
17
|
+
t.datetime :created_at, precision: 6, null: false
|
|
18
|
+
else
|
|
19
|
+
t.datetime :created_at, null: false
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
t.index [:key], unique: true
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
create_table :active_storage_attachments, id: primary_key_type do |t|
|
|
26
|
+
t.string :name, null: false
|
|
27
|
+
t.references :record, null: false, polymorphic: true, index: false, type: foreign_key_type
|
|
28
|
+
t.references :blob, null: false, type: foreign_key_type
|
|
29
|
+
|
|
30
|
+
if connection.supports_datetime_with_precision?
|
|
31
|
+
t.datetime :created_at, precision: 6, null: false
|
|
32
|
+
else
|
|
33
|
+
t.datetime :created_at, null: false
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
t.index [:record_type, :record_id, :name, :blob_id], name: :index_active_storage_attachments_uniqueness, unique: true
|
|
37
|
+
t.foreign_key :active_storage_blobs, column: :blob_id
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
create_table :active_storage_variant_records, id: primary_key_type do |t|
|
|
41
|
+
t.belongs_to :blob, null: false, index: false, type: foreign_key_type
|
|
42
|
+
t.string :variation_digest, null: false
|
|
43
|
+
|
|
44
|
+
t.index [:blob_id, :variation_digest], name: :index_active_storage_variant_records_uniqueness, unique: true
|
|
45
|
+
t.foreign_key :active_storage_blobs, column: :blob_id
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
private
|
|
50
|
+
|
|
51
|
+
def primary_and_foreign_key_types
|
|
52
|
+
config = Rails.configuration.generators
|
|
53
|
+
setting = config.options[config.orm][:primary_key_type]
|
|
54
|
+
primary_key_type = setting || :primary_key
|
|
55
|
+
foreign_key_type = setting || :bigint
|
|
56
|
+
[primary_key_type, foreign_key_type]
|
|
57
|
+
end
|
|
58
|
+
end
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
# This migration comes from active_storage (originally 20190112182829)
|
|
2
|
+
class AddServiceNameToActiveStorageBlobs < ActiveRecord::Migration[6.0]
|
|
3
|
+
def up
|
|
4
|
+
return unless table_exists?(:active_storage_blobs)
|
|
5
|
+
|
|
6
|
+
unless column_exists?(:active_storage_blobs, :service_name)
|
|
7
|
+
add_column :active_storage_blobs, :service_name, :string
|
|
8
|
+
|
|
9
|
+
if (configured_service = ActiveStorage::Blob.service.name)
|
|
10
|
+
ActiveStorage::Blob.unscoped.update_all(service_name: configured_service)
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
change_column :active_storage_blobs, :service_name, :string, null: false
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def down
|
|
18
|
+
return unless table_exists?(:active_storage_blobs)
|
|
19
|
+
|
|
20
|
+
remove_column :active_storage_blobs, :service_name
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
# This migration comes from active_storage (originally 20191206030411)
|
|
2
|
+
class CreateActiveStorageVariantRecords < ActiveRecord::Migration[6.0]
|
|
3
|
+
def change
|
|
4
|
+
return unless table_exists?(:active_storage_blobs)
|
|
5
|
+
|
|
6
|
+
# Use Active Record's configured type for primary key
|
|
7
|
+
create_table :active_storage_variant_records, id: primary_key_type, if_not_exists: true do |t|
|
|
8
|
+
t.belongs_to :blob, null: false, index: false, type: blobs_primary_key_type
|
|
9
|
+
t.string :variation_digest, null: false
|
|
10
|
+
|
|
11
|
+
t.index %i[blob_id variation_digest], name: "index_active_storage_variant_records_uniqueness", unique: true
|
|
12
|
+
t.foreign_key :active_storage_blobs, column: :blob_id
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
private
|
|
17
|
+
|
|
18
|
+
def primary_key_type
|
|
19
|
+
config = Rails.configuration.generators
|
|
20
|
+
config.options[config.orm][:primary_key_type] || :primary_key
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def blobs_primary_key_type
|
|
24
|
+
pkey_name = connection.primary_key(:active_storage_blobs)
|
|
25
|
+
pkey_column = connection.columns(:active_storage_blobs).find { |c| c.name == pkey_name }
|
|
26
|
+
pkey_column.bigint? ? :bigint : pkey_column.type
|
|
27
|
+
end
|
|
28
|
+
end
|
data/db/migrate/20240701225424_remove_not_null_on_active_storage_blobs_checksum.active_storage.rb
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
# This migration comes from active_storage (originally 20211119233751)
|
|
2
|
+
class RemoveNotNullOnActiveStorageBlobsChecksum < ActiveRecord::Migration[6.0]
|
|
3
|
+
def change
|
|
4
|
+
return unless table_exists?(:active_storage_blobs)
|
|
5
|
+
|
|
6
|
+
change_column_null(:active_storage_blobs, :checksum, true)
|
|
7
|
+
end
|
|
8
|
+
end
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
class CreatePandaCMSForms < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_forms, id: :uuid do |t|
|
|
4
|
+
t.string :name
|
|
5
|
+
t.integer :submissions, default: 0
|
|
6
|
+
t.timestamps
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
add_index :panda_cms_forms, :name, unique: true
|
|
10
|
+
end
|
|
11
|
+
end
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
class CreatePandaCMSFormSubmissions < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_form_submissions, id: :uuid do |t|
|
|
4
|
+
t.references :form, type: :uuid, null: false, foreign_key: {to_table: :panda_cms_forms}
|
|
5
|
+
t.jsonb :data, null: false, default: {}
|
|
6
|
+
t.timestamps
|
|
7
|
+
end
|
|
8
|
+
end
|
|
9
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
class CreatePandaCMSPosts < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_post_tags, id: :uuid do |t|
|
|
4
|
+
t.string :tag
|
|
5
|
+
t.string :description
|
|
6
|
+
t.string :slug
|
|
7
|
+
t.timestamps
|
|
8
|
+
t.index :tag, unique: true
|
|
9
|
+
t.index :slug, unique: true
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
create_table :panda_cms_posts, id: :uuid do |t|
|
|
13
|
+
t.string :title
|
|
14
|
+
t.string :slug
|
|
15
|
+
t.text :content
|
|
16
|
+
t.datetime :published_at
|
|
17
|
+
t.references :post_tag, type: :uuid, null: false, foreign_key: {to_table: :panda_cms_post_tags}
|
|
18
|
+
t.references :user, type: :uuid, null: false, foreign_key: {to_table: :panda_cms_users}
|
|
19
|
+
t.timestamps
|
|
20
|
+
t.index :slug, unique: true
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
create_enum :panda_cms_post_status, ["active", "draft", "hidden", "archived"]
|
|
24
|
+
add_column :panda_cms_posts, :status, :panda_cms_post_status, default: "draft", null: false
|
|
25
|
+
add_index :panda_cms_posts, :status
|
|
26
|
+
end
|
|
27
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
class CreatePandaCMSPostVersions < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
create_table :panda_cms_post_versions, id: :uuid do |t|
|
|
4
|
+
t.string :item_type, null: false
|
|
5
|
+
t.string :item_id, null: false
|
|
6
|
+
t.string :event, null: false
|
|
7
|
+
t.string :whodunnit
|
|
8
|
+
t.jsonb :object
|
|
9
|
+
t.jsonb :object_changes
|
|
10
|
+
t.datetime :created_at
|
|
11
|
+
end
|
|
12
|
+
add_index :panda_cms_post_versions, %i[item_type item_id]
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
class FixPandaCMSVisitsColumnNames < ActiveRecord::Migration[7.1]
|
|
2
|
+
def change
|
|
3
|
+
change_table :panda_cms_visits do |t|
|
|
4
|
+
t.rename :panda_cms_page_id, :page_id
|
|
5
|
+
t.rename :panda_cms_redirect_id, :redirect_id
|
|
6
|
+
t.rename :panda_cms_user_id, :user_id
|
|
7
|
+
t.string :referrer, null: true
|
|
8
|
+
t.datetime :visited_at
|
|
9
|
+
t.string :url, null: true
|
|
10
|
+
t.jsonb :params, null: true
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# This migration comes from action_text (originally 20180528164100)
|
|
2
|
+
class CreateActionTextTables < ActiveRecord::Migration[7.2]
|
|
3
|
+
def change
|
|
4
|
+
create_table :action_text_rich_texts, id: :uuid do |t|
|
|
5
|
+
t.string :name, null: false
|
|
6
|
+
t.text :body, limit: 16.megabytes - 1
|
|
7
|
+
t.references :record, null: false, polymorphic: true, index: false, type: :uuid
|
|
8
|
+
t.timestamps
|
|
9
|
+
t.index [:record_type, :record_id, :name], name: "index_action_text_rich_texts_uniqueness", unique: true
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
create_table :action_text_rich_text_versions, id: :uuid do |t|
|
|
13
|
+
t.string :item_type, null: false
|
|
14
|
+
t.string :item_id, null: false
|
|
15
|
+
t.string :event, null: false
|
|
16
|
+
t.string :whodunnit
|
|
17
|
+
t.jsonb :object
|
|
18
|
+
t.jsonb :object_changes
|
|
19
|
+
t.datetime :created_at
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
add_index :action_text_rich_text_versions, %i[item_type item_id]
|
|
23
|
+
end
|
|
24
|
+
end
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
class AddDepthToPandaCMSMenus < ActiveRecord::Migration[7.2]
|
|
2
|
+
def change
|
|
3
|
+
add_column :panda_cms_menus, :depth, :integer, null: true, default: nil
|
|
4
|
+
|
|
5
|
+
homepage = Panda::CMS::Page.find_by(path: "/")
|
|
6
|
+
if homepage
|
|
7
|
+
main_menu = Panda::CMS::Menu.find_by(start_page_id: homepage.id, kind: :auto)
|
|
8
|
+
main_menu&.update(depth: 2)
|
|
9
|
+
end
|
|
10
|
+
end
|
|
11
|
+
end
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
class ConvertPostContentToEditorJs < ActiveRecord::Migration[7.1]
|
|
2
|
+
def up
|
|
3
|
+
Panda::CMS::Post.find_each do |post|
|
|
4
|
+
next if post.post_content.blank?
|
|
5
|
+
|
|
6
|
+
editor_content = {
|
|
7
|
+
time: Time.current.to_i,
|
|
8
|
+
version: "2.28.2",
|
|
9
|
+
blocks: [
|
|
10
|
+
{
|
|
11
|
+
type: "paragraph",
|
|
12
|
+
data: {
|
|
13
|
+
text: post.post_content.to_plain_text
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
]
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
post.update_column(:content, editor_content)
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def down
|
|
24
|
+
Panda::CMS::Post.find_each do |post|
|
|
25
|
+
next if post.content.blank?
|
|
26
|
+
|
|
27
|
+
# Extract plain text from EditorJS format
|
|
28
|
+
plain_text = post.content["blocks"]
|
|
29
|
+
&.map { |block| block["data"]["text"] }
|
|
30
|
+
&.join("\n")
|
|
31
|
+
|
|
32
|
+
post.update_column(:content, plain_text)
|
|
33
|
+
end
|
|
34
|
+
end
|
|
35
|
+
end
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
class RemovePostTagReferences < ActiveRecord::Migration[8.0]
|
|
2
|
+
def up
|
|
3
|
+
remove_reference :panda_cms_posts, :post_tag, foreign_key: {to_table: :panda_cms_post_tags}, type: :uuid
|
|
4
|
+
drop_table :panda_cms_post_tags
|
|
5
|
+
end
|
|
6
|
+
|
|
7
|
+
def down
|
|
8
|
+
create_table :panda_cms_post_tags, id: :uuid do |t|
|
|
9
|
+
t.string :tag
|
|
10
|
+
t.string :description
|
|
11
|
+
t.string :slug
|
|
12
|
+
t.timestamps
|
|
13
|
+
t.index :tag, unique: true
|
|
14
|
+
t.index :slug, unique: true
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
add_reference :panda_cms_posts, :post_tag, type: :uuid, foreign_key: {to_table: :panda_cms_post_tags}
|
|
18
|
+
end
|
|
19
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
class AddEditorJsToPosts < ActiveRecord::Migration[7.0]
|
|
2
|
+
def up
|
|
3
|
+
# First, add a temporary column
|
|
4
|
+
add_column :panda_cms_posts, :content_jsonb, :jsonb, default: {}, null: false
|
|
5
|
+
|
|
6
|
+
# Copy data from the old column to the new one, converting to JSONB
|
|
7
|
+
execute <<-SQL
|
|
8
|
+
UPDATE panda_cms_posts
|
|
9
|
+
SET content_jsonb =
|
|
10
|
+
CASE
|
|
11
|
+
WHEN content IS NULL THEN '{}'::jsonb
|
|
12
|
+
WHEN content::text = '' THEN '{}'::jsonb
|
|
13
|
+
ELSE content::jsonb
|
|
14
|
+
END;
|
|
15
|
+
SQL
|
|
16
|
+
|
|
17
|
+
# Remove the old column
|
|
18
|
+
remove_column :panda_cms_posts, :content
|
|
19
|
+
|
|
20
|
+
# Rename the new column to the original name
|
|
21
|
+
rename_column :panda_cms_posts, :content_jsonb, :content
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def down
|
|
25
|
+
change_column :panda_cms_posts, :content, :text
|
|
26
|
+
end
|
|
27
|
+
end
|