duanliang1019 2018-07-04 08:56
浏览 184
已采纳

HTTP静态文件处理程序不断显示目录列表

When I implement a static server handler, if I access to root path, it will show the whole directory, like this:

access to root folder

My code is:

package main

import (
    "flag"
    "log"
    "net/http"
    "strings"
)

func main() {
    port := flag.String("p", "3000", "port to serve on")
    directory := flag.String("d", ".", "the directory of static file to host")
    flag.Parse()

    http.Handle("/statics/", http.StripPrefix(strings.TrimRight("/statics/", "/"), http.FileServer(http.Dir(*directory))))

    log.Printf("Serving %s on HTTP port: %s
", *directory, *port)
    log.Fatal(http.ListenAndServe(":"+*port, nil))
}

go to : http://locahost:3000/statics/

  • 写回答

1条回答 默认 最新

  • dty9731 2018-07-04 09:39
    关注

    Fortunately or not, the default behavior of http.FileServer is that if the path denotes a directory without an index.html file, a directory listing will be served. And it does not provide a simple way to turn that off. But...

    http.FileServer operates on a virtual filesystem described by the http.FileSystem interface.

    This interface has a single method which tells how to open a file, and obtain an http.File "view" of it:

    type FileSystem interface {
            Open(name string) (File, error)
    }
    

    If you want to disable directory listing, all you have to do is provide your own implementation of http.FileSystem which when a directory is targeted, you simply report / return an error. That's all it takes.

    Of course you don't have to do this all by yourself. You may create your own FileSystem which uses / utilizes http.Dir, which is the default implementation that uses the native file system (restricted to a specific directory tree).

    type myfs struct {
        http.Dir
    }
    
    func (m myfs) Open(name string) (result http.File, err error) {
        f, err := m.Dir.Open(name)
        if err != nil {
            return
        }
    
        fi, err := f.Stat()
        if err != nil {
            return
        }
        if fi.IsDir() {
            // Return a response that would have been if directory would not exist:
            return m.Dir.Open("does-not-exist")
        }
        return f, nil
    }
    

    Using the above custom implementation:

    handler := http.FileServer(myfs{http.Dir(*directory)})
    http.Handle(
        "/statics/",
        http.StripPrefix(strings.TrimRight("/statics/", "/"), handler),
    )
    

    And that's all. Attempting to browse http://locahost:3000/statics/ will result in the default response:

    404 page not found
    

    Notes:

    The above implementation does a second Dir.Open() call to return an error, which is always the same. To "speed things up", we can store this response and just reuse it:

    var notFoundFile, notFoundErr = http.Dir("dummy").Open("does-not-exist")
    

    And when we detect a directory in our myfs.Open() method:

    if fi.IsDir() {
        // Return a response that "belogns" to opening a non-existing folder:
        return notFoundFile, notFoundErr
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥20 如何通过代码传输视频到亚马逊平台
  • ¥15 php查询mysql数据库并显示至下拉列表中
  • ¥15 freertos下使用外部中断失效
  • ¥15 输入的char字符转为int类型,不是对应的ascall码,如何才能使之转换为对应ascall码?或者使输入的char字符可以正常与其他字符比较?
  • ¥15 devserver配置完 启动服务 无法访问static上的资源
  • ¥15 解决websocket跟c#客户端通信
  • ¥30 Python调用dll文件输出Nan重置dll状态
  • ¥15 浮动div的高度控制问题。
  • ¥66 换电脑后应用程序报错
  • ¥50 array数据同步问题