代码之家  ›  专栏  ›  技术社区  ›  Flux

如何在web服务器日志中显示HTTP状态码?

  •  2
  • Flux  · 技术社区  · 6 年前

    #lang racket
    (require web-server/servlet-env)
    
    ; Some web app code here ...
    
    ;; Start the web server.
    (serve/servlet request-handler
                   #:log-file "/dev/stdout")
    

    当我启动web服务器并通过浏览器访问web应用程序时,日志显示如下:

    127.0.0.1 - - [25/Dec/2018:12:34:56 +0000] "GET /servlets/standalone.rkt HTTP/1.1" - -
    127.0.0.1 - - [25/Dec/2018:12:34:56 +0000] "GET /favicon.ico HTTP/1.1" - -
    

    500 , 403 , 404 等等。?

    如何使web服务器日志显示HTTP状态代码?

    Issue on GitHub .

    1 回复  |  直到 5 年前
        1
  •  1
  •   Greg Hendershott    6 年前

    这个 built-in logging 只是请求日志,而不是请求和响应日志。我同意,那遗漏了一些重要的信息。

    事实上,我通常有一整链的包装纸 dispatch 程序来自 dispatch-rules

    (serve/servlet (~> ;Note: requests go UP this chain, responses DOWN
                    dispatch
                    wrap-gzip
                    wrap-not-modified
                    wrap-authorize
                    wrap-authenticate
                    wrap-http->https
                    wrap-timed-and-logged)
                   #:servlet-path      "/"
                   #:servlet-regexp    #px""
                   #:listen-ip         #f
                   #:port              (current-internal-port)
                   #:servlet-responder error-responder)
    

    定义示例 wrap-timed-and-logged

    (define handler? (-> request? response?))
    (define wrapper? (-> handler? handler?))
    
    (define/contract ((wrap-timed-and-logged handler) req) wrapper?
      (define t0 (current-inexact-milliseconds))
    
      (define resp (handler req))
    
      (define t1 (current-inexact-milliseconds))
      (define dur (round (- t1 t0)))
    
      ;; Let's use "structured logging" here to make it easier to search,
      ;; and do things like create CloudWatch metrics from CloudWatch Logs
      ;; filters (they have a syntax to extract things from JSON.)
      (log-info
       (jsexpr->string
        (hasheq 'request  (hasheq 'method  (~a (request-method req))
                                  'ip      (request-client-ip req)
                                  'path    (url->string (request-uri req))
                                  'headers (headers->hasheq (request-headers/raw req)))
                'response (hasheq 'code     (response-code resp)
                                  'headers  (headers->hasheq (response-headers resp))
                                  'duration dur))))
    
      resp)
    
    (define (headers->hasheq hs)
      (for/hasheq ([h (in-list hs)])
        (values (string->symbol (~a (header-field h)))
                (~a (header-value h)))))
    

    定义示例 error-responder :

    ;; Don't show exception info to end users! Instead log it.
    (define (error-responder url exn)
      (log-error "Exception responding to ~v:\n~a"
                 (url->string url)
                 (exn->string exn))
      (response/full 500 #"Oops"
                     (current-seconds)
                     #f '() '()))