Some cleanup, refactoring & docs
This commit is contained in:
parent
5c20e264e2
commit
ca7aa322c3
11 changed files with 284 additions and 169 deletions
|
|
@ -1565,6 +1565,13 @@ class Plugin(object):
|
|||
initialization of the implementation.
|
||||
"""
|
||||
|
||||
def __init__(self):
|
||||
self._identifier = None
|
||||
self._plugin_name = None
|
||||
self._plugin_version = None
|
||||
self._basefolder = None
|
||||
self._logger = None
|
||||
|
||||
def initialize(self):
|
||||
"""
|
||||
Called by the plugin core after performing all injections. Override this to initialize your implementation.
|
||||
|
|
|
|||
|
|
@ -8,9 +8,11 @@ Please note that the plugin implementation types are documented in the section
|
|||
|
||||
.. autoclass:: OctoPrintPlugin
|
||||
:show-inheritance:
|
||||
:members:
|
||||
|
||||
.. autoclass:: ReloadNeedingPlugin
|
||||
:show-inheritance:
|
||||
:members:
|
||||
|
||||
"""
|
||||
|
||||
|
|
@ -23,6 +25,7 @@ __copyright__ = "Copyright (C) 2014 The OctoPrint Project - Released under terms
|
|||
|
||||
from .core import (Plugin, RestartNeedingPlugin, SortablePlugin)
|
||||
|
||||
# noinspection PyCompatibility
|
||||
from past.builtins import basestring
|
||||
|
||||
class OctoPrintPlugin(Plugin):
|
||||
|
|
@ -74,16 +77,39 @@ class OctoPrintPlugin(Plugin):
|
|||
The :class:`~octoprint.server.LifecycleManager` instance. Injected by the plugin core system upon initialization
|
||||
of the implementation.
|
||||
|
||||
.. attribute:: _user_manager
|
||||
|
||||
The :class:`~octoprint.users.UserManager` instance. Injected by the plugin core system upon initialization
|
||||
of the implementation.
|
||||
|
||||
.. attribute:: _connectivity_checker
|
||||
|
||||
The :class:`~octoprint.util.ConnectivityChecker` instance. Injected by the plugin core system upon initialization
|
||||
of the implementation.
|
||||
|
||||
.. attribute:: _data_folder
|
||||
|
||||
Path to the data folder for the plugin to use for any data it might have to persist. Should always be accessed
|
||||
through :meth:`get_plugin_data_folder` since that function will also ensure that the data folder actually exists
|
||||
and if not creating it before returning it. Injected by the plugin core system upon initialization of the
|
||||
implementation.
|
||||
|
||||
.. automethod:: get_plugin_data_folder
|
||||
"""
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._plugin_manager = None
|
||||
self._printer_profile_manager = None
|
||||
self._event_bus = None
|
||||
self._analysis_queue = None
|
||||
self._slicing_manager = None
|
||||
self._file_manager = None
|
||||
self._printer = None
|
||||
self._app_session_manager = None
|
||||
self._plugin_lifecycle_manager = None
|
||||
self._user_manager = None
|
||||
self._connectivity_checker = None
|
||||
self._data_folder = None
|
||||
|
||||
def get_plugin_data_folder(self):
|
||||
"""
|
||||
Retrieves the path to a data folder specifically for the plugin, ensuring it exists and if not creating it
|
||||
|
|
@ -107,10 +133,10 @@ class ReloadNeedingPlugin(Plugin):
|
|||
|
||||
|
||||
class EnvironmentDetectionPlugin(OctoPrintPlugin, RestartNeedingPlugin):
|
||||
|
||||
|
||||
def get_additional_environment(self):
|
||||
pass
|
||||
|
||||
|
||||
def on_environment_detected(self, environment, *args, **kwargs):
|
||||
pass
|
||||
|
||||
|
|
@ -602,6 +628,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
See below for details on this.
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic,PyUnusedLocal
|
||||
def will_handle_ui(self, request):
|
||||
"""
|
||||
Called by OctoPrint to determine if the mixin implementation will be
|
||||
|
|
@ -624,6 +651,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return False
|
||||
|
||||
# noinspection PyMethodMayBeStatic,PyUnusedLocal
|
||||
def on_ui_render(self, now, request, render_kwargs):
|
||||
"""
|
||||
Called by OctoPrint to retrieve the response to send to the client
|
||||
|
|
@ -712,6 +740,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_additional_key_data_for_cache(self):
|
||||
"""
|
||||
Allows to return additional data to use in the cache key.
|
||||
|
|
@ -723,6 +752,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_additional_tracked_files(self):
|
||||
"""
|
||||
Allows to return additional files to track for validating existing caches. By default OctoPrint
|
||||
|
|
@ -735,6 +765,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_custom_tracked_files(self):
|
||||
"""
|
||||
Allows to define a complete separate set of files to track for (in)validating the cache. If this
|
||||
|
|
@ -747,6 +778,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_custom_etag(self):
|
||||
"""
|
||||
Allows to use a custom way to calculate the ETag, instead of the default method (hashing
|
||||
|
|
@ -757,6 +789,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_additional_etag(self, default_additional):
|
||||
"""
|
||||
Allows to provide a list of additional fields to use for ETag generation.
|
||||
|
|
@ -772,6 +805,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return default_additional
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_custom_lastmodified(self):
|
||||
"""
|
||||
Allows to calculate the LastModified differently than using the most recent modification
|
||||
|
|
@ -782,6 +816,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_preemptive_caching_enabled(self):
|
||||
"""
|
||||
Allows to control whether the view provided by the plugin should be preemptively
|
||||
|
|
@ -794,6 +829,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return True
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_data_for_preemptive_caching(self):
|
||||
"""
|
||||
Allows defining additional data to be persisted in the preemptive cache configuration, on
|
||||
|
|
@ -804,6 +840,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_additional_request_data_for_preemptive_caching(self):
|
||||
"""
|
||||
Allows defining additional request data to persist in the preemptive cache configuration and
|
||||
|
|
@ -819,6 +856,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_preemptive_caching_additional_unless(self):
|
||||
"""
|
||||
Allows defining additional reasons for temporarily not adding a preemptive cache record for
|
||||
|
|
@ -832,6 +870,7 @@ class UiPlugin(OctoPrintPlugin, SortablePlugin):
|
|||
"""
|
||||
return False
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_ui_custom_template_filter(self, default_template_filter):
|
||||
"""
|
||||
Allows to specify a custom template filter to use for filtering the template contained in the
|
||||
|
|
@ -916,6 +955,7 @@ class WizardPlugin(OctoPrintPlugin, ReloadNeedingPlugin):
|
|||
``WizardPlugin`` is a :class:`~octoprint.plugin.core.ReloadNeedingPlugin`.
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def is_wizard_required(self):
|
||||
"""
|
||||
Allows the plugin to report whether it needs to display a wizard to the
|
||||
|
|
@ -931,6 +971,7 @@ class WizardPlugin(OctoPrintPlugin, ReloadNeedingPlugin):
|
|||
"""
|
||||
return False
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_wizard_version(self):
|
||||
"""
|
||||
The version of this plugin's wizard. OctoPrint will only display a wizard
|
||||
|
|
@ -950,6 +991,7 @@ class WizardPlugin(OctoPrintPlugin, ReloadNeedingPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_wizard_details(self):
|
||||
"""
|
||||
Called by OctoPrint when the wizard wrapper dialog is shown. Allows the plugin to return data
|
||||
|
|
@ -964,6 +1006,7 @@ class WizardPlugin(OctoPrintPlugin, ReloadNeedingPlugin):
|
|||
"""
|
||||
return dict()
|
||||
|
||||
# noinspection PyMethodMayBeStatic,PyUnusedLocal
|
||||
def on_wizard_finish(self, handled):
|
||||
"""
|
||||
Called by OctoPrint whenever the user finishes a wizard session.
|
||||
|
|
@ -982,6 +1025,7 @@ class WizardPlugin(OctoPrintPlugin, ReloadNeedingPlugin):
|
|||
"""
|
||||
pass
|
||||
|
||||
# noinspection PyProtectedMember
|
||||
@classmethod
|
||||
def is_wizard_ignored(cls, seen_wizards, implementation):
|
||||
"""
|
||||
|
|
@ -1132,6 +1176,7 @@ class SimpleApiPlugin(OctoPrintPlugin):
|
|||
}
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_api_commands(self):
|
||||
"""
|
||||
Return a dictionary here with the keys representing the accepted commands and the values being lists of
|
||||
|
|
@ -1139,12 +1184,14 @@ class SimpleApiPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def is_api_adminonly(self):
|
||||
"""
|
||||
Return True if the API is only available to users having the admin role.
|
||||
"""
|
||||
return False
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_api_command(self, command, data):
|
||||
"""
|
||||
Called by OctoPrint upon a POST request to ``/api/plugin/<plugin identifier>``. ``command`` will contain one of
|
||||
|
|
@ -1164,6 +1211,7 @@ class SimpleApiPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_api_get(self, request):
|
||||
"""
|
||||
Called by OctoPrint upon a GET request to ``/api/plugin/<plugin identifier>``. ``request`` will contain the
|
||||
|
|
@ -1262,6 +1310,7 @@ class BlueprintPlugin(OctoPrintPlugin, RestartNeedingPlugin):
|
|||
return f
|
||||
return decorator
|
||||
|
||||
# noinspection PyProtectedMember
|
||||
def get_blueprint(self):
|
||||
"""
|
||||
Creates and returns the blueprint for your plugin. Override this if you want to define and handle your blueprint yourself.
|
||||
|
|
@ -1327,6 +1376,7 @@ class BlueprintPlugin(OctoPrintPlugin, RestartNeedingPlugin):
|
|||
template_folder=template_folder
|
||||
)
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def is_blueprint_protected(self):
|
||||
"""
|
||||
Whether a valid API key is needed to access the blueprint (the default) or not. Note that this only restricts
|
||||
|
|
@ -1395,16 +1445,19 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
should have access to via :meth:`~octoprint.plugin.SettingsPlugin.get_settings_restricted_paths`. OctoPrint will
|
||||
return its settings on the REST API even to anonymous clients, but will filter out fields it know are restricted,
|
||||
therefore you **must** make sure that you specify sensitive information accordingly to limit access as required!
|
||||
|
||||
.. attribute:: _settings
|
||||
|
||||
The :class:`~octoprint.plugin.PluginSettings` instance to use for accessing the plugin's settings. Injected by
|
||||
the plugin core system upon initialization of the implementation.
|
||||
"""
|
||||
|
||||
config_version_key = "_config_version"
|
||||
"""Key of the field in the settings that holds the configuration format version."""
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._settings = None
|
||||
"""
|
||||
The :class:`~octoprint.plugin.PluginSettings` instance to use for accessing the plugin's settings. Injected by
|
||||
the plugin core system upon initialization of the implementation.
|
||||
"""
|
||||
|
||||
def on_settings_load(self):
|
||||
"""
|
||||
Loads the settings for the plugin, called by the Settings API view in order to retrieve all settings from
|
||||
|
|
@ -1437,6 +1490,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
|
||||
restricted_paths = self.get_settings_restricted_paths()
|
||||
|
||||
# noinspection PyShadowingNames
|
||||
def restrict_path_unless(data, path, condition):
|
||||
if not path:
|
||||
return
|
||||
|
|
@ -1535,6 +1589,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
|
||||
return diff
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_settings_defaults(self):
|
||||
"""
|
||||
Retrieves the plugin's default settings with which the plugin's settings manager will be initialized.
|
||||
|
|
@ -1544,6 +1599,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return dict()
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_settings_restricted_paths(self):
|
||||
"""
|
||||
Retrieves the list of paths in the plugin's settings which be restricted on the REST API.
|
||||
|
|
@ -1598,6 +1654,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return dict()
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_settings_preprocessors(self):
|
||||
"""
|
||||
Retrieves the plugin's preprocessors to use for preprocessing returned or set values prior to returning/setting
|
||||
|
|
@ -1635,6 +1692,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return dict(), dict()
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_settings_version(self):
|
||||
"""
|
||||
Retrieves the settings format version of the plugin.
|
||||
|
|
@ -1649,6 +1707,7 @@ class SettingsPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_settings_migrate(self, target, current):
|
||||
"""
|
||||
Called by OctoPrint if it detects that the installed version of the plugin necessitates a higher settings version
|
||||
|
|
@ -1735,6 +1794,7 @@ class EventHandlerPlugin(OctoPrintPlugin):
|
|||
videos rendering etc.
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_event(self, event, payload):
|
||||
"""
|
||||
Called by OctoPrint upon processing of a fired event on the platform.
|
||||
|
|
@ -1753,6 +1813,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def is_slicer_configured(self):
|
||||
"""
|
||||
Unless the return value of this method is ``True``, OctoPrint will not register the slicer within the slicing
|
||||
|
|
@ -1762,6 +1823,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return False
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_slicer_properties(self):
|
||||
"""
|
||||
Plugins should override this method to return a ``dict`` containing a bunch of meta data about the implemented slicer.
|
||||
|
|
@ -1799,6 +1861,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
destination_extensions=["gco", "gcode", "g"]
|
||||
)
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_slicer_default_profile(self):
|
||||
"""
|
||||
Should return a :class:`~octoprint.slicing.SlicingProfile` containing the default slicing profile to use with
|
||||
|
|
@ -1810,6 +1873,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_slicer_profile(self, path):
|
||||
"""
|
||||
Should return a :class:`~octoprint.slicing.SlicingProfile` parsed from the slicing profile stored at the
|
||||
|
|
@ -1823,6 +1887,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
return None
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def save_slicer_profile(self, path, profile, allow_overwrite=True, overrides=None):
|
||||
"""
|
||||
Should save the provided :class:`~octoprint.slicing.SlicingProfile` to the indicated ``path``, after applying
|
||||
|
|
@ -1839,6 +1904,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
pass
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def do_slice(self, model_path, printer_profile, machinecode_path=None, profile_path=None, position=None, on_progress=None, on_progress_args=None, on_progress_kwargs=None):
|
||||
"""
|
||||
Called by OctoPrint to slice ``model_path`` for the indicated ``printer_profile``. If the ``machinecode_path`` is ``None``,
|
||||
|
|
@ -1895,6 +1961,7 @@ class SlicerPlugin(OctoPrintPlugin):
|
|||
"""
|
||||
pass
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def cancel_slicing(self, machinecode_path):
|
||||
"""
|
||||
Cancels the slicing to the indicated file.
|
||||
|
|
@ -1911,16 +1978,18 @@ class ProgressPlugin(OctoPrintPlugin):
|
|||
limited to minimally 1% steps.
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_print_progress(self, storage, path, progress):
|
||||
"""
|
||||
Called by OctoPrint on minimally 1% increments during a running print job.
|
||||
|
||||
:param string location: Location of the file
|
||||
:param string storage: Location of the file
|
||||
:param string path: Path of the file
|
||||
:param int progress: Current progress as a value between 0 and 100
|
||||
"""
|
||||
pass
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def on_slicing_progress(self, slicer, source_location, source_path, destination_location, destination_path, progress):
|
||||
"""
|
||||
Called by OctoPrint on minimally 1% increments during a running slicing job.
|
||||
|
|
@ -1946,6 +2015,7 @@ class AppPlugin(OctoPrintPlugin):
|
|||
|
||||
"""
|
||||
|
||||
# noinspection PyMethodMayBeStatic
|
||||
def get_additional_apps(self):
|
||||
return []
|
||||
|
||||
|
|
|
|||
|
|
@ -33,6 +33,7 @@ class AnnouncementPlugin(octoprint.plugin.AssetPlugin,
|
|||
octoprint.plugin.TemplatePlugin,
|
||||
octoprint.plugin.EventHandlerPlugin):
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._cached_channel_configs = None
|
||||
self._cached_channel_configs_mutex = threading.RLock()
|
||||
|
|
@ -184,6 +185,7 @@ class AnnouncementPlugin(octoprint.plugin.AssetPlugin,
|
|||
|
||||
return hash.hexdigest()
|
||||
|
||||
# noinspection PyShadowingNames
|
||||
def condition(lm, etag):
|
||||
return check_etag(etag)
|
||||
|
||||
|
|
|
|||
|
|
@ -1,22 +1,21 @@
|
|||
# coding=utf-8
|
||||
from __future__ import absolute_import, division, print_function
|
||||
|
||||
__author__ = "Gina Häußge <osd@foosel.net>"
|
||||
__license__ = 'GNU Affero General Public License http://www.gnu.org/licenses/agpl.html'
|
||||
__copyright__ = "Copyright (C) 2015 The OctoPrint Project - Released under terms of the AGPLv3 License"
|
||||
|
||||
|
||||
import octoprint.plugin
|
||||
|
||||
|
||||
from flask.ext.babel import gettext
|
||||
from .subwizards import Subwizards
|
||||
|
||||
|
||||
class CoreWizardPlugin(octoprint.plugin.AssetPlugin,
|
||||
octoprint.plugin.TemplatePlugin,
|
||||
octoprint.plugin.WizardPlugin,
|
||||
octoprint.plugin.SettingsPlugin,
|
||||
octoprint.plugin.BlueprintPlugin):
|
||||
octoprint.plugin.BlueprintPlugin,
|
||||
Subwizards):
|
||||
|
||||
#~~ TemplatePlugin API
|
||||
|
||||
|
|
@ -34,6 +33,9 @@ class CoreWizardPlugin(octoprint.plugin.AssetPlugin,
|
|||
|
||||
result = list()
|
||||
for key, method in required.items():
|
||||
if not callable(method):
|
||||
continue
|
||||
|
||||
if not method():
|
||||
continue
|
||||
|
||||
|
|
@ -92,135 +94,7 @@ class CoreWizardPlugin(octoprint.plugin.AssetPlugin,
|
|||
return result
|
||||
|
||||
def get_wizard_version(self):
|
||||
return 2
|
||||
|
||||
#~~ ACL subwizard
|
||||
|
||||
def _is_acl_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_acl_wizard_required(self):
|
||||
return self._user_manager.enabled and not self._user_manager.hasBeenCustomized()
|
||||
|
||||
def _get_acl_wizard_details(self):
|
||||
return dict(required=self._is_acl_wizard_required())
|
||||
|
||||
def _get_acl_wizard_name(self):
|
||||
return gettext("Access Control")
|
||||
|
||||
def _get_acl_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_acl_wizard_required())
|
||||
|
||||
@octoprint.plugin.BlueprintPlugin.route("/acl", methods=["POST"])
|
||||
def acl_wizard_api(self):
|
||||
from flask import request
|
||||
from octoprint.server.api import valid_boolean_trues, NO_CONTENT
|
||||
|
||||
data = request.values
|
||||
if hasattr(request, "json") and request.json:
|
||||
data = request.json
|
||||
|
||||
if "ac" in data and data["ac"] in valid_boolean_trues and \
|
||||
"user" in data.keys() and "pass1" in data.keys() and \
|
||||
"pass2" in data.keys() and data["pass1"] == data["pass2"]:
|
||||
# configure access control
|
||||
self._settings.global_set_boolean(["accessControl", "enabled"], True)
|
||||
self._user_manager.enable()
|
||||
self._user_manager.addUser(data["user"], data["pass1"], True, ["user", "admin"], overwrite=True)
|
||||
elif "ac" in data.keys() and not data["ac"] in valid_boolean_trues:
|
||||
# disable access control
|
||||
self._settings.global_set_boolean(["accessControl", "enabled"], False)
|
||||
|
||||
octoprint.server.loginManager.anonymous_user = octoprint.users.DummyUser
|
||||
octoprint.server.principals.identity_loaders.appendleft(octoprint.users.dummy_identity_loader)
|
||||
|
||||
self._user_manager.disable()
|
||||
self._settings.save()
|
||||
return NO_CONTENT
|
||||
|
||||
#~~ Webcam subwizard
|
||||
|
||||
def _is_webcam_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_webcam_wizard_required(self):
|
||||
webcam_snapshot_url = self._settings.global_get(["webcam", "snapshot"])
|
||||
webcam_stream_url = self._settings.global_get(["webcam", "stream"])
|
||||
ffmpeg_path = self._settings.global_get(["webcam", "ffmpeg"])
|
||||
|
||||
return not (webcam_snapshot_url and webcam_stream_url and ffmpeg_path)
|
||||
|
||||
def _get_webcam_wizard_details(self):
|
||||
return dict(required=self._is_webcam_wizard_required())
|
||||
|
||||
def _get_webcam_wizard_name(self):
|
||||
return gettext("Webcam & Timelapse")
|
||||
|
||||
#~~ Server commands subwizard
|
||||
|
||||
def _is_servercommands_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_servercommands_wizard_required(self):
|
||||
system_shutdown_command = self._settings.global_get(["server", "commands", "systemShutdownCommand"])
|
||||
system_restart_command = self._settings.global_get(["server", "commands", "systemRestartCommand"])
|
||||
server_restart_command = self._settings.global_get(["server", "commands", "serverRestartCommand"])
|
||||
|
||||
return not (system_shutdown_command and system_restart_command and server_restart_command)
|
||||
|
||||
def _get_servercommands_wizard_details(self):
|
||||
return dict(required=self._is_servercommands_wizard_required())
|
||||
|
||||
def _get_servercommands_wizard_name(self):
|
||||
return gettext("Server Commands")
|
||||
|
||||
#~~ Online check subwizard
|
||||
|
||||
def _is_onlinecheck_wizard_firstrunonly(self):
|
||||
return False
|
||||
|
||||
def _is_onlinecheck_wizard_required(self):
|
||||
return self._settings.global_get(["server", "onlineCheck", "enabled"]) is None
|
||||
|
||||
def _get_onlinecheck_wizard_details(self):
|
||||
return dict(required=self._is_onlinecheck_wizard_required())
|
||||
|
||||
def _get_onlinecheck_wizard_name(self):
|
||||
return gettext("Online connectivity check")
|
||||
|
||||
def _get_onlinecheck_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_onlinecheck_wizard_required())
|
||||
|
||||
#~~ Plugin blacklist subwizard
|
||||
|
||||
def _is_pluginblacklist_wizard_firstrunonly(self):
|
||||
return False
|
||||
|
||||
def _is_pluginblacklist_wizard_required(self):
|
||||
return self._settings.global_get(["server", "pluginBlacklist", "enabled"]) is None
|
||||
|
||||
def _get_pluginblacklist_wizard_details(self):
|
||||
return dict(required=self._is_pluginblacklist_wizard_required())
|
||||
|
||||
def _get_pluginblacklist_wizard_name(self):
|
||||
return gettext("Plugin blacklist")
|
||||
|
||||
def _get_pluginblacklist_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_pluginblacklist_wizard_required())
|
||||
|
||||
#~~ Printer profile subwizard
|
||||
|
||||
def _is_printerprofile_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_printerprofile_wizard_required(self):
|
||||
return self._printer_profile_manager.is_default_unmodified() and self._printer_profile_manager.profile_count == 1
|
||||
|
||||
def _get_printerprofile_wizard_details(self):
|
||||
return dict(required=self._is_printerprofile_wizard_required())
|
||||
|
||||
def _get_printerprofile_wizard_name(self):
|
||||
return gettext("Default Printer Profile")
|
||||
return 3
|
||||
|
||||
#~~ helpers
|
||||
|
||||
|
|
|
|||
154
src/octoprint/plugins/corewizard/subwizards.py
Normal file
154
src/octoprint/plugins/corewizard/subwizards.py
Normal file
|
|
@ -0,0 +1,154 @@
|
|||
# coding=utf-8
|
||||
from __future__ import absolute_import, division, print_function
|
||||
|
||||
__license__ = 'GNU Affero General Public License http://www.gnu.org/licenses/agpl.html'
|
||||
__copyright__ = "Copyright (C) 2015 The OctoPrint Project - Released under terms of the AGPLv3 License"
|
||||
|
||||
import octoprint.plugin
|
||||
|
||||
import sys
|
||||
import inspect
|
||||
from flask.ext.babel import gettext
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class ServerCommandsSubwizard(object):
|
||||
def _is_servercommands_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_servercommands_wizard_required(self):
|
||||
system_shutdown_command = self._settings.global_get(["server", "commands", "systemShutdownCommand"])
|
||||
system_restart_command = self._settings.global_get(["server", "commands", "systemRestartCommand"])
|
||||
server_restart_command = self._settings.global_get(["server", "commands", "serverRestartCommand"])
|
||||
|
||||
return not (system_shutdown_command and system_restart_command and server_restart_command)
|
||||
|
||||
def _get_servercommands_wizard_details(self):
|
||||
return dict(required=self._is_servercommands_wizard_required())
|
||||
|
||||
def _get_servercommands_wizard_name(self):
|
||||
return gettext("Server Commands")
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class WebcamSubwizard(object):
|
||||
def _is_webcam_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_webcam_wizard_required(self):
|
||||
webcam_snapshot_url = self._settings.global_get(["webcam", "snapshot"])
|
||||
webcam_stream_url = self._settings.global_get(["webcam", "stream"])
|
||||
ffmpeg_path = self._settings.global_get(["webcam", "ffmpeg"])
|
||||
|
||||
return not (webcam_snapshot_url and webcam_stream_url and ffmpeg_path)
|
||||
|
||||
def _get_webcam_wizard_details(self):
|
||||
return dict(required=self._is_webcam_wizard_required())
|
||||
|
||||
def _get_webcam_wizard_name(self):
|
||||
return gettext("Webcam & Timelapse")
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class AclSubwizard(object):
|
||||
def _is_acl_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_acl_wizard_required(self):
|
||||
return self._user_manager.enabled and not self._user_manager.hasBeenCustomized()
|
||||
|
||||
def _get_acl_wizard_details(self):
|
||||
return dict(required=self._is_acl_wizard_required())
|
||||
|
||||
def _get_acl_wizard_name(self):
|
||||
return gettext("Access Control")
|
||||
|
||||
def _get_acl_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_acl_wizard_required())
|
||||
|
||||
@octoprint.plugin.BlueprintPlugin.route("/acl", methods=["POST"])
|
||||
def acl_wizard_api(self):
|
||||
from flask import request, abort
|
||||
from octoprint.server.api import valid_boolean_trues, NO_CONTENT
|
||||
|
||||
if not self._settings.global_get(["server", "firstRun"]) or self._user_manager.hasBeenCustomized():
|
||||
abort(404)
|
||||
|
||||
data = request.values
|
||||
if hasattr(request, "json") and request.json:
|
||||
data = request.json
|
||||
|
||||
if "ac" in data and data["ac"] in valid_boolean_trues and \
|
||||
"user" in data.keys() and "pass1" in data.keys() and \
|
||||
"pass2" in data.keys() and data["pass1"] == data["pass2"]:
|
||||
# configure access control
|
||||
self._settings.global_set_boolean(["accessControl", "enabled"], True)
|
||||
self._user_manager.enable()
|
||||
self._user_manager.addUser(data["user"], data["pass1"], True, ["user", "admin"], overwrite=True)
|
||||
elif "ac" in data.keys() and not data["ac"] in valid_boolean_trues:
|
||||
# disable access control
|
||||
self._settings.global_set_boolean(["accessControl", "enabled"], False)
|
||||
|
||||
octoprint.server.loginManager.anonymous_user = octoprint.users.DummyUser
|
||||
octoprint.server.principals.identity_loaders.appendleft(octoprint.users.dummy_identity_loader)
|
||||
|
||||
self._user_manager.disable()
|
||||
self._settings.save()
|
||||
return NO_CONTENT
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class OnlineCheckSubwizard(object):
|
||||
def _is_onlinecheck_wizard_firstrunonly(self):
|
||||
return False
|
||||
|
||||
def _is_onlinecheck_wizard_required(self):
|
||||
return self._settings.global_get(["server", "onlineCheck", "enabled"]) is None
|
||||
|
||||
def _get_onlinecheck_wizard_details(self):
|
||||
return dict(required=self._is_onlinecheck_wizard_required())
|
||||
|
||||
def _get_onlinecheck_wizard_name(self):
|
||||
return gettext("Online connectivity check")
|
||||
|
||||
def _get_onlinecheck_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_onlinecheck_wizard_required())
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class PluginBlacklistSubwizard(object):
|
||||
def _is_pluginblacklist_wizard_firstrunonly(self):
|
||||
return False
|
||||
|
||||
def _is_pluginblacklist_wizard_required(self):
|
||||
return self._settings.global_get(["server", "pluginBlacklist", "enabled"]) is None
|
||||
|
||||
def _get_pluginblacklist_wizard_details(self):
|
||||
return dict(required=self._is_pluginblacklist_wizard_required())
|
||||
|
||||
def _get_pluginblacklist_wizard_name(self):
|
||||
return gettext("Plugin blacklist")
|
||||
|
||||
def _get_pluginblacklist_additional_wizard_template_data(self):
|
||||
return dict(mandatory=self._is_pluginblacklist_wizard_required())
|
||||
|
||||
|
||||
# noinspection PyUnresolvedReferences,PyMethodMayBeStatic
|
||||
class PrinterProfileSubwizard(object):
|
||||
def _is_printerprofile_wizard_firstrunonly(self):
|
||||
return True
|
||||
|
||||
def _is_printerprofile_wizard_required(self):
|
||||
return self._printer_profile_manager.is_default_unmodified() and self._printer_profile_manager.profile_count == 1
|
||||
|
||||
def _get_printerprofile_wizard_details(self):
|
||||
return dict(required=self._is_printerprofile_wizard_required())
|
||||
|
||||
def _get_printerprofile_wizard_name(self):
|
||||
return gettext("Default Printer Profile")
|
||||
|
||||
|
||||
Subwizards = type("Subwizwards",
|
||||
tuple(cls for clsname, cls in inspect.getmembers(sys.modules[__name__], inspect.isclass)
|
||||
if clsname.endswith("Subwizard")),
|
||||
dict())
|
||||
|
|
@ -31,6 +31,7 @@ class CuraPlugin(octoprint.plugin.SlicerPlugin,
|
|||
octoprint.plugin.StartupPlugin,
|
||||
octoprint.plugin.WizardPlugin):
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._logger = logging.getLogger("octoprint.plugins.cura")
|
||||
self._cura_logger = logging.getLogger("octoprint.plugins.cura.engine")
|
||||
|
|
@ -79,7 +80,7 @@ class CuraPlugin(octoprint.plugin.SlicerPlugin,
|
|||
self._cura_logger.addHandler(cura_logging_handler)
|
||||
self._cura_logger.setLevel(logging.DEBUG if self._settings.get_boolean(["debug_logging"]) else logging.CRITICAL)
|
||||
self._cura_logger.propagate = False
|
||||
|
||||
|
||||
engine = self._settings.get(["cura_engine"])
|
||||
if not self._is_engine_configured(cura_engine=engine):
|
||||
self._logger.info("Path to CuraEngine has not been configured or does not exist (currently set to %r), "
|
||||
|
|
@ -519,6 +520,7 @@ def _get_usage_from_length(filament_length, filament_diameter):
|
|||
|
||||
return usage
|
||||
|
||||
|
||||
__plugin_name__ = "CuraEngine (<= 15.04)"
|
||||
__plugin_author__ = "Gina Häußge"
|
||||
__plugin_url__ = "http://docs.octoprint.org/en/master/bundledplugins/cura.html"
|
||||
|
|
|
|||
|
|
@ -8,7 +8,9 @@ __copyright__ = "Copyright (C) 2014 The OctoPrint Project - Released under terms
|
|||
|
||||
import re
|
||||
|
||||
# noinspection PyCompatibility
|
||||
from builtins import range
|
||||
# noinspection PyCompatibility
|
||||
from past.builtins import basestring
|
||||
|
||||
class SupportLocationTypes(object):
|
||||
|
|
|
|||
|
|
@ -10,9 +10,10 @@ The SSDP/UPNP implementations has been largely inspired by https://gist.github.c
|
|||
"""
|
||||
|
||||
import logging
|
||||
import os
|
||||
import flask
|
||||
from flask.ext.babel import gettext
|
||||
|
||||
# noinspection PyCompatibility
|
||||
from builtins import range
|
||||
|
||||
import octoprint.plugin
|
||||
|
|
@ -24,14 +25,6 @@ except:
|
|||
pybonjour = False
|
||||
|
||||
|
||||
__plugin_name__ = "Discovery"
|
||||
__plugin_author__ = "Gina Häußge"
|
||||
__plugin_url__ = "http://docs.octoprint.org/en/master/bundledplugins/discovery.html"
|
||||
__plugin_description__ = "Makes the OctoPrint instance discoverable via Bonjour/Avahi/Zeroconf and uPnP"
|
||||
__plugin_disabling_discouraged__ = gettext("Without this plugin your OctoPrint instance will no longer be "
|
||||
"discoverable on the network via Bonjour and uPnP.")
|
||||
__plugin_license__ = "AGPLv3"
|
||||
|
||||
def __plugin_load__():
|
||||
if not pybonjour:
|
||||
# no pybonjour available, we can't use that
|
||||
|
|
@ -62,6 +55,7 @@ class DiscoveryPlugin(octoprint.plugin.StartupPlugin,
|
|||
|
||||
ssdp_multicast_port = 1900
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self.host = None
|
||||
self.port = None
|
||||
|
|
@ -685,3 +679,12 @@ class DiscoveryPlugin(octoprint.plugin.StartupPlugin,
|
|||
else:
|
||||
import socket
|
||||
return u"OctoPrint instance on {}".format(socket.gethostname())
|
||||
|
||||
|
||||
__plugin_name__ = "Discovery"
|
||||
__plugin_author__ = "Gina Häußge"
|
||||
__plugin_url__ = "http://docs.octoprint.org/en/master/bundledplugins/discovery.html"
|
||||
__plugin_description__ = "Makes the OctoPrint instance discoverable via Bonjour/Avahi/Zeroconf and uPnP"
|
||||
__plugin_disabling_discouraged__ = gettext("Without this plugin your OctoPrint instance will no longer be "
|
||||
"discoverable on the network via Bonjour and uPnP.")
|
||||
__plugin_license__ = "AGPLv3"
|
||||
|
|
|
|||
|
|
@ -91,6 +91,7 @@ class OctoPiSupportPlugin(octoprint.plugin.EnvironmentDetectionPlugin,
|
|||
octoprint.plugin.AssetPlugin,
|
||||
octoprint.plugin.TemplatePlugin):
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._version = None
|
||||
self._cpuinfo = None
|
||||
|
|
|
|||
|
|
@ -12,14 +12,13 @@ import octoprint.plugin.core
|
|||
|
||||
from octoprint.settings import valid_boolean_trues
|
||||
from octoprint.server.util.flask import restricted_access, with_revalidation_checking, check_etag
|
||||
from octoprint.server import admin_permission, VERSION
|
||||
from octoprint.util.pip import LocalPipCaller, UnknownPip
|
||||
from octoprint.server import admin_permission
|
||||
from octoprint.util.pip import LocalPipCaller
|
||||
from octoprint.util.version import get_octoprint_version_string, get_octoprint_version, is_octoprint_compatible
|
||||
from octoprint.util.platform import get_os
|
||||
|
||||
from flask import jsonify, make_response
|
||||
from flask.ext.babel import gettext
|
||||
from collections import OrderedDict
|
||||
|
||||
import logging
|
||||
import sarge
|
||||
|
|
@ -27,7 +26,6 @@ import sys
|
|||
import requests
|
||||
import re
|
||||
import os
|
||||
import pkg_resources
|
||||
import copy
|
||||
import dateutil.parser
|
||||
import time
|
||||
|
|
@ -44,7 +42,7 @@ class PluginManagerPlugin(octoprint.plugin.SimpleApiPlugin,
|
|||
octoprint.plugin.EventHandlerPlugin):
|
||||
|
||||
ARCHIVE_EXTENSIONS = (".zip", ".tar.gz", ".tgz", ".tar")
|
||||
|
||||
|
||||
# valid pip install URL schemes according to https://pip.pypa.io/en/stable/reference/pip_install/
|
||||
URL_SCHEMES = ("http", "https", "git",
|
||||
"git+http", "git+https", "git+ssh", "git+git",
|
||||
|
|
@ -61,6 +59,7 @@ class PluginManagerPlugin(octoprint.plugin.SimpleApiPlugin,
|
|||
|
||||
RECONNECT_HOOKS = ["octoprint.comm.protocol.*",]
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._pending_enable = set()
|
||||
self._pending_disable = set()
|
||||
|
|
@ -313,7 +312,7 @@ class PluginManagerPlugin(octoprint.plugin.SimpleApiPlugin,
|
|||
if url is not None:
|
||||
if not any(map(lambda scheme: url.startswith(scheme + "://"), self.URL_SCHEMES)):
|
||||
raise ValueError("Invalid URL to pip install from")
|
||||
|
||||
|
||||
source = url
|
||||
source_type = "url"
|
||||
already_installed_check = lambda line: url in line
|
||||
|
|
|
|||
|
|
@ -15,8 +15,8 @@ import time
|
|||
import logging
|
||||
import logging.handlers
|
||||
import hashlib
|
||||
import traceback
|
||||
|
||||
# noinspection PyCompatibility
|
||||
from concurrent import futures
|
||||
|
||||
from . import version_checks, updaters, exceptions, util, cli
|
||||
|
|
@ -41,9 +41,10 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
octoprint.plugin.EventHandlerPlugin):
|
||||
|
||||
COMMIT_TRACKING_TYPES = ("github_commit", "bitbucket_commit")
|
||||
|
||||
|
||||
DATA_FORMAT_VERSION = "v2"
|
||||
|
||||
# noinspection PyMissingConstructor
|
||||
def __init__(self):
|
||||
self._update_in_progress = False
|
||||
self._configured_checks_mutex = threading.Lock()
|
||||
|
|
@ -343,7 +344,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
|
||||
if "octoprint_type" in data:
|
||||
octoprint_type = data["octoprint_type"]
|
||||
|
||||
|
||||
if octoprint_type == "github_release":
|
||||
self._settings.set(["checks", "octoprint", "type"], octoprint_type, defaults=defaults, force=True)
|
||||
self._settings.set(["checks", "octoprint", "method"], "pip", defaults=defaults, force=True)
|
||||
|
|
@ -364,7 +365,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
self._settings.set(["checks", "octoprint", "prerelease"], False, defaults=defaults, force=True)
|
||||
self._settings.set(["checks", "octoprint", "prerelease_channel"], None, defaults=defaults, force=True)
|
||||
updated_octoprint_check_config = True
|
||||
|
||||
|
||||
if updated_octoprint_check_config:
|
||||
self._refresh_configured_checks = True
|
||||
try:
|
||||
|
|
@ -381,11 +382,11 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
if current is None or current < 6:
|
||||
# up until & including config version 5 we didn't set the method parameter for the octoprint check
|
||||
# configuration
|
||||
|
||||
|
||||
configured_checks = self._settings.get(["checks"], incl_defaults=False)
|
||||
if configured_checks is not None and "octoprint" in configured_checks:
|
||||
octoprint_check = dict(configured_checks["octoprint"])
|
||||
|
||||
|
||||
if not "method" in octoprint_check and octoprint_check.get("type") == "git_commit":
|
||||
defaults = dict(plugins=dict(softwareupdate=dict(checks=dict(octoprint=dict(method="pip")))))
|
||||
self._settings.set(["checks", "octoprint", "method"], "update_script", defaults=defaults)
|
||||
|
|
@ -698,7 +699,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
releaseNotes=release_notes,
|
||||
online=target_online,
|
||||
error=target_error)
|
||||
|
||||
|
||||
if target == "octoprint" and "released_version" in populated_check:
|
||||
information[target]["released_version"] = populated_check["released_version"]
|
||||
|
||||
|
|
@ -1023,7 +1024,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
# we compare versions fully, not just the base so that we see a difference
|
||||
# between RCs + stable for the same version release
|
||||
result["force_base"] = False
|
||||
|
||||
|
||||
if check.get("prerelease", None):
|
||||
# we are tracking prereleases => we want to be on the correct prerelease channel/branch
|
||||
channel = check.get("prerelease_channel", None)
|
||||
|
|
@ -1031,7 +1032,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
# if we have a release channel, we also set our update_branch here to our release channel
|
||||
# in case it's not already set
|
||||
result["update_branch"] = check.get("update_branch", channel)
|
||||
|
||||
|
||||
else:
|
||||
# we are not tracking prereleases, but aren't on the stable branch either => switch back
|
||||
# to stable branch on update
|
||||
|
|
@ -1049,7 +1050,7 @@ class SoftwareUpdatePlugin(octoprint.plugin.BlueprintPlugin,
|
|||
# branch of the release channel - unequality means we might have to handle
|
||||
# a downgrade
|
||||
result["release_compare"] = "python_unequal"
|
||||
|
||||
|
||||
elif check.get("pip", None):
|
||||
# we force python unequality check for pip installs, to be able to downgrade
|
||||
result["release_compare"] = "python_unequal"
|
||||
|
|
|
|||
Loading…
Reference in a new issue