Upload location is now platform dependent
win32 defaults to %APPDATA%/Cura/uploads macos defaults to ~/Library/Application Support/Cura/uploads (I hope, can't test it...) linux defaults to ~/.cura/uploads Server now also checks if file to be uploaded or deleted ends on .gcode and makes filename secure before doing anything on the filesystem Also added favicon ;) and some bla to the README.mdmaster
parent
909278897c
commit
375fffdd3f
|
@ -2,16 +2,36 @@
|
|||
# coding=utf-8
|
||||
__author__ = 'Gina Häußge <osd@foosel.net>'
|
||||
|
||||
from flask import Flask, request, render_template, jsonify
|
||||
from flask import Flask, request, render_template, jsonify, make_response
|
||||
from werkzeug import secure_filename
|
||||
|
||||
from printer import Printer
|
||||
|
||||
import sys
|
||||
import os
|
||||
import fnmatch
|
||||
|
||||
BASEURL='/ajax/'
|
||||
APPNAME="Cura"
|
||||
BASEURL="/ajax/"
|
||||
SUCCESS={}
|
||||
UPLOAD_FOLDER="uploads"
|
||||
|
||||
# taken from http://stackoverflow.com/questions/1084697/how-do-i-store-desktop-application-data-in-a-cross-platform-way-for-python
|
||||
if sys.platform == 'darwin':
|
||||
from AppKit import NSSearchPathForDirectoriesInDomains
|
||||
# http://developer.apple.com/DOCUMENTATION/Cocoa/Reference/Foundation/Miscellaneous/Foundation_Functions/Reference/reference.html#//apple_ref/c/func/NSSearchPathForDirectoriesInDomains
|
||||
# NSApplicationSupportDirectory = 14
|
||||
# NSUserDomainMask = 1
|
||||
# True for expanding the tilde into a fully qualified path
|
||||
appdata = os.path.join(NSSearchPathForDirectoriesInDomains(14, 1, True)[0], APPNAME)
|
||||
elif sys.platform == 'win32':
|
||||
appdata = os.path.join(os.environ['APPDATA'], APPNAME)
|
||||
else:
|
||||
appdata = os.path.expanduser(os.path.join("~", "." + APPNAME.lower()))
|
||||
|
||||
UPLOAD_FOLDER = appdata + os.sep + "uploads"
|
||||
if not os.path.isdir(UPLOAD_FOLDER):
|
||||
os.makedirs(UPLOAD_FOLDER)
|
||||
ALLOWED_EXTENSIONS = set(["gcode"])
|
||||
|
||||
app = Flask("Cura.webui")
|
||||
printer = Printer()
|
||||
|
@ -63,7 +83,7 @@ def printerMessages():
|
|||
return jsonify(messages=printer.messages)
|
||||
|
||||
@app.route(BASEURL + 'state/log', methods=['GET'])
|
||||
def printerMessages():
|
||||
def printerLogs():
|
||||
return jsonify(log=printer.log)
|
||||
|
||||
@app.route(BASEURL + 'state/temperatures', methods=['GET'])
|
||||
|
@ -164,8 +184,9 @@ def readGcodeFiles():
|
|||
@app.route(BASEURL + 'gcodefiles/upload', methods=['POST'])
|
||||
def uploadGcodeFile():
|
||||
file = request.files['gcode_file']
|
||||
if file != None:
|
||||
filename = UPLOAD_FOLDER + os.sep + file.filename
|
||||
if file and allowed_file(file.filename):
|
||||
secure = secure_filename(file.filename)
|
||||
filename = os.path.join(UPLOAD_FOLDER, secure)
|
||||
file.save(filename)
|
||||
return readGcodeFiles()
|
||||
|
||||
|
@ -177,8 +198,12 @@ def loadGcodeFile():
|
|||
|
||||
@app.route(BASEURL + 'gcodefiles/delete', methods=['POST'])
|
||||
def deleteGcodeFile():
|
||||
if request.values.has_key("filename"):
|
||||
filename = request.values["filename"]
|
||||
os.remove(UPLOAD_FOLDER + os.sep + filename)
|
||||
if allowed_file(filename):
|
||||
secure = UPLOAD_FOLDER + os.sep + secure_filename(filename)
|
||||
if os.path.exists(secure):
|
||||
os.remove(secure)
|
||||
return readGcodeFiles()
|
||||
|
||||
def sizeof_fmt(num):
|
||||
|
@ -191,6 +216,8 @@ def sizeof_fmt(num):
|
|||
num /= 1024.0
|
||||
return "%3.1f%s" % (num, 'TB')
|
||||
|
||||
def allowed_file(filename):
|
||||
return "." in filename and filename.rsplit(".", 1)[1] in ALLOWED_EXTENSIONS
|
||||
|
||||
def run():
|
||||
app.debug = True
|
||||
app.run(host="0.0.0.0")
|
||||
app.run(host="0.0.0.0", port=5000)
|
||||
|
|
|
@ -38,7 +38,7 @@ class Printer():
|
|||
def connect(self):
|
||||
if self.comm != None:
|
||||
self.comm.close()
|
||||
self.comm = machineCom.MachineCom(port="COM4", baudrate=115200, callbackObject=self)
|
||||
self.comm = machineCom.MachineCom(callbackObject=self)
|
||||
|
||||
def disconnect(self):
|
||||
if self.comm != None:
|
||||
|
@ -193,5 +193,5 @@ class Printer():
|
|||
if self.comm == None:
|
||||
return
|
||||
self.comm.cancelPrint()
|
||||
self.comm.sendCommand("M84")
|
||||
self.comm.sendCommands(["M84", "M104 S0", "M140 S0"]) # disable motors, switch off heaters
|
||||
|
||||
|
|
Binary file not shown.
After Width: | Height: | Size: 345 KiB |
|
@ -3,6 +3,8 @@
|
|||
<head>
|
||||
<title>Cura WebUI</title>
|
||||
|
||||
<link rel="shortcut icon" href="{{ url_for('static', filename='img/favicon.ico') }}">
|
||||
|
||||
<link href="{{ url_for('static', filename='css/bootstrap.min.css') }}" rel="stylesheet" media="screen">
|
||||
<link href="{{ url_for('static', filename='css/jquery.fileupload-ui.css') }}" rel="stylesheet" media="screen">
|
||||
<link href="{{ url_for('static', filename='css/ui.css') }}" rel="stylesheet" media="screen">
|
||||
|
|
11
README.md
11
README.md
|
@ -83,3 +83,14 @@ At time of writing, pyobjc 2.5 is not available at pypi. You have to clone repo
|
|||
|
||||
###Packaging
|
||||
To package Cura into application bundle simply do `python setup.py py2app`. Resulting bundle is self-contained -- it includes Python and all needed packages.
|
||||
|
||||
WebUI
|
||||
=====
|
||||
|
||||
This fork of Cura includes a WebUI for remote printing via the browser. It depends on the Python module "flask" and
|
||||
its dependencies "werkzeug", "jinja2" and "itsdangerous", so you'll need those in order to run the WebUI. A simple
|
||||
`pip install -r requirements.txt` or `pip install flask` should take care of that.
|
||||
|
||||
Once installed, you can startup the WebUI instead of the regular Cura UI via the command-line option `--web` or `-w`. The
|
||||
web interface will then be available on port 5000. If you want to change that (or the IP address the server binds to,
|
||||
which currently is `0.0.0.0`), please take a look at the source code of `Cura/webui/__init__.py`.
|
Loading…
Reference in New Issue