Serving index.html from tornado web server - python

I'm trying to write a web application and am using Tornado Web for the json xhr calls. But I'm trying to serve a static index.html which is to serve the main app.
How can I serve a simple page and still have requesthandlers for the rest of my application?
Here's what I tried so far:
import tornado.ioloop
import tornado.web
import json
import os
games = [...]
class HomeHandler(tornado.web.RequestHandler):
def get(self):
self.render('index.html')
class MatchHandler(tornado.web.RequestHandler):
def get(self):
self.write(json.dumps(games))
path = os.path.join(os.getcwd(), 'app')
if __name__ == "__main__":
application = tornado.web.Application(
[
(r'/', HomeHandler),
(r'/games', MatchHandler),
(r'/*.*', tornado.web.StaticFileHandler, {'path': path})
],
template_path=os.path.join(os.path.dirname(__file__), 'app')
)
application.listen(16001)
tornado.ioloop.IOLoop.current().start()
Thanks in advance!

The StaticFileHandler regex needs to A) contain a capturing group and B) use regex syntax instead of glob syntax:
(r'/(.*\..*)', tornado.web.StaticFileHandler, {'path': path})
This will match any paths containing a dot and send it to the StaticFileHandler.

Your code looks correct to me. Put a file named "index.html" in the "app" subdirectory of your current working directory when you run the app, and the contents of that "index.html" will be the response when you visit http://localhost:16001/

Your code should work fine, as #a-jesse-jiryu-davis answered. To expand a bit on it, you could use tornado.web.StaticFileHandler if you just need to serve your static file. This will make it more flexible, and also take advantage of server-side caching etc.

Related

How would I serve this html file with Flask (nota a template)

I'm using apidoc to generate a documentation website. On running, it creates a folder called doc, which contains an index.html file and accompanying css and js.
I'd like to be able to serve this folder with a Flask server, but can't work out how to do it.
My folder structure looks like this
-root
--- doc/ #contains all of the static stuff
--- server.py
I've tried this, but can't get it to work:
app = Flask(__name__, static_url_path="/doc")
#app.route('/')
def root():
return app.send_from_directory('index.html')
One of the problems is that all of the static files referenced in the index.html generated by apidoc are relative to that page, so /js/etc. doesn't work, since it's actually /doc/js...
It would be great if someone could help me with the syntax here. Thanks.
I spot three problems in code.
a) you do not need to use static_url_path, as send_from_directory is independent of it
b) when I try to run above code, and go to /, I get a AttributeError: 'Flask' object has no attribute 'send_from_directory' - this means translates to app.send_from_directory is wrong - you need to import this function from flask, ie from flask import send_from_directory
c) when I then try to run your code, I get a TypeError: send_from_directory() missing 1 required positional argument: 'filename', which means send_from_directory needs another argument; it needs both a directory and a file
Putting this all together you get something like this:
from flask import Flask
from flask import send_from_directory
app = Flask(__name__)
#app.route("/")
def index():
return send_from_directory("doc", "index.html")
As a takeway (for myself):
reading the documentation helps a lot ( https://flask.palletsprojects.com/en/1.1.x/api/ )
having a close look at the - at first scary - error messages gives really good hints on what to do

How to custom 404 error page load subfolders using cherrypy

I would like to override 404 error page showed in cherrypy to my custom error page. The challenge is to read all subfolders inside the directory that contain my index.html. These subfolders are img, css, js...
According to cherrypy documentation I found that I can custom a 404 error page overriding this function and doing a cherrypy.config.update in the following form:
_cp_config = {
'error_page.404': os.path.join(localDir, "static/index.html")
}
I customised the page with success and cherrypy load my html with success.
Here is my code that loads the html (but not the subdirectories inside that folder).
import cherrypy
import os
from django.core.wsgi import get_wsgi_application
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "myapp.settings")
application = get_wsgi_application()
WEBAPP = "/app-web/"
CONF_WEBAPP = {'/':
{'tools.staticdir.on': True,
'tools.staticdir.dir': WEBAPP,
'tools.staticdir.index': 'index.html'}}
WEB_ROOT = '/webclient/'
class ServeWebApp(object):
#cherrypy.expose
def index(self):
pass
if __name__ == '__main__':
cherrypy.tree.graft(application, '/')
cherrypy.tree.mount(ServeWebApp(), '/webapp', config=CONF_WEBAPP)
cherrypy.config.update({'error_page.404': os.path.join(WEB_ROOT, "index.html")})
cherrypy.server.socket_host = "0.0.0.0"
cherrypy.server.socket_port = 8000
cherrypy.server.thread_pool = 100
cherrypy.engine.start()
cherrypy.engine.block()
I am serving a static web site fully functional with css and js declaring CONF_WEBAPP and loading in the line:
cherrypy.tree.mount(ServeWebApp(), '/webapp', config=CONF_WEBAPP)
inside my folder WEB_ROOT I have an index.html file, and a
set of folders {css, js, fonts, img}.
I would like to load the index file and all subdirectories inside that folder. Is it possible? Are there another way to get the same result?
I can not use another tool to show custom page (like Nginx, apache).
Another method to customize but I could not follow that way because it uses functions
Here is how I solved my problem.
First I installed lib requests in my virtualenv.
import requests
from ConfigParser import RawConfigParser
config = RawConfigParser()
#file with my urls I would like to use in my app.
config.read('myparams.ini')
class PlatformAndroid(object):
android_url = config.get('links', 'android')#static url to play store
redir = requests.get(android_url)
if redir.status_code < 400: #case my app is published in play store
raise cherrypy.HTTPRedirect(android_url)
#unpublished app
raise cherrypy.HTTPRedirect(config.get('links','webapp')) #fallback to webapp version of my platform specific app.
if __name__ == '__main__':
cherrypy.tree.mount(PlatformAndroid(), '/android')
cherrypy.engine.start()
cherrypy.engine.block()
myparams.ini
[links]
android : http://play.google.com/store/apps/
ios : http://itunes.apple.com/us/app/
webapp : http://mysite.example.com/webapp/

