-
Notifications
You must be signed in to change notification settings - Fork 13
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Finalize plugin interface; Add to documentation.
- Loading branch information
Showing
14 changed files
with
369 additions
and
8,539 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,186 @@ | ||
--- | ||
id: PluginInterface | ||
title: AppImage Updater Bridge Plugin Interface | ||
sidebar_label: Qt Plugin Interface | ||
--- | ||
|
||
A plugin interface is a specification of public slots and signals that can be used to access | ||
the functionality of the plugin itself. The interface is not bound to any specific programming | ||
language and easily translates to any Qt bindings and programming language. | ||
|
||
All slots are [reentrant](https://doc.qt.io/qt-5/threads-reentrancy.html) and thread safe. | ||
|
||
Please refer the C++ documentation for info on how the slots act. | ||
|
||
> IMPORTANT: You have to start your Qt event loop for AppImageUpdaterBridge to function. | ||
### A note on Data Types | ||
|
||
Since plugins are not C++ specific, The data types are vaguely defined. | ||
In dynamic languages like python, you can just use native data types. (i.e) For QString, you can use str or QString from your Qt binding itself. | ||
|
||
I'm not sure about other Qt bindings, So help is much welcomed. | ||
|
||
## Slots | ||
|
||
| Name | Description | | ||
|------|------------------------------------| | ||
| [start()](#start) | Starts the update. | | ||
| [cancel()](#cancel) | Cancels current update process. | | ||
| [setAppImage(QString)](#setappimage-qstring) | Assume the given string as path to AppImage to update. | | ||
| [setShowLog(bool)](#setshowlogbool) | If the given boolean is true then prints log. | | ||
| [setOutputDirectory(QString)](#setoutputdirectory-qstring) | Set the output directory as given string. | | ||
| [setProxy(QNetworkProxy)](#setproxyconst-qnetworkproxy-https-docqtio-qt-5-qnetworkproxyhtml) | Use proxy as given in QNetworkProxy object. | | ||
| [checkForUpdate()](#checkforupdate) | Checks for new update. | | ||
| [clear()](#clear) | Clears internal cache and stores. | | ||
|
||
## Signals | ||
|
||
| Name | Description | | ||
|------|---------------| | ||
| [started()](#started) | Emitted when the update is actually started. | | ||
| [canceled()](#canceled) | Emitted when the update is canceled. | | ||
| [finished(QJsonObject , QString)](#finishedqjsonobject-qstring) | Emitted when update finishes. | | ||
| [updateAvailable(bool, QJsonObject)](#updateavailablebool-qjsonobject) | Emitted when checkForUpdate() is called. | | ||
| [error(short)](#errorshort) | Emitted when some error occurs. | | ||
| [progress(int, qint64, qint64, double, QString)](#progressint-percentage--qint64-bytesreceived--qint64-bytestotal--double-speed--qstring-speedunits) | Emitted on progress of update. See here for more information. | | ||
| [logger(QString, QString)](#loggerqstring-qstring) | See here for more information. | | ||
|
||
|
||
## Documentation | ||
|
||
### start() | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Starts the updater. | ||
Emits **started()** signal when starts. | ||
|
||
|
||
> Minor Note: You don't have to worry about anything if you called checkForUpdate or getAppImageEmbededInformation | ||
slots before start , Don't worry about overheads too , Since when you call checkForUpdate slot , The information | ||
is cached and when start slot is called again , it will be faster than normal. | ||
|
||
> Important Note: You should also call clear and set the settings again if you want to clear the cache. | ||
### cancel() | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Cancels the update. | ||
Emits **canceled()** signal when cancel was successfull. | ||
|
||
|
||
### setAppImage(QString) | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Sets the AppImage Path as the given **QString**. | ||
|
||
|
||
### setShowLog(bool) | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Turns on and off the log printer. | ||
|
||
> Note: logger signal will be emitted all the time if the library is compiled with LOGGING_DISABLED undefined, | ||
setShowLog will not affect this activity at all, But setShowLog will print these log messages | ||
if set to true. | ||
|
||
### setOutputDirectory(QString) | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Writes the new version of the AppImage to the given Output directory , Assuming the given QString a directory path. | ||
The default is the old version AppImage's directory. | ||
|
||
|
||
### setProxy([QNetworkProxy](https://doc.qt.io/qt-5/qnetworkproxy.html)) | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Sets the given [QNetworkProxy](https://doc.qt.io/qt-5/qnetworkproxy.html) as the proxy | ||
|
||
### checkForUpdate() | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Checks update for the current operating AppImage. | ||
emits **updateAvailable(bool , QJsonObject)** , Where the *bool* will be **true** if the AppImage | ||
needs update. The QJsonObject in the signal will have the details of the current operating | ||
AppImage. | ||
|
||
|
||
### clear() | ||
<p align="right"> <b>[SLOT]</b> </p> | ||
|
||
Clears all internal **cache** and stores. | ||
|
||
|
||
### started() | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when the updater is started successfully. | ||
|
||
### canceled() | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when the update is canceled successfully. | ||
|
||
### finished(QJsonObject , QString) | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when the update is finished successfully. The given *QJsonObject* has the details of the new version | ||
of the AppImage and the given *QString* has the absolute path to the old versioin of the AppImage. | ||
|
||
The *QJsonObject* will follow the folloing format with respect to json , | ||
|
||
{ | ||
"AbsolutePath" : "Absolute path of the new version of the AppImage" , | ||
"Sha1Hash" : "Sha1 hash of the new version of the AppImage" | ||
} | ||
|
||
> Note: If the absolute path of the new version of the AppImage is same as the old version then | ||
it could mean that there were no updates needed , You can however listen to the *updateAvailable* | ||
signal to know the exact state of updates. You should call *checkForUpdate* and then call *start* | ||
if updates were really available. | ||
|
||
|
||
### updateAvailable(bool , QJsonObject) | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when *[checkForUpdate()](#checkforupdate)* is called. | ||
The given *bool* states if the operating AppImage needs update and the *QJsonObject* gives the details of | ||
the current operating AppImage. | ||
|
||
The *QJsonObject* will follow the following format with respect to json , | ||
|
||
{ | ||
"AbsolutePath" : "The absolute path of the current operating AppImage" , | ||
"Sha1Hash" : "The Sha1 hash of the current operating AppImage" , | ||
"RemoteSha1Hash" : "The Sha1 hash of the lastest AppImage" , | ||
"ReleaseNotes" : "Release notes if available" | ||
} | ||
|
||
### error(short) | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when the updater is errored. The given short integer is the error code. | ||
See [error codes](AppImageUpdaterBridgeErrorCodes.html). | ||
|
||
|
||
### progress(int percentage , qint64 bytesReceived , qint64 bytesTotal , double speed , QString speedUnits) | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
The updater's progress is emitted through this unified signal. | ||
|
||
**Where** , | ||
|
||
| Variable | Description | | ||
|----------------|------------------------------------------------------------------| | ||
| percentage | % Finished revising the latest AppImage. | | ||
| bytesReceived | The received bytes of the latest AppImage. | | ||
| bytesTotal | The total bytes of the latest AppImage. | | ||
| speed | The transfer speed value. | | ||
| speedUnit | The transfer speed unit(e.g. KiB/s , etc... ) for **speed**. | | ||
|
||
### logger(QString , QString) | ||
<p align="right"> <b>[SIGNAL]</b> </p> | ||
|
||
Emitted when the updater issues a log message with the *first QString* as the log message and | ||
the *second QString* as the path to the respective AppImage. | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,95 @@ | ||
--- | ||
id: PyQt5PluginExample | ||
title: Using AppImage Updater Bridge Plugin in PyQt5 | ||
sidebar_label: Using Plugin in PyQt5 | ||
--- | ||
|
||
This guide Demonstrates how to use the *AppImageUpdaterBridge* plugin to update a single AppImage file. | ||
This example assumes you are using PyQt5 as your python binding to Qt framework. | ||
|
||
> Note that if the plugin is placed in the predefined Qt Plugin path, then you don't need the | ||
> absolute path of the plugin. Simply set the file name to 'libAppImageUpdaterBridge'. | ||
|
||
## Building the Plugin | ||
|
||
``` | ||
$ git clone https://github.com/antony-jr/AppImageUpdaterBridge | ||
$ cd AppImageUpdaterBridge | ||
$ mkdir build | ||
$ cd build | ||
$ cmake -DBUILD_AS_PLUGIN .. | ||
$ make -j$(nproc) | ||
$ export PLUGIN_PATH=$(pwd)/libAppImageUpdaterBridge.so | ||
``` | ||
|
||
## Update.py | ||
|
||
``` | ||
#!/usr/bin/env python3 | ||
import os | ||
import sys | ||
from PyQt5.QtCore import QPluginLoader | ||
from PyQt5.QtCore import QCoreApplication | ||
if len(sys.argv) < 2: | ||
print("Usage: ./Update.py [APPIMAGE PATH]") | ||
sys.exit(0) | ||
app = QCoreApplication(sys.argv) | ||
# Try to load the plugin from predefined | ||
# Qt Plugin paths. | ||
loader = QPluginLoader() | ||
loader.setFileName('libAppImageUpdaterBridge') | ||
if not loader.load(): | ||
try: | ||
plugin_path = os.eviron['PLUGIN_PATH'] | ||
except: | ||
print("Unable to resolve plugin path.") | ||
sys.exit(0) | ||
loader.setFileName(plugin_path) | ||
if not loader.load(): | ||
print("Cannot load plugin because: {}".format(loader.errorString())) | ||
sys.exit(-1) | ||
appimage_path = sys.argv[1] | ||
obj = loader.instance() | ||
def handleFinish(info, old_appimge_path): | ||
print(info) | ||
app.quit() | ||
def handleError(code): | ||
print("A error occured, error code: {}".format(code)) | ||
app.quit() | ||
def handleUpdate(avail): | ||
if avail: | ||
print("A new version of the AppImage is available.") | ||
print("Updating now... ") | ||
obj.start() | ||
else: | ||
print("You have the latest AppImage!") | ||
app.quit() | ||
obj.updateAvailable.connect(handleUpdate) | ||
obj.finished.connect(handleFinish) | ||
obj.error.connect(handleError) | ||
obj.setAppImage(appimage_path) | ||
print("Checking for Update... ") | ||
obj.checkForUpdate() | ||
sys.exit(app.exec_()) | ||
``` | ||
|
||
## Execution | ||
|
||
``` | ||
$ chmod +x Update.py | ||
$ ./Update.py some.AppImage | ||
``` | ||
|
||
See the examples directory in the source tree for more examples. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
#!/usr/bin/env python3 | ||
import os | ||
import sys | ||
from PyQt5.QtCore import QPluginLoader | ||
from PyQt5.QtCore import QCoreApplication | ||
|
||
if len(sys.argv) < 2: | ||
print("Usage: ./Update.py [APPIMAGE PATH]") | ||
sys.exit(0) | ||
|
||
app = QCoreApplication(sys.argv) | ||
|
||
# Try to load the plugin from predefined | ||
# Qt Plugin paths. | ||
loader = QPluginLoader() | ||
loader.setFileName('libAppImageUpdaterBridge') | ||
if not loader.load(): | ||
try: | ||
plugin_path = os.eviron['PLUGIN_PATH'] | ||
except: | ||
print("Unable to resolve plugin path.") | ||
sys.exit(0) | ||
loader.setFileName(plugin_path) | ||
if not loader.load(): | ||
print("Cannot load plugin because: {}".format(loader.errorString())) | ||
sys.exit(-1) | ||
|
||
|
||
appimage_path = sys.argv[1] | ||
obj = loader.instance() | ||
|
||
def handleFinish(info, old_appimge_path): | ||
print(info) | ||
app.quit() | ||
|
||
def handleError(code): | ||
print("A error occured, error code: {}".format(code)) | ||
app.quit() | ||
|
||
def handleUpdate(avail): | ||
if avail: | ||
print("A new version of the AppImage is available.") | ||
print("Updating now... ") | ||
obj.start() | ||
else: | ||
print("You have the latest AppImage!") | ||
app.quit() | ||
|
||
obj.updateAvailable.connect(handleUpdate) | ||
obj.finished.connect(handleFinish) | ||
obj.error.connect(handleError) | ||
|
||
obj.setAppImage(appimage_path) | ||
|
||
print("Checking for Update... ") | ||
obj.checkForUpdate() | ||
sys.exit(app.exec_()) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.