Skip to content

Commit 6c0ba10

Browse files
authored
Add HEAD support for storage API object endpoint (#759)
* Support HEAD method on storage API Problem: As reporeted in #667. The storage API is replying 404 for existing objects when method HEAD is used, although GET replies with 200. Solution: Update storage API method route and handler to behave as "donwload" when HEAD method is used. * Update documentation regarding flag usage Problem: As a new user, one tends to simply use what comes in the README.md file without realizing there is plenty more features at hand. Solution: Update README.md to pointing out there is a -help flag that lists all the available configuration overrides. I was tempted to copy and paste its output, but it might add too much noise for the reader so disregarded that thought.
1 parent ae04303 commit 6c0ba10

File tree

4 files changed

+19
-2
lines changed

4 files changed

+19
-2
lines changed

README.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,16 @@ It is possible to use fake-gcs-server with signed URLs, although with a few cave
8484
- You need to configure fake-gcs-server to accept this local URL (by setting
8585
`-public-host`)
8686

87+
### Available server flags
88+
89+
fake-gcs-server supports various features that can be configured through flags
90+
upon start. Use the `-help` flag to list all of them alongside their usage
91+
instructions
92+
93+
```shell
94+
docker run --rm fsouza/fake-gcs-server -help
95+
```
96+
8797
## Client library examples
8898

8999
For examples using SDK from multiple languages, check out the

fakestorage/object.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -481,7 +481,7 @@ func (s *Server) listObjects(r *http.Request) jsonResponse {
481481
}
482482

483483
func (s *Server) getObject(w http.ResponseWriter, r *http.Request) {
484-
if alt := r.URL.Query().Get("alt"); alt == "media" {
484+
if alt := r.URL.Query().Get("alt"); alt == "media" || r.Method == http.MethodHead {
485485
s.downloadObject(w, r)
486486
return
487487
}

fakestorage/server.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -231,7 +231,7 @@ func (s *Server) buildMuxer() {
231231
r.Path("/b/{bucketName}/o/{objectName:.+}/acl").Methods(http.MethodGet).HandlerFunc(jsonToHTTPHandler(s.listObjectACL))
232232
r.Path("/b/{bucketName}/o/{objectName:.+}/acl").Methods(http.MethodPost).HandlerFunc(jsonToHTTPHandler(s.setObjectACL))
233233
r.Path("/b/{bucketName}/o/{objectName:.+}/acl/{entity}").Methods(http.MethodPut).HandlerFunc(jsonToHTTPHandler(s.setObjectACL))
234-
r.Path("/b/{bucketName}/o/{objectName:.+}").Methods(http.MethodGet).HandlerFunc(s.getObject)
234+
r.Path("/b/{bucketName}/o/{objectName:.+}").Methods(http.MethodGet, http.MethodHead).HandlerFunc(s.getObject)
235235
r.Path("/b/{bucketName}/o/{objectName:.+}").Methods(http.MethodDelete).HandlerFunc(jsonToHTTPHandler(s.deleteObject))
236236
r.Path("/b/{sourceBucket}/o/{sourceObject:.+}/copyTo/b/{destinationBucket}/o/{destinationObject:.+}").Methods(http.MethodPost).HandlerFunc(jsonToHTTPHandler(s.rewriteObject))
237237
r.Path("/b/{sourceBucket}/o/{sourceObject:.+}/rewriteTo/b/{destinationBucket}/o/{destinationObject:.+}").Methods(http.MethodPost).HandlerFunc(jsonToHTTPHandler(s.rewriteObject))

fakestorage/server_test.go

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -290,6 +290,13 @@ func testDownloadObject(t *testing.T, server *Server) {
290290
map[string]string{"accept-ranges": "bytes", "content-length": "9"},
291291
"something",
292292
},
293+
{
294+
"HEAD: using storage api",
295+
http.MethodHead,
296+
"://storage.googleapis.com/storage/v1/b/some-bucket/o/files/txt/text-01.txt",
297+
map[string]string{"accept-ranges": "bytes", "content-length": "9"},
298+
"",
299+
},
293300
{
294301
"HEAD: bucket in the path",
295302
http.MethodHead,

0 commit comments

Comments
 (0)