Packages
phoenix_kit
1.7.21
1.7.211
1.7.210
1.7.209
1.7.208
1.7.207
1.7.206
1.7.205
1.7.204
1.7.203
1.7.202
1.7.201
1.7.200
1.7.199
1.7.198
1.7.197
1.7.196
1.7.194
1.7.193
1.7.192
1.7.191
1.7.190
1.7.189
1.7.187
1.7.186
1.7.185
1.7.184
1.7.183
1.7.182
1.7.181
1.7.180
1.7.179
1.7.178
1.7.177
1.7.176
1.7.175
1.7.174
1.7.173
1.7.172
1.7.171
1.7.170
1.7.169
1.7.168
1.7.167
1.7.166
1.7.165
1.7.164
1.7.162
1.7.161
1.7.160
1.7.159
1.7.157
1.7.156
1.7.155
1.7.154
1.7.153
1.7.152
1.7.151
1.7.150
1.7.149
1.7.146
1.7.145
1.7.144
1.7.143
1.7.138
1.7.133
1.7.132
1.7.131
1.7.130
1.7.128
1.7.126
1.7.125
1.7.121
1.7.120
1.7.119
1.7.118
1.7.117
1.7.116
1.7.115
1.7.114
1.7.113
1.7.112
1.7.111
1.7.110
1.7.109
1.7.108
1.7.107
1.7.106
1.7.105
1.7.104
1.7.103
1.7.102
1.7.101
1.7.100
1.7.99
1.7.98
1.7.97
1.7.96
1.7.95
1.7.94
1.7.93
1.7.92
1.7.91
1.7.90
1.7.89
1.7.88
1.7.87
1.7.86
1.7.85
1.7.84
1.7.83
1.7.82
1.7.81
1.7.80
1.7.79
1.7.78
1.7.77
1.7.76
1.7.75
1.7.74
1.7.71
1.7.70
1.7.69
1.7.66
1.7.65
1.7.64
1.7.63
1.7.62
1.7.61
1.7.59
1.7.58
1.7.57
1.7.56
1.7.55
1.7.54
1.7.53
1.7.52
1.7.51
1.7.49
1.7.44
1.7.43
1.7.42
1.7.41
1.7.39
1.7.38
1.7.37
1.7.36
1.7.34
1.7.33
1.7.31
1.7.30
1.7.29
1.7.28
1.7.27
1.7.26
1.7.25
1.7.24
1.7.23
1.7.22
1.7.21
1.7.20
1.7.19
1.7.18
1.7.17
1.7.16
1.7.15
1.7.14
1.7.13
1.7.12
1.7.11
1.7.10
1.7.9
1.7.8
1.7.7
1.7.6
1.7.5
1.7.4
1.7.3
1.7.2
1.7.1
1.7.0
1.6.20
1.6.19
1.6.18
1.6.17
1.6.16
1.6.15
1.6.14
1.6.13
1.6.12
1.6.11
1.6.10
1.6.9
1.6.8
1.6.7
1.6.6
1.6.5
1.6.4
1.6.3
1.5.2
1.5.1
1.5.0
1.4.9
1.4.8
1.4.7
1.4.6
1.4.5
1.4.4
1.4.3
1.4.2
1.4.1
1.4.0
1.3.2
1.3.1
1.3.0
1.2.10
1.2.9
1.2.8
1.2.7
1.2.5
1.2.4
1.2.2
1.2.1
1.2.0
1.1.0
1.0.0
A foundation for building Elixir Phoenix apps — SaaS, social networks, ERP systems, marketplaces, and more
Current section
Files
Jump to
Current section
Files
lib/mix/tasks/phoenix_kit.migrate_blogging_to_publishing.ex
defmodule Mix.Tasks.PhoenixKit.MigrateBloggingToPublishing do
@shortdoc "Migrates blogging module to publishing (storage path and settings)"
@moduledoc """
Migrates the PhoenixKit blogging module to the new publishing module.
## What this task does
1. Renames `priv/blogging` directory to `priv/publishing` (if it exists)
2. Migrates settings keys from legacy names to new names:
- `blogging_enabled` → `publishing_enabled`
- `blogging_blogs` → `publishing_groups`
- `blogging_file_cache_enabled` → `publishing_file_cache_enabled`
- `blogging_memory_cache_enabled` → `publishing_memory_cache_enabled`
- `blogging_render_cache_enabled` → `publishing_render_cache_enabled`
- `blogging_render_cache_enabled_*` → `publishing_render_cache_enabled_*`
## Usage
mix phoenix_kit.migrate_blogging_to_publishing
mix phoenix_kit.migrate_blogging_to_publishing --dry-run
mix phoenix_kit.migrate_blogging_to_publishing --verbose
## Options
- `--dry-run` - Shows what would be changed without making any changes
- `--verbose` - Shows detailed output of each operation
## Safety
This task is idempotent - it's safe to run multiple times:
- If `priv/publishing` already exists, directory rename is skipped
- If new settings keys already have values, those values are preserved
- Legacy settings are not deleted (kept for backward compatibility)
## Rollback
To rollback, manually:
1. Rename `priv/publishing` back to `priv/blogging`
2. The application will automatically read from legacy settings keys
"""
use Mix.Task
alias PhoenixKit.Modules.Publishing
alias PhoenixKit.Modules.Publishing.Storage
alias PhoenixKit.Settings
@impl Mix.Task
def run(args) do
{opts, _, _} = OptionParser.parse(args, switches: [dry_run: :boolean, verbose: :boolean])
dry_run = Keyword.get(opts, :dry_run, false)
verbose = Keyword.get(opts, :verbose, false)
Mix.shell().info("PhoenixKit Blogging → Publishing Migration")
Mix.shell().info(String.duplicate("=", 50))
if dry_run do
Mix.shell().info("Running in DRY RUN mode - no changes will be made\n")
end
# Start the application to access Settings
unless dry_run do
Mix.Task.run("app.start")
end
# Step 1: Migrate storage directory
migrate_storage_directory(dry_run, verbose)
# Step 2: Migrate settings keys
migrate_settings_keys(dry_run, verbose)
Mix.shell().info("\nMigration complete!")
end
defp migrate_storage_directory(dry_run, _verbose) do
Mix.shell().info("\n1. Storage Directory Migration")
Mix.shell().info(String.duplicate("-", 30))
# Get paths
legacy_path = Storage.legacy_root_path()
new_path = Storage.new_root_path()
legacy_exists = File.dir?(legacy_path)
new_exists = File.dir?(new_path)
cond do
new_exists ->
Mix.shell().info("✓ New path already exists: #{new_path}")
Mix.shell().info(" Skipping directory rename")
legacy_exists ->
if dry_run do
Mix.shell().info("Would rename: #{legacy_path}")
Mix.shell().info(" to: #{new_path}")
else
case File.rename(legacy_path, new_path) do
:ok ->
Mix.shell().info("✓ Renamed: #{legacy_path}")
Mix.shell().info(" to: #{new_path}")
{:error, reason} ->
Mix.shell().error("✗ Failed to rename directory: #{inspect(reason)}")
Mix.shell().error(" You may need to rename manually:")
Mix.shell().error(" mv #{legacy_path} #{new_path}")
end
end
true ->
Mix.shell().info("✓ Neither path exists - fresh installation")
Mix.shell().info(" New installations will use: #{new_path}")
end
end
defp migrate_settings_keys(dry_run, verbose) do
Mix.shell().info("\n2. Settings Key Migration")
Mix.shell().info(String.duplicate("-", 30))
if dry_run do
Mix.shell().info("Settings migration requires database access.")
Mix.shell().info("Run without --dry-run to migrate settings.")
return_settings_to_migrate()
else
migrate_settings(verbose)
end
end
defp return_settings_to_migrate do
settings = [
{"blogging_enabled", "publishing_enabled"},
{"blogging_blogs", "publishing_groups"},
{"blogging_file_cache_enabled", "publishing_file_cache_enabled"},
{"blogging_memory_cache_enabled", "publishing_memory_cache_enabled"},
{"blogging_render_cache_enabled", "publishing_render_cache_enabled"}
]
Mix.shell().info("\nSettings that would be migrated:")
for {old_key, new_key} <- settings do
Mix.shell().info(" #{old_key} → #{new_key}")
end
Mix.shell().info(" blogging_render_cache_enabled_* → publishing_render_cache_enabled_*")
end
defp migrate_settings(verbose) do
# Core settings to migrate
core_settings = [
{"blogging_enabled", "publishing_enabled"},
{"blogging_blogs", "publishing_groups"},
{"blogging_file_cache_enabled", "publishing_file_cache_enabled"},
{"blogging_memory_cache_enabled", "publishing_memory_cache_enabled"},
{"blogging_render_cache_enabled", "publishing_render_cache_enabled"}
]
# Migrate core settings
for {old_key, new_key} <- core_settings do
migrate_setting(old_key, new_key, verbose)
end
# Migrate per-blog render cache settings
migrate_per_blog_render_cache_settings(verbose)
end
defp migrate_setting(old_key, new_key, verbose) do
# Check if new key already has a value
case Settings.get_setting(new_key, nil) do
nil ->
# New key doesn't exist, check legacy key
case Settings.get_setting(old_key, nil) do
nil ->
if verbose do
Mix.shell().info(" - #{old_key}: not set, skipping")
end
value ->
Settings.update_setting(new_key, value)
Mix.shell().info("✓ Migrated: #{old_key} → #{new_key}")
if verbose do
Mix.shell().info(" Value: #{inspect(value)}")
end
end
_value ->
Mix.shell().info("✓ #{new_key}: already exists, keeping existing value")
end
end
defp migrate_per_blog_render_cache_settings(verbose) do
# Find all per-blog render cache settings
# These match the pattern blogging_render_cache_enabled_{slug}
prefix = "blogging_render_cache_enabled_"
new_prefix = "publishing_render_cache_enabled_"
# We need to query the settings table for keys matching the pattern
# Since we don't have a direct query function, we'll use the blogs list
# to determine which per-blog settings might exist
case Publishing.list_groups() do
blogs when is_list(blogs) ->
for blog <- blogs do
slug = blog["slug"]
old_key = prefix <> slug
new_key = new_prefix <> slug
migrate_setting(old_key, new_key, verbose)
end
_ ->
if verbose do
Mix.shell().info(" - No blogs found for per-blog settings migration")
end
end
end
end