Versioning and upgrading in the SharePoint Framework (SPFx) can be a bit tricky, but understanding how they work is crucial for maintaining your projects efficiently.

Interestingly, I’ve seen this question pop up a few times recently, from my panel at the European SharePoint Conference (ESPC) 2024 in Stockholm, Sweden, to students in my Mastering the SharePoint Framework course, to just this week during an office hours session in my SharePoint Framework Development Accelerator program.
Conventional wisdom says you can use the popular ClI for Microsoft 365 to upgrade your project. While that works just fine in most cases, projects of considerable size or when you’re jumping many major versions, in my opinion, isn’t the best option. Instead, I think it’s not only easier, but a better approach to create a new project and make specific changes to trick SharePoint into thinking it’s the same solution already deployed.
But first, let’s look at the multiple locations where you can find version numbers in SPFx solutions.
Key Versioning Locations in SPFx
There are three places where version numbers are specified in a SharePoint Framework project. However, only one of these directly impacts the upgrade process:
- Package Solution version (Important): Located in ./config/package-solution.json, this version determines whether an upgrade is available.
- Component Manifest version: Found in the manifest files of individual components, this is mainly for documentation.
- Package.json version: Used to centralize component versions and like the component manifest version property, it is only good for documentation.
How the *.sppkg Package Solution Version Works
When a new package is uploaded to the App Catalog, SharePoint identifies it as an upgrade if the version number has changed. However, upgrading only reactivates the SharePoint Feature associated with the solution.
But, regardless if the package’s version has changed, when its updated and deployed to the App Catalog, SharePoint will deploy the JavaScript bundles to the servers… regardless if you upgrade the package in the UX.
Example Scenario:
Monday: You deploy v1.0.0.0 of your package, as defined in the ./config/package-solution.json file.
{ "solution": { "name": "hello-world-client-side-solution", "id": "fba2bd20-1cc4-4091-bbee-c9d915109f99", "version": "1.0.0.0", .. } }
Tuesday: You modify the code but don’t change the version number. When redeployed, all existing instances of the web part receive the updated code automatically.
Wednesday: You update the package to v1.1.0.0. SharePoint prompts for an upgrade, but even without upgrading, the new code is deployed.
{ "solution": { "name": "hello-world-client-side-solution", "id": "fba2bd20-1cc4-4091-bbee-c9d915109f99", "version": "1.1.0.0", .. } }
Thursday: You add a new web part and update v1.2.0.0. The upgrade button must be clicked for the new web part to appear in the toolbox.
{ "solution": { "name": "hello-world-client-side-solution", "id": "fba2bd20-1cc4-4091-bbee-c9d915109f99", "version": "1.2.0.0", .. } }
Component Versioning in SPFx
Each web part or extension can also have an individual version number. This is specified in the manifest file but does not impact deployment behavior. If you use an asterisk (*
) instead of a fixed version, it inherits the ./package.json version.
{
"id": "976f874b-e076-45d2-8dbc-b9e871da0e7e",
"alias": "HelloWorldWebPart",
"componentType": "WebPart",
"version": "*",
"manifestVersion": 2,
..
}
This approach ensures all components follow a unified versioning scheme.
Upgrading SPFx Projects
Upgrading a SharePoint Framework project can be done manually or using a tool such as the CLI for Microsoft 365.
Option 1: Using Microsoft 365 CLI for Upgrades
The Microsoft 365 CLI provides a structured way to analyze and upgrade an SPFx project. It identifies required updates and provides commands to apply them.
Install the CLI globally:
npm install -g @pnp/cli-microsoft365
Navigate to your project directory.
Run the upgrade command:
m365 spfx project upgrade --output md
Follow the provided steps to update dependencies and configurations.
This works great for small upgrades, such as upgrading a project from one, two, or a few versions.
Option 2: Manual Upgrade Approach
Project updates can get complicated real fast. When you have a large project and/or one with major version jumps, such as SPFx v1.4.1 to v1.20, tools like the CLI for Microsoft 365, while it works, can lead to a long upgrade process requiring you to perform lots of steps. Getting just one of those steps incorrect, or missing it, could lead to a long debugging session.
That’s why, I think the safest approach to upgrading a large project, or one that involves jumping many versions, is to create a new project and migrate components from the original project to the new project manually.
The key to this approach is to make sure you keep the names, aliases, and IDs fo all components and the package the same as the original solution you’re upgrading.
Start by creating a new project with the same name and folder structure as the original project. To get this name, I like to use the ./.yo-rc.json file. In the following example, I can tell the name of the folder and solution is hello-world:
{ "@microsoft/generator-sharepoint": { "plusBeta": false, "isCreatingSolution": true, "nodeVersion": "18.20.4", "sdksVersions": { "@microsoft/microsoft-graph-client": "3.0.2", "@microsoft/teams-js": "2.24.0" }, "version": "1.20.0", "libraryName": "hello-world", "libraryId": "fba2bd20-1cc4-4091-bbee-c9d915109f99", "environment": "spo", "packageManager": "npm", "solutionName": "hello-world", "solutionShortDescription": "hello-world description", "skipFeatureDeployment": true, "isDomainIsolated": false, "componentType": "webpart" } }
Next, get the name of the components in the original solution. You’ll find these in the ./src/[COMPONET-TYPE]/[COMPONENT-NAME]/*.manifest.json. In the following example, I can tell the name was HelloWorld:
{ "id": "976f874b-e076-45d2-8dbc-b9e871da0e7e", "alias": "HelloWorldWebPart", "componentType": "WebPart", .. }
Create a new project with the desired SPFx Yeoman generator version. Use the names you’ve collected above for the solution name and component name. If you have multiple components, rerun the SPFx Yeoman generator each time to add new components to the package.
Copy business logic and components from the old project.
Update the solution ID of the new project to match the old project. This way SharePoint will treat the new package as an upgrade of the old one, not a different package. These ID’s are found in the ./config/package-solution.json file:
{ "solution": { "name": "hello-world-client-side-solution", "id": "fba2bd20-1cc4-4091-bbee-c9d915109f99", "version": "1.0.0.0", .. } }
Next, update all the IDs for the components as well. These are found in the ./src/[COMPONET-TYPE]/[COMPONENT-NAME]/*.manifest.json:
{ "id": "976f874b-e076-45d2-8dbc-b9e871da0e7e", "alias": "HelloWorldWebPart", "componentType": "WebPart", .. }
Test your solution locally and optionally in your shared test environment to ensure everything works as desired. Depending how old the original project is, you’re likely to run into some code issues or a lot of linting errors and warnings you’ll need to address.
Well, you might elect to just ignore those linting issues too… I won’t judge. 😉
Navigate ESLint in SharePoint Framework (SPFx) Projects + Guidance
Learn how to handle ESLint build-time errors, modify rules, and selectively disable rules in SPFx projects AND get my recommendations in this article.
https://www.voitanos.io/blog/navigate-eslint-sharepoint-framework-projects-guidance/
Test, Test, TEST the deployment the new package to SharePoint. It’s very easy to get things just slightly wrong. I strongly encourage you to test upgrading the old solution to the new solution within site collection App Catalogs if possible. I usually test this at least 2 or 3 times. Each time, I create a new site collection, turn on the Site Collection App Catalog. This way I can keep things as isolated as possible.
Good Practices for Versioning
Finally, when it comes to versioning and upgrading SPFx solutions, here are a few general things I recommend to my students and coaching clients:
- Increment the package solution version when making structural changes (e.g., adding/removing components, modifying manifests).
- Keep component versions consistent for better maintainability.
- Use Semantic Versioning principles: Major (1.x), Minor (1.1.x), and Patch (1.1.1.x) versions should follow logical upgrade paths.
If you elect to adopt Semantic Versioning for you SPFx projects, keep in mind that not everyone does this.
For example, the SPFx team most certainly does not follow Semantic Versioning for the NPM packages used by the SPFx. Just because it looks like a project does, unless it’s explicitly stated in the docs, assume it isn’t.
Conclusion
Understanding versioning in the SharePoint Framework is essential for maintaining smooth deployments and upgrades. Whether using manual methods or the Microsoft 365 CLI, following best practices ensures stability and maintainability.
