Now liveThe Skillselion MCP - thousands of ranked skills, loaded into your agent mid-task. No install.Get it →
openaec-foundation avatar

Frappe Ops Upgrades

  • 57 installs
  • 159 repo stars
  • Updated July 8, 2026
  • openaec-foundation/erpnext_anthropic_claude_development_skill_package

Upgrade Frappe/ERPNext across major versions with bench update and migrate, handling patch failures, breaking changes, and rollback.

About

Guides upgrading Frappe/ERPNext between major versions and handling failed migrations. A developer uses it when planning a version upgrade or recovering from a broken migration.

  • Upgrade Frappe/ERPNext across major versions (v14→v15→v16)
  • Covers bench update, migrate, patch troubleshooting, and rollback

Frappe Ops Upgrades by the numbers

  • 57 all-time installs (skills.sh)
  • Ranked #682 of 1,435 DevOps & CI/CD skills by installs in the Skillselion catalog
  • Data as of Aug 5, 2026 (Skillselion catalog sync)
npx skills add https://github.com/openaec-foundation/erpnext_anthropic_claude_development_skill_package --skill frappe-ops-upgrades

Add your badge

Show developers this skill is listed on Skillselion. Paste this into your README.

Listed on Skillselion
Installs57
repo stars159
Last updatedJuly 8, 2026
Repositoryopenaec-foundation/erpnext_anthropic_claude_development_skill_package

What it does

Upgrade Frappe/ERPNext across major versions with bench update and migrate, handling patch failures, breaking changes, and rollback.

Files

SKILL.mdMarkdownGitHub ↗

Version Upgrades

Complete guide for upgrading Frappe/ERPNext between major versions, handling failed migrations, and rolling back safely.

Versions: v14 → v15 → v16

---

Quick Reference: Upgrade Commands

TaskCommand
Full updatebench update
Update specific appbench update --pull --app erpnext
Switch branchbench switch-to-branch version-15 frappe erpnext
Run migrations onlybench --site mysite migrate
Check migration readinessbench --site mysite ready-for-migration
Backup before upgradebench --site mysite backup
Restore from backupbench --site mysite restore /path/to/backup.sql.gz
Re-run failed patchAdd #YYYY-MM-DD suffix in patches.txt

---

Decision Tree: Upgrade Strategy

Need to upgrade?
├── Single minor version bump (e.g., v15.10 → v15.20)?
│   └── YES → Run `bench update` directly
├── Major version jump (e.g., v14 → v15)?
│   ├── Have custom apps?
│   │   ├── YES → Test on staging FIRST, check breaking changes
│   │   └── NO → Follow standard upgrade path
│   └── Multiple major versions (v14 → v16)?
│       └── ALWAYS upgrade one version at a time: v14 → v15 → v16
└── Production environment?
    ├── YES → ALWAYS test on staging clone first
    └── NO → Proceed with standard upgrade

---

Pre-Upgrade Checklist

ALWAYS complete these steps before ANY major version upgrade:

1. Full backupbench --site mysite backup --with-files 2. Test on staging — Clone production to a staging bench and test there first 3. Check breaking changes — Review the breaking changes section below 4. Audit custom apps — Run custom apps against new version's API changes 5. Check Python/Node versions — v15 requires Node 18+; v16 requires Node 24+, Python 3.14+ 6. Disable schedulerbench --site mysite scheduler disable 7. Check pending jobsbench --site mysite ready-for-migration 8. Read release notes — Check GitHub release notes for each version

---

Standard Upgrade Process

Step-by-Step

# 1. Backup all sites
bench backup-all-sites

# 2. Switch to target version branch
bench switch-to-branch version-15 frappe erpnext

# 3. Update (pulls code, installs deps, builds, migrates)
bench update

# 4. Verify
bench --site mysite migrate  # if not done by update
bench version                # confirm versions

What bench update Executes (In Order)

1. Backup all sites 2. Pull latest code for all apps (git pull) 3. Install Python requirements (pip install) 4. Install Node requirements (yarn install) 5. Build static assets (bench build) 6. Run migrations on all sites (bench migrate) 7. Restart bench processes

---

v14 → v15 Breaking Changes

Environment Requirements

Requirementv14v15
Node.jsv14+v18+
Python packagingsetup.pypyproject.toml

