创建一个tar文件,通过Google App Engine进行服务。

huangapple go评论78阅读模式
英文:

Creating a tar file to be served via Google App Engine

问题

我正在为使用Go的Google AppEngine编写一个应用程序,并且需要将一堆文件打包成tar文件,在用户访问特定URL时提供给他们。目前这些文件是静态的,所以我可以在上传到服务器之前将它们打包成tar文件来解决这个问题。将来我希望在打包之前动态地修改它们,所以我想学习如何在请求时打包和提供静态文件。

在我的init()函数中,我有以下代码:

http.HandleFunc("/download.tar", tarit)

tarit函数是我遇到问题的函数,目前它的代码如下:

func tarit(w http.ResponseWriter, r *http.Request) {
	tarball := tar.NewWriter(w)
	defer tarball.Close()

	info, err := os.Stat("/files")
	if err != nil {
		return
	}

	var baseDir string
	if info.IsDir() {
		baseDir = filepath.Base("/files")
	}

	filepath.Walk("/files", func(path string, info os.FileInfo, err error) error {
		if err != nil {
			return err
		}
		header, err := tar.FileInfoHeader(info, info.Name())
		if err != nil {
			return err
		}

		if baseDir != "" {
			header.Name = filepath.Join(baseDir, strings.TrimPrefix(path, "/files"))
		}

		if err := tarball.WriteHeader(header); err != nil {
			return err
		}

		if info.IsDir() {
			return nil
		}

		file, err := os.Open(path)
		if err != nil {
			return err
		}
		defer file.Close()
		_, err = io.Copy(tarball, file)
		return err
	})
}

我要添加到tar文件中的文件位于/files目录下,并且我已将此文件夹添加为app.yaml中的static_dir。

当访问适当的URL时,浏览器下载的tar文件只有1 KB大小,并且看起来是空的。

如果有人能指出我做错了什么,或者我理解错了什么,我将非常感激。我也很乐意提供您需要的任何其他细节。

谢谢!

英文:

I'm writing an application for Google AppEngine using Go, and need to tar together a bunch of files to serve to the user when they navigate to a particular URL. At the moment the files are static, and so I could solve this problem by tarring them before upload to the server. In the future I would like to dynamically alter them before tarring, and so would like to learn how to tar & serve the static files on request.

In my init() function I have the following line:

http.HandleFunc("/download.tar", tarit)

The function tarit is the one I am having a problem with, and it currently looks like the following:

func tarit(w http.ResponseWriter, r *http.Request) {
	tarball := tar.NewWriter(w)
	defer tarball.Close()

	info, err := os.Stat("/files")
	if err != nil {
		return
	}

	var baseDir string
	if info.IsDir() {
		baseDir = filepath.Base("/files")
	}

	filepath.Walk("/files", func(path string, info os.FileInfo, err error) error {
		if err != nil {
			return err
		}
		header, err := tar.FileInfoHeader(info, info.Name())
		if err != nil {
			return err
		}

		if baseDir != "" {
			header.Name = filepath.Join(baseDir, strings.TrimPrefix(path, "/files"))
		}

		if err := tarball.WriteHeader(header); err != nil {
			return err
		}

		if info.IsDir() {
			return nil
		}

		file, err := os.Open(path)
		if err != nil {
			return err
		}
		defer file.Close()
		_, err = io.Copy(tarball, file)
		return err
	})
}

The files I am trying to add to the tarball are located in /files, and I've added this folder as a static_dir in the app.yaml.

When navigating to the appropriate URL, the browser downloads a tar file that is only 1 KB in size, and appears to be empty.

I would very much appreciate if someone could point out where I am going wrong, or what I am misunderstanding. I'd also be very happy to provide any other details that you would like.

Thanks!

答案1

得分: 0

请将路径指定为相对于包含 app.yaml 文件的目录的路径。在发布的代码中,路径是绝对路径 "/files"。也许你应该将其更改为 "files"。

记录从 os.Stat 和 filepath.Walk 返回的错误。这些错误可能会帮助你找到问题所在。

英文:

Specify directories using paths relative to the directory containing app.yaml. The path in the posted code is the absolute path "/files". Perhaps you should change it to "files".

Log the errors returned from os.Stat and filepath.Walk. The errors will probably lead you to the problem.

huangapple
  • 本文由 发表于 2016年4月23日 01:41:11
  • 转载请务必保留本文链接:https://go.coder-hub.com/36800168.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定