func (app *App) errorPage(ctx *Context, elapsed time.Duration, skip int, stackSkip int, req string, err interface{}) { t := newInternalTemplate(app) if terr := t.parse("panic.html", devserver.TemplateVars(&Context{})); terr != nil { panic(terr) } if devserver.IsActive() { t.tmpl.AddPlugin(devserver.ReloadPlugin()) } if terr := t.prepare(); terr != nil { panic(terr) } stack := runtimeutil.FormatStackHTML(stackSkip + 1) location, code := runtimeutil.FormatCallerHTML(skip+1, 5, true, true) ctx.statusCode = -http.StatusInternalServerError data := map[string]interface{}{ "Error": fmt.Sprintf("%v", err), "Subtitle": fmt.Sprintf("(after %s)", elapsed), "Location": location, "Code": code, "Stack": stack, "Request": req, "Name": filepath.Base(os.Args[0]), "IsDevServer": devserver.IsDevServer(app), } if err := t.Execute(ctx, data); err != nil { var msg string if file, line, ok := runtimeutil.PanicLocation(); ok { msg = fmt.Sprintf("error rendering error page: %v @ %s:%d)", err, file, line) } else { msg = fmt.Sprintf("error rendering error page: %v", err) } ctx.WriteString(msg) } }
// ListenAndServe starts listening on the configured address and // port (see Address() and Port). func (app *App) ListenAndServe() error { if err := app.Prepare(); err != nil { return err } if err := app.checkPort(); err != nil { return err } Signals.WillListen.emit(app) app.started = time.Now().UTC() if devserver.IsActive() { // Attach the automatic reload template plugin to automatically // reload the page when the server restarts vars := devserver.TemplateVars(&Context{}) plugin := devserver.ReloadPlugin() app.AddTemplateVars(vars) app.AddTemplatePlugin(plugin) for _, c := range app.included { c.app.AddTemplateVars(vars) c.app.AddTemplatePlugin(plugin) } } else { if app.Logger != nil { if app.address != "" { app.Logger.Infof("Listening on %s, port %d", app.address, app.cfg.Port) } else { app.Logger.Infof("Listening on port %d", app.cfg.Port) } } } var err error time.AfterFunc(500*time.Millisecond, func() { if err == nil { Signals.DidListen.emit(app) } }) err = http.ListenAndServe(app.address+":"+strconv.Itoa(app.cfg.Port), app) return err }
func (b *Broadcaster) Attach(a *app.App) { a.HandleWebsocket(b.pattern(), b.handler()) a.AddTemplateVars(devserver.TemplateVars(&app.Context{})) a.AddTemplatePlugin(devserver.ReloadPlugin()) b.ts = time.Now() }