Backend Breaking Changes

  • `db.set()` removed — Use doc.db_set() instead
  • `db.sql()` parameters removedas_utf8 and formatted no longer accepted
  • `db.set_value()` for Singles — Use frappe.db.set_single_value() instead
  • `job_name` deprecated — Use job_id parameter in enqueue()
  • `frappe.new_doc()` argumentsparent_doc, parentfield, as_dict MUST be keyword args
  • `frappe.get_installed_apps()` — No longer accepts sort or frappe_last args
  • Method override order reversed — Last override now takes precedence
  • Timezone functions renamedconvert_utc_to_user_timezoneconvert_utc_to_system_timezone

Frontend Breaking Changes

  • Vue 2 → Vue 3 — All Vue components MUST be migrated
  • Window globals removedget_todayfrappe.datetime.get_today, userfrappe.session.user
  • `this` in Client Scripts — Local scope access no longer supported
  • Image lazy loading — Replace website-image-lazy class with native loading="lazy"

Security Changes

  • Server Scripts disabled by default — Enable: bench set-config -g server_script_enabled 1
  • "Desk User" role added — Replaces "All" role for desk user permissions
  • `currentsite.txt` removed — Use bench use sitename or FRAPPE_SITE env var

Removed Features

  • Event Streaming moved to separate app
  • Cordova support removed
  • setup.py removed (use pyproject.toml)
  • --make_copy and --restore build flags removed (use --hard-link)

See breaking-changes.md for the complete list.

---

v15 → v16 Breaking Changes

Environment Requirements

Requirementv15v16
Node.jsv18+v24+
Python3.10+3.14+

Backend Breaking Changes

  • Default sort order changedcreation instead of modified for all list queries
  • `has_permission` hooks — MUST return explicit True; None no longer accepted
  • `frappe.get_doc(doctype, name, field=value)` — No longer updates values
  • DB commits in document hooks — No longer allowed to prevent data integrity issues
  • `frappe.sendmail(now=True)` — No longer commits transactions implicitly
  • `db.get_value()` for Singles — Now returns proper types instead of strings
  • State-changing methods require POST/api/method/logout, /api/method/upload_file, etc.

Separated Modules (Install Separately)

  • Energy Points → frappe/eps
  • Newsletter → frappe/newsletter
  • Backup Integrations → frappe/offsite_backups
  • Blog → frappe/blog

Frontend Breaking Changes

  • Report/Dashboard/Page JS evaluated as IIFEs (no global scope pollution)
  • Awesome Bar redesigned, moved to sidebar (Cmd+K)
  • List view right sidebar removed
  • /apps endpoint deprecated; /app reroutes to /desk

Configuration Changes

  • Site config cached for up to one minute (changes not immediate)
  • Country field requires valid ISO 3166 ALPHA-2 code
  • bench version output format changed to "plain" (use -f legacy for old format)
  • override_doctype hook classes MUST inherit from the overridden class

See breaking-changes.md for the complete list.

---

Patch System

How Patches Work

Patches are one-off data migration scripts that run during bench migrate. They are defined in each app's patches.txt file.

patches.txt Format [v14+]

[pre_model_sync]
# Runs BEFORE schema sync — use for data prep
myapp.patches.v15_0.prepare_data_for_migration

[post_model_sync]
# Runs AFTER schema sync — use for data that needs new schema
myapp.patches.v15_0.migrate_data_to_new_fields

Patch Execution Rules

  • Patches run in the order defined in patches.txt
  • Each patch runs exactly ONCE — tracked in the __patches table
  • To re-run a patch, append a date comment: myapp.patches.v15_0.fix #2025-03-20
  • One-off statements: execute:frappe.delete_doc('Page', 'old_page', ignore_missing=True)

Writing a Patch

# myapp/patches/v15_0/migrate_field_data.py
import frappe

def execute():
    # ALWAYS reload if you need the NEW schema
    frappe.reload_doc("module_name", "doctype", "doctype_name")

    # Perform data migration
    frappe.db.sql("""
        UPDATE `tabSales Invoice`
        SET new_field = old_field
        WHERE old_field IS NOT NULL
    """)

Debugging Stuck Patches

# Check which patches have run
bench --site mysite console
>>> frappe.db.sql("SELECT * FROM __patches WHERE patch LIKE '%stuck_patch%'")

# Remove a patch record to force re-run
>>> frappe.db.sql("DELETE FROM __patches WHERE patch = 'myapp.patches.v15_0.broken_patch'")
>>> frappe.db.commit()