Router change file for static files

I have routers/handlers in Tornado app like
handlers = [
(r"/", BaseHandler),
(r"/salary/([a-zA-Z0-9]*)$", BaseHandler),
(r"/salary/([a-zA-Z0-9]*)/([a-zA-Z0-9]*)$", BaseHandler),
]
and static files inside settings like
static_path=os.path.join(os.path.dirname(__file__), "static"),
and when I call web page with url
/salary/99 it works fine
but when I call like
/salary/99/33 it doesn't work (doesn't work for any for router r"/salary/([a-zA-Z0-9])/([a-zA-Z0-9])$"). Doesn't work means doesn't load css and js => change static files path to /salary/static.... instead of /static...)
How adds this salary from router to static path, how to avoid this ?
What you want is instruct Tornado how to serve static files. Read the first paragraphs of http://www.tornadoweb.org/en/branch2.4/web.html#application-configuration, you will find that you will either define a tornado.web.StaticFileHandler or set static_path.

web.py url handling: multiple subapplication redirection

When using web.py framework. you can redirect an url to a subapplication.
e.g (code.py):
import web
import subapp1
urls = (
"/sub1", subapp1.app,
"/(.*)", "index"
)
....
this is really straight forward.
However, when writing subapp1.py which has its own url handlers, if i want to re-route some url, say '/sub2', to another subapplication (subapp2), i am failing.
Formerly in subapp1.py
import web
import subapp2
urls = (
"/sub2", subapp2.app,
"/(.*)", "some_local_class"
)
....
GET request to "/sub1/sub2/", is handled by "some_local_class" in supapp1.py. But i need this url is re-routed to subapp2.py.
Is there anything i am missing? Or may be this is not recommended url handling methodology in web.py?
After some trial-error, found that there is nothing wrong with web.py and rerouting from subapp to another subapp. It is all working perfectly.
What is wrong is my method. Do not try to create a subapp in package's init.py file. At least when i moved subapp to its own module, it all worked well.

How to serve file in webpy?

I am using webpy framefork. I want to serve static file on one of requests. Is there special method in webpy framework or I just have to read and return that file?
If you are running the dev server (without apache):
Create a directory (also known as a folder) called static in the location of the script that runs the web.py server. Then place the static files you wish to serve in the static folder.
For example, the URL http://localhost/static/logo.png will send the image ./static/logo.png to the client.
Reference: http://webpy.org/cookbook/staticfiles
Update. If you really need to serve a static file on / you can simply use a redirect:
#!/usr/bin/env python
import web
urls = (
'/', 'index'
)
class index:
def GET(self):
# redirect to the static file ...
raise web.seeother('/static/index.html')
app = web.application(urls, globals())
if __name__ == "__main__": app.run()
I struggled with this for the last couple of hours... Yuck!
Found two solutions which are both working for me...
1 - in .htaccess add this line before the ModRewrite line:
RewriteCond %{REQUEST_URI} !^/static/.*
This will make sure that requests to the /static/ directory are NOT rewritten to go to your code.py script.
2 - in the code.py add a static handler and a url entry for each of several directories:
urls = (
'/' , 'index' ,
'/add', 'add' ,
'/(js|css|images)/(.*)', 'static',
'/one' , 'one'
)
class static:
def GET(self, media, file):
try:
f = open(media+'/'+file, 'r')
return f.read()
except:
return '' # you can send an 404 error here if you want
Note - I stole this from the web.py google group but can't find the dang post any more!
Either of these worked for me, both within the templates for web.py and for a direct call to a web-page that I put into "static"
I don't recommend serving static files with web.py. You'd better have apache or nginx configured for that.
The other answers did not work for me.
You can first load the html file in app.py or even write the html within app.py.
Then, you can make the index class' GET method return the static html.
index_html = '''<html>hello world!</html>'''
class index:
def GET(self):
return index_html

Categories

Resources