CLI Overview
Quick Start Guide
wheels info
wheels reload
wheels deps
wheels destroy
wheels watch
wheels generate app
wheels generate app-wizard
wheels generate controller
wheels generate model
wheels generate view
wheels generate property
wheels generate route
wheels generate resource
wheels generate api-resource
wheels generate frontend
wheels generate test
wheels generate snippets
wheels scaffold
wheels db create
wheels db drop
wheels db setup
wheels db reset
wheels db status
wheels db version
wheels db rollback
wheels db seed
wheels db dump
wheels db restore
wheels db shell
wheels db schema
wheels dbmigrate info
wheels dbmigrate latest
wheels dbmigrate up
wheels dbmigrate down
wheels dbmigrate reset
wheels dbmigrate exec
wheels dbmigrate create blank
wheels dbmigrate create table
wheels dbmigrate create column
wheels dbmigrate remove table
wheels test
wheels test run
wheels test coverage
wheels test debug
wheels config list
wheels config set
wheels config env
wheels env
wheels env setup
wheels env list
wheels env switch
wheels environment
wheels console
wheels runner
wheels server
wheels server start
wheels server stop
wheels server restart
wheels server status
wheels server log
wheels server open
wheels plugins
wheels plugins list
wheels plugins install
wheels plugins remove
wheels analyze
wheels analyze code
wheels analyze performance
wheels analyze security
wheels security
wheels security scan
wheels optimize
wheels optimize performance
wheels docs
wheels docs generate
wheels docs serve
wheels ci init
wheels docker init
wheels docker deploy
wheels deploy
wheels deploy audit
wheels deploy exec
wheels deploy hooks
wheels deploy init
wheels deploy lock
wheels deploy logs
wheels deploy proxy
wheels deploy push
wheels deploy rollback
wheels deploy secrets
wheels deploy setup
wheels deploy status
wheels deploy stop
Configuration Management
Creating Commands
Service Architecture
Migrations Guide
Testing Guide
Object Relational Mapping
Creating Records
Reading Records
Updating Records
Deleting Records
Column Statistics
Dynamic Finders
Getting Paginated Data
Associations
Nested Properties
Object Validation
Object Callbacks
Calculated Properties
Transactions
Dirty Records
Soft Delete
Automatic Time Stamps
Using Multiple Data Sources
description: How to publish your plugin to forgebox.io via CommandBox
Publishing Plugins
So, you've created your new magic, world solving plugin, and naturally, you want to share it with the world. Wheels uses forgebox.io as a plugins repository. This enables us to manage our Wheels application's dependencies, install updates easily via CommandBox and more.
As a plugin author, it's well worth spending a little time setting yourself up to work with forgebox with the minimum amount of effort. Once done, you'll be able to either publish directly from the commandline, or upload to forgebox manually.
This tutorial makes extensive use of CommandBox, GIT and the Wheels CLI.
Requirements
We strongly recommend always having the latest version of CommandBox.
You'll also want the Wheels CLI. You can install that in CommandBox via install wheels-cli
. This will also update it if you've got an older version installed.
Some scripted commands also require the git CLI, although these are technically optional.
Setup a forgebox user account
If you've not got a forgebox.io account you can either register directly on forgebox or very quickly via CommandBox itself
{% code title="CommandBox" %}
# Register for an account
$ forgebox register
{% endcode %}
Once you've got your credentials, you should be good to go.
If you've already got an account, you need to login at least once, which will store an API token for future use:
{% code title="CommandBox" %}
# Login
$ forgebox login
# (optional) Check which account you're logged in with
$ forgebox whoami
{% endcode %}
Ensure you've got a box.json in your plugin root
Forgebox uses your local box.json
- you'll need one! Critical package information like the name of your plugin and the location are stored here. You can create one manually, or you can run:
{% code title="Shell" %}
# Create a basic box.json
$ init
# Or pass in parameters at the same time
$ init name="My Funky Plugin" slug=my-funky-plugin version=1.0.0 type="wheels-plugins"
# Or use the wizard
$ init --wizard
{% endcode %}
Ensure you've set some critical box.json attributes
In order for other Wheels users to quickly identify and install your plugin via the Wheels CLI, make sure you set the following box.json
attributes - whilst a standard box.json
might only have name, version,author
, we need a little more information. Here's a template to get you started: (replace the values in CAPS)
{% code title="box.json" %}
{
// Required:
"name":"PLUGIN-NAME",
"version":"0.0.1",
"author":"YOURNAME",
// Required: GitHub Repository stub
"location":"GITHUBUSERNAME/GITHUB-REPONAME#v0.0.1",
// Required: Should always be /app/plugins/
"directory":"/app/plugins/",
// Required: Should always be true
"createPackageDirectory":true,
// Required: Must be the name of your primary CFC File
"packageDirectory":"PLUGIN-NAME",
// Required: The Forgebox slug, must be unique
"slug":"FORGEBOX-SLUG",
// Required: Must be wheels-plugins
"type":"wheels-plugins",
// Required: From here is optional but recommended
"homepage":"https://github.com/GITHUBUSERNAME/GITHUB-REPONAME",
"shortDescription":"PLUGIN DESCRIPTION",
"keywords":"KEYWORD",
"private":false,
"scripts":{
"postVersion":"package set location='GITHUBUSERNAME/GITHUB-REPONAME#v`package version`'",
"patch-release":"bump --patch",
"minor-release":"bump --minor",
"major-release":"bump --major",
"postPublish":"!git push --follow-tags && publish"
}
}
{% endcode %}
Your completed box.json
might look something like this:
{% code title="box.json" %}
{
// Required:
"name":"Shortcodes",
"version":"0.0.4",
"author":"Tom King",
// Required: GitHub Repository stub, including version hash
"location":"neokoenig/wheels-shortcodes#v0.0.4",
// Required: Should always be /app/plugins/
"directory":"/app/plugins/",
// Required: Should always be true
"createPackageDirectory":true,
// Required: Must be the name of your primary CFC File
"packageDirectory":"Shortcodes",
// Required: The Forgebox slug, must be unique
"slug":"shortcodes",
// Required: Must be wheels-plugins
"type":"wheels-plugins",
// Required: From here is optional but recommended
"homepage":"https://github.com/neokoenig/wheels-shortcodes",
"shortDescription":"Shortcodes Plugin for Wheels",
"keywords":"shortcodes",
"private":false,
"scripts":{
"postVersion":"package set location='neokoenig/wheels-shortcodes#v`package version`'",
"patch-release":"bump --patch",
"minor-release":"bump --minor",
"major-release":"bump --major",
"postPublish":"!git push --follow-tags && publish"
}
}
{% endcode %}
Using the forgebox staging server (optional)
If this is the first time you've done this, you might want to try the forgebox staging server. That way you can make sure your publishing process is spot on without having lots of unnecessary versions pushed up. You can view the staging server version at http://forgebox.stg.ortussolutions.com/
{% code title="CommandBox" %}
# Add staging server configuration
$ config set endpoints.forgebox.APIURL=http://forgebox.stg.ortussolutions.com/api/v1
# Revert back to production configuration
$ config clear endpoints.forgebox.APIURL
{% endcode %}
Remember this configuration will "stick", so make sure you change it back afterwards. (I find once changed, it might not kick in until you reload the CommandBox shell via r
).
Publishing a plugin to forgebox
Both Wheels CLI and Forgebox are expecting a tagged release with the plugin contents (e.g. zip). So the best way to publish is to...
- Navigate into the plugin directory
- Ensure that directory is authorized to publish the repo (e.g.
git remote -v
should list your fetch/push endpoints)
Note: Git dislikes nested repos, so it's best to setup a test wheels site specifically for plugin development/deployment. Then
git init
within each plugin directory itself, but not at the root. (e.g./app/plugins/PluginName/
)
{% code title="CommandBox" %}
# from CommandBox prompt, within plugin directory
$ run-script patch-release
{% endcode %}
ForgeBox does not store your actual package files like npm, but points to your download location.
The following should happen (again, assuming you have git publish rights from that plugin directory)
- Auto increment your version number within box.json
- Push updated box.json to forgebox (with new version number + location)
- Create a git "Tagged Release" which is basically a zip containing the source files
Once you run this command, you can run forgebox show my-package
to confirm it's there. If you change the slug, a new package will be created. If you change the version, a new version will be added to the existing package.
Adding a new version via publishing scripts
By adding the following block to our box.json
, we can more easily deploy new versions with a single command:
{% code title="box.json" %}
"scripts":{
"postVersion":"package set location='GITHUBUSERNAME/GITHUB-REPONAME#v`package version`'",
"patch-release":"bump --patch",
"minor-release":"bump --minor",
"major-release":"bump --major",
"postPublish":"!git push --follow-tags && publish"
}
{% endcode %}
Obviously, you'll need to change location='GITHUBUSERNAME/GITHUB-REPONAME#v
to your repo.
With these in place, once you've committed your changes to your local repository, you can now do:
{% code title="CommandBox" %}
# Don't forget to commit your changes. You can access git directly from commandbox using !
$ !git add .
$ !git commit -m "my new changes"
# Move from 1.0.0 -> 1.0.1
$ run-script patch-release
# Move from 1.0.0 -> 1.1.0
$ run-script minor-release
# Move from 1.0.0 -> 2.0.0
$ run-script major-release
{% endcode %}
This will:
- Set the package location to include the new version number
- Publish to forgebox.io
- Push your changes to gitHub (assuming you've set that up)
- Publish a gitHub tagged release
This saves you having to manually update the version number too!
{% code title="Commandbox" %}
# Example output of a patch release
$ run-script patch-release
Running package script [patch-release].
> bump --patch && publish
Set version = 0.1.7
Running package script [postVersion].
> package set location='neokoenig/wheels-cli#v`package version`'
Set location = neokoenig/wheels-cli#v0.1.7
Package is a Git repo. Tagging...
Tag [v0.1.7] created.
Sending package information to ForgeBox, please wait...
Package is alive, you can visit it here: https://www.forgebox.io/view/wheels-cli
Running package script [postPublish].
> !git push --follow-tags
Counting objects: 10, done.
Delta compression using up to 12 threads.
Compressing objects: 100% (8/8), done.
Writing objects: 100% (10/10), 908 bytes | 0 bytes/s, done.
Total 10 (delta 5), reused 0 (delta 0)
remote: Resolving deltas: 100% (5/5), completed with 4 local objects.
To https://github.com/neokoenig/wheels-cli.git
477648f..400604b master -> master
* [new tag] v0.1.7 -> v0.1.7
Package published successfully in [forgebox]
{% endcode %}
Lastly, you can double check it's made it into the plugins list via wheels plugins list
Removing a plugin from forgebox
Likewise, you can unpublish a plugin, but keep in mind people might be relying on your plugin, so don't do this lightly!
{% code title="CommandBox" %}
// Remove all versions of a package
$ unpublish
// Remove a specific version of a package
$ unpublish 1.2.3
// Skip the user confirmation prompt
$ unpublish 1.2.3 --force
{% endcode %}