Information for Developers
Code:
/**
* Adds your plugin to the updater. The URL will be updated if
* your plugin was previously added.
*
* @param url URL to your plugin's update file.
* @noreturn
*/
native Updater_AddPlugin(const String:url[]);
/**
* Removes your plugin from the updater. This does not need to
* be called during OnPluginEnd.
*
* @noreturn
*/
native Updater_RemovePlugin();
/**
* Forces your plugin to be checked for updates. The behaviour
* of the update is dependant on the server's configuration.
*
* @return True if an update was triggered. False otherwise.
* @error Plugin not found in updater.
*/
native bool:Updater_ForceUpdate();
/**
* Called when your plugin is about to be checked for updates.
*
* @return Plugin_Handled to prevent checking, Plugin_Continue to allow it.
*/
forward Action:Updater_OnPluginChecking();
/**
* Called when your plugin is about to begin downloading an available update.
*
* @return Plugin_Handled to prevent downloading, Plugin_Continue to allow it.
*/
forward Action:Updater_OnPluginDownloading();
/**
* Called when your plugin's update files have been fully downloaded
* and are about to write to their proper location. This should be used
* to free read-only resources that require write access for your update.
*
* @note OnPluginUpdated will be called later during the same frame.
*
* @noreturn
*/
forward Updater_OnPluginUpdating();
/**
* Called when your plugin's update has been completed. It is safe
* to reload your plugin at this time.
*
* @noreturn
*/
forward Updater_OnPluginUpdated();
/**
* @brief Reloads a plugin.
*
* @param plugin Plugin Handle (INVALID_HANDLE uses the calling plugin).
* @noreturn
*/
stock ReloadPlugin(Handle:plugin=INVALID_HANDLE);
When testing an update with your plugin, I recommend that you test it against a debug version of Updater. It will log detailed download information to
Updater_Debug.log in case you accidentally used malformed URLs or paths.
Code:
/* Line 25: updater.sp */
#define DEBUG // This will enable verbose logging. Useful for developers testing their updates.
Example Plugin
Code:
#include <sourcemod>
#undef REQUIRE_PLUGIN
#include <updater>
#define UPDATE_URL "http://website.com/myplugin/updatefile.txt"
public OnPluginStart()
{
if (LibraryExists("updater"))
{
Updater_AddPlugin(UPDATE_URL)
}
}
public OnLibraryAdded(const String:name[])
{
if (StrEqual(name, "updater"))
{
Updater_AddPlugin(UPDATE_URL)
}
}
Now let's take a look at what UPDATE_URL is pointing to ...
Update File Format
Simple Update - Majority of plugins will use this.
Code:
"Updater"
{
"Information"
{
"Version"
{
"Latest" "1.0.1"
}
"Notes" "More info @ www.sourcemod.net. Changes in 1.0.1:"
"Notes" "Added new Batman model"
"Notes" "Minor code changes"
}
"Files"
{
"Plugin" "Path_SM/plugins/myplugin.smx"
"Plugin" "Path_SM/translations/myplugin.phrases.txt"
"Plugin" "Path_SM/translations/ru/myplugin.phrases.txt"
"Plugin" "Path_Mod/models/characters/batman.mdl"
"Plugin" "Path_Mod/materials/models/characters/batman.vmt"
"Source" "Path_SM/scripting/myplugin.sp"
}
}
Patch Update - Useful on large plugins to avoid downloading all files when only a few have changed. Patch files will be used if the "Previous" version matches the server's currently running version.
Code:
"Updater"
{
"Information"
{
"Version"
{
"Latest" "1.0.1"
"Previous" "1.0.0"
}
"Notes" "More info @ www.sourcemod.net. Changes in 1.0.1:"
"Notes" "Added Russian phrases"
"Notes" "Minor code changes"
}
"Files"
{
"Patch"
{
"Plugin" "Path_SM/plugins/myplugin.smx"
"Plugin" "Path_SM/translations/ru/myplugin.phrases.txt"
"Source" "Path_SM/scripting/myplugin.sp"
}
"Plugin" "Path_SM/plugins/myplugin.smx"
"Plugin" "Path_SM/translations/myplugin.phrases.txt"
"Plugin" "Path_SM/translations/ru/myplugin.phrases.txt"
"Plugin" "Path_Mod/models/characters/batman.mdl"
"Plugin" "Path_Mod/materials/models/characters/batman.vmt"
"Source" "Path_SM/scripting/myplugin.sp"
}
}
All web paths are relative to your plugin's update file (UPDATE_URL in this case). Using the above example, the URLs for this update would look like this:
Code:
UPDATE_URL = http://website.com/myplugin/updatefile.txt
http://website.com/myplugin/plugins/myplugin.smx
http://website.com/myplugin/translations/myplugin.phrases.txt
http://website.com/myplugin/translations/ru/myplugin.phrases.txt
http://website.com/myplugin/models/characters/batman.mdl
http://website.com/myplugin/materials/models/characters/batman.vmt
http://website.com/myplugin/scripting/myplugin.sp
Final Notes
- You should only reload your plugin manually if your plugin can handle late load situations. Otherwise letting it reload automatically during the next mapchange is safest.
- If you have released a plugin that uses Updater, post a link to it in this thread. I'd like to take a look at it!
- If you're looking for somewhere to host your update files for free: Updater Integration Using Bitbucket