# Then re-run migrate
bench --site mysite migrate

---

Rollback Procedure

Immediate Rollback (Within Hours)

# 1. Stop all processes
bench stop

# 2. Restore database from pre-upgrade backup
bench --site mysite restore /path/to/pre-upgrade-backup.sql.gz \
  --with-public-files /path/to/files.tar \
  --with-private-files /path/to/private-files.tar

# 3. Switch back to previous version branch
bench switch-to-branch version-14 frappe erpnext

# 4. Install old dependencies
bench setup requirements

# 5. Build old assets
bench build

# 6. Start bench
bench start  # or: sudo bench restart (production)

Critical Rules for Rollback

  • ALWAYS keep pre-upgrade backups for at least 7 days
  • NEVER run bench migrate after restoring to old branch — schema is already correct
  • ALWAYS restore files alongside database — file references may break otherwise
  • NEVER attempt rollback after users have created new data on the upgraded version

---

Frappe Packages: Moving Customizations Between Sites

Frappe Packages (v14+) are lightweight UI-built applications — bundles of Custom Module Defs distributed as .tar.gz tarballs. For Custom Fields, Property Setters, and DocPerms on standard DocTypes, use Fixtures instead.

Quick Reference: Package vs Fixtures vs App

MechanismUse WhenCLI Command
PackageUI-built DocTypes, Scripts, Web PagesUI only (Package Import/Release)
FixturesCustom Fields, Property Setters, DocPermsbench --site mysite export-fixtures
Frappe AppFull development workflow, CI/CD, testsbench get-app, bench install-app

Package Workflow (UI-Based)

1. Create a Package document → assign Custom Module Defs to it 2. Create a Package Release → exports to [bench]/sites/[site]/packages/ as [package]-[version].tar.gz 3. On target site, create Package Import → attach tarball, check Activate 4. System migrates data like an app migration; use Force to overwrite existing files

Fixtures Workflow (CLI-Based)

# hooks.py — define what to export
fixtures = [
    "Custom Field",
    "Property Setter",
    {"dt": "Client Script", "filters": [["module", "=", "My Module"]]}
]
# Export fixtures to JSON in your app
bench --site mysite export-fixtures --app myapp

# Fixtures auto-sync on: bench --site mysite migrate

NEVER use Packages to modify standard/core DocTypes — use a Frappe App with Fixtures.

See frappe-packages.md for the complete reference including decision trees, limitations, and best practices.

---

Custom App Compatibility Checks

Before upgrading, audit each custom app:

1. Check deprecated APIs — Search for removed functions listed in breaking changes 2. Check `setup.py` — Must migrate to pyproject.toml for v15+ 3. Check Vue components — Must be Vue 3 compatible for v15+ 4. Check `patches.txt` — Ensure patches use [pre_model_sync]/[post_model_sync] sections [v14+] 5. Check hooks.py — Verify no removed hooks are used 6. Run testsbench --site test_site run-tests --app myapp

---

Decision Tree: In-Place vs Fresh Install

Choosing upgrade strategy:
├── Small site (< 10 GB database)?
│   └── In-place upgrade is usually fine
├── Large site (> 50 GB database)?
│   ├── Many custom apps? → Fresh install + data migration
│   └── Standard apps only? → In-place with extended downtime window
├── Skipping multiple versions (v13 → v15)?
│   └── ALWAYS fresh install — sequential upgrades are too risky
└── Critical production with zero-downtime requirement?
    └── Fresh install on parallel server + DNS switch

---

Version Differences Summary

Featurev14v15v16
Python packagingsetup.pypyproject.tomlpyproject.toml
Vue versionVue 2Vue 3Vue 3
Node.js minimumv14v18v24
Python minimum3.83.103.14
Server ScriptsEnabledDisabled defaultDisabled default
Default sortmodifiedmodifiedcreation
patches.txt sectionsYesYesYes
Workspace sidebarNoNoYes
Separated modulesEvent StreamingBlog, Newsletter, EPS

---

Reference Files

FileContents
examples.mdComplete upgrade workflow examples
anti-patterns.mdCommon upgrade mistakes and fixes
breaking-changes.mdDetailed breaking changes per version
frappe-packages.mdPackages, fixtures, and moving customizations between sites

Related skills

DevOps & CI/CDdeployinfra

This week in AI coding

Five minutes, every Monday - the tools, releases and tactics for developers.

unsubscribe anytime.