2013-10-28 21:08:36 +00:00
|
|
|
# coding=utf-8
|
2014-08-05 09:26:13 +00:00
|
|
|
from __future__ import absolute_import
|
|
|
|
|
|
2013-10-28 21:08:36 +00:00
|
|
|
__author__ = "Gina Häußge <osd@foosel.net>"
|
|
|
|
|
__license__ = 'GNU Affero General Public License http://www.gnu.org/licenses/agpl.html'
|
2014-08-05 09:26:13 +00:00
|
|
|
__copyright__ = "Copyright (C) 2014 The OctoPrint Project - Released under terms of the AGPLv3 License"
|
2013-10-28 21:08:36 +00:00
|
|
|
|
|
|
|
|
from flask import request, jsonify, abort, make_response
|
2015-01-22 16:59:31 +00:00
|
|
|
from flask.exceptions import JSONBadRequest
|
2013-10-28 21:08:36 +00:00
|
|
|
from flask.ext.login import current_user
|
|
|
|
|
|
|
|
|
|
import octoprint.users as users
|
|
|
|
|
|
2014-08-05 09:26:13 +00:00
|
|
|
from octoprint.server import SUCCESS, admin_permission, userManager
|
2013-12-21 13:46:20 +00:00
|
|
|
from octoprint.server.api import api
|
2014-08-05 09:26:13 +00:00
|
|
|
from octoprint.server.util.flask import restricted_access
|
2013-10-28 21:08:36 +00:00
|
|
|
|
|
|
|
|
|
|
|
|
|
#~~ user settings
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users", methods=["GET"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
@admin_permission.require(403)
|
|
|
|
|
def getUsers():
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
return jsonify({"users": userManager.getAllUsers()})
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users", methods=["POST"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
@admin_permission.require(403)
|
|
|
|
|
def addUser():
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
if not "application/json" in request.headers["Content-Type"]:
|
|
|
|
|
return make_response("Expected content-type JSON", 400)
|
|
|
|
|
|
|
|
|
|
try:
|
2013-10-28 21:08:36 +00:00
|
|
|
data = request.json
|
2015-01-22 16:59:31 +00:00
|
|
|
except JSONBadRequest:
|
|
|
|
|
return make_response("Malformed JSON body in request", 400)
|
2013-10-28 21:08:36 +00:00
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
name = data["name"]
|
|
|
|
|
password = data["password"]
|
|
|
|
|
active = data["active"]
|
2013-10-28 21:08:36 +00:00
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
roles = ["user"]
|
|
|
|
|
if "admin" in data.keys() and data["admin"]:
|
|
|
|
|
roles.append("admin")
|
2013-10-28 21:08:36 +00:00
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
try:
|
|
|
|
|
userManager.addUser(name, password, active, roles)
|
|
|
|
|
except users.UserAlreadyExists:
|
|
|
|
|
abort(409)
|
2013-10-28 21:08:36 +00:00
|
|
|
return getUsers()
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>", methods=["GET"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
def getUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
if current_user is not None and not current_user.is_anonymous() and (current_user.get_name() == username or current_user.is_admin()):
|
|
|
|
|
user = userManager.findUser(username)
|
|
|
|
|
if user is not None:
|
|
|
|
|
return jsonify(user.asDict())
|
|
|
|
|
else:
|
|
|
|
|
abort(404)
|
|
|
|
|
else:
|
|
|
|
|
abort(403)
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>", methods=["PUT"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
@admin_permission.require(403)
|
|
|
|
|
def updateUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
user = userManager.findUser(username)
|
|
|
|
|
if user is not None:
|
2015-01-22 16:59:31 +00:00
|
|
|
if not "application/json" in request.headers["Content-Type"]:
|
|
|
|
|
return make_response("Expected content-type JSON", 400)
|
|
|
|
|
|
|
|
|
|
try:
|
2013-10-28 21:08:36 +00:00
|
|
|
data = request.json
|
2015-01-22 16:59:31 +00:00
|
|
|
except JSONBadRequest:
|
|
|
|
|
return make_response("Malformed JSON body in request", 400)
|
2013-10-28 21:08:36 +00:00
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
# change roles
|
|
|
|
|
roles = ["user"]
|
|
|
|
|
if "admin" in data.keys() and data["admin"]:
|
|
|
|
|
roles.append("admin")
|
|
|
|
|
userManager.changeUserRoles(username, roles)
|
2013-10-28 21:08:36 +00:00
|
|
|
|
2015-01-22 16:59:31 +00:00
|
|
|
# change activation
|
|
|
|
|
if "active" in data.keys():
|
|
|
|
|
userManager.changeUserActivation(username, data["active"])
|
2013-10-28 21:08:36 +00:00
|
|
|
return getUsers()
|
|
|
|
|
else:
|
|
|
|
|
abort(404)
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>", methods=["DELETE"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
@admin_permission.require(http_exception=403)
|
|
|
|
|
def removeUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
try:
|
|
|
|
|
userManager.removeUser(username)
|
|
|
|
|
return getUsers()
|
|
|
|
|
except users.UnknownUser:
|
|
|
|
|
abort(404)
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>/password", methods=["PUT"])
|
2013-10-28 21:08:36 +00:00
|
|
|
@restricted_access
|
|
|
|
|
def changePasswordForUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
if current_user is not None and not current_user.is_anonymous() and (current_user.get_name() == username or current_user.is_admin()):
|
2015-01-22 16:59:31 +00:00
|
|
|
if not "application/json" in request.headers["Content-Type"]:
|
|
|
|
|
return make_response("Expected content-type JSON", 400)
|
|
|
|
|
|
|
|
|
|
try:
|
2013-10-28 21:08:36 +00:00
|
|
|
data = request.json
|
2015-01-22 16:59:31 +00:00
|
|
|
except JSONBadRequest:
|
|
|
|
|
return make_response("Malformed JSON body in request", 400)
|
|
|
|
|
|
|
|
|
|
if not "password" in data.keys() or not data["password"]:
|
|
|
|
|
return make_response("password is missing from request", 400)
|
|
|
|
|
|
|
|
|
|
try:
|
|
|
|
|
userManager.changeUserPassword(username, data["password"])
|
|
|
|
|
except users.UnknownUser:
|
|
|
|
|
return make_response(("Unknown user: %s" % username, 404, []))
|
|
|
|
|
|
2013-10-28 21:08:36 +00:00
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
else:
|
|
|
|
|
return make_response(("Forbidden", 403, []))
|
|
|
|
|
|
2013-11-19 21:53:26 +00:00
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>/apikey", methods=["DELETE"])
|
2013-11-19 21:53:26 +00:00
|
|
|
@restricted_access
|
|
|
|
|
def deleteApikeyForUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
if current_user is not None and not current_user.is_anonymous() and (current_user.get_name() == username or current_user.is_admin()):
|
|
|
|
|
try:
|
|
|
|
|
userManager.deleteApikey(username)
|
|
|
|
|
except users.UnknownUser:
|
|
|
|
|
return make_response(("Unknown user: %s" % username, 404, []))
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
else:
|
|
|
|
|
return make_response(("Forbidden", 403, []))
|
|
|
|
|
|
|
|
|
|
|
2013-12-21 13:46:20 +00:00
|
|
|
@api.route("/users/<username>/apikey", methods=["POST"])
|
2013-11-19 21:53:26 +00:00
|
|
|
@restricted_access
|
|
|
|
|
def generateApikeyForUser(username):
|
|
|
|
|
if userManager is None:
|
|
|
|
|
return jsonify(SUCCESS)
|
|
|
|
|
|
|
|
|
|
if current_user is not None and not current_user.is_anonymous() and (current_user.get_name() == username or current_user.is_admin()):
|
|
|
|
|
try:
|
|
|
|
|
apikey = userManager.generateApiKey(username)
|
|
|
|
|
except users.UnknownUser:
|
|
|
|
|
return make_response(("Unknown user: %s" % username, 404, []))
|
|
|
|
|
return jsonify({"apikey": apikey})
|
|
|
|
|
else:
|
|
|
|
|
return make_response(("Forbidden", 403, []))
|