Skip to content

Commit

Permalink
main: make server configurable
Browse files Browse the repository at this point in the history
  • Loading branch information
fsouza committed Jul 18, 2019
1 parent 76b224a commit 7bd4a35
Show file tree
Hide file tree
Showing 8 changed files with 290 additions and 62 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
fake-gcs-server
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,13 +44,13 @@ To make sure everything works as expected you can execute these commands:

```shell
curl --insecure https://0.0.0.0:4443/storage/v1/b
{"kind":"storage#buckets","items":[{"kind":"storage#bucket","id":"sample_bucket","name":"sample_bucket"}],"prefixes":null}
{"kind":"storage#buckets","items":[{"kind":"storage#bucket","id":"sample-bucket","name":"sample-bucket"}],"prefixes":null}

curl --insecure https://0.0.0.0:4443/storage/v1/b/sample_bucket/o
{"kind":"storage#objects","items":[{"kind":"storage#object","name":"some_file.txt","id":"sample_bucket/some_file.txt","bucket":"sample_bucket","size":"33"}],"prefixes":[]}
curl --insecure https://0.0.0.0:4443/storage/v1/b/sample-bucket/o
{"kind":"storage#objects","items":[{"kind":"storage#object","name":"some_file.txt","id":"sample-bucket/some_file.txt","bucket":"sample-bucket","size":"33"}],"prefixes":[]}
```

This will result in two ``buckets`` containing one ``blob`` each.
This will result in one bucket called ``sample-bucket`` containing one object called ``some_file.txt``.

## Example with the Python client library

Expand Down
File renamed without changes.
2 changes: 2 additions & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ module github.com/fsouza/fake-gcs-server

require (
cloud.google.com/go v0.42.0
github.com/google/go-cmp v0.3.0
github.com/gorilla/mux v1.7.3
github.com/sirupsen/logrus v1.4.2
google.golang.org/api v0.7.0
)

Expand Down
11 changes: 11 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ cloud.google.com/go v0.42.0/go.mod h1:BOSR3VbTLkk6FDC/TcffxP4NF/FFBGA5ku+jvKOP7p
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b h1:VKtxabqXZkF25pY9ekfRL6a582T4P37/31XEstQ5p58=
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
Expand Down Expand Up @@ -39,6 +41,14 @@ github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ
github.com/hashicorp/golang-lru v0.5.1 h1:0hERBMJE1eitiLkihrMvRVBYAkpHzc/J3QdDN+dAcgU=
github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1:6v2b51hI/fHJwM22ozAgKL4VKDeJcHhJFhtBdhmNjmU=
github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/sirupsen/logrus v1.4.2 h1:SPIRibHv4MatM3XXNO2BJeFLZwZ2LvZgfQ5+UNI2im4=
github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE=
github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.2.2 h1:bSDNvY7ZPG5RlJ8otE/7V6gMiyenm9RtJ7IUVIAoJ1w=
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
go.opencensus.io v0.21.0 h1:mU6zScU4U1YAFPHEHYk+3JC4SY7JxgkqS10ZOSyksNg=
go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU=
go.opencensus.io v0.22.0 h1:C9hSCOW830chIVkdja34wa6Ky+IzWllkUinR+BtRZd4=
Expand Down Expand Up @@ -87,6 +97,7 @@ golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a h1:1BGLXjeY4akVXGgbC9HugT3Jv
golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b h1:ag/x1USPSsqHud38I9BAC88qdNLDHHtQ4mlgQIZPPNA=
golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
Expand Down
74 changes: 74 additions & 0 deletions internal/config/config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
// Copyright 2019 Francisco Souza. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package config

import (
"flag"
"fmt"
"math"

"github.com/fsouza/fake-gcs-server/fakestorage"
)

const (
filesystemBackend = "filesystem"
memoryBackend = "memory"
)

type Config struct {
Seed string
publicHost string
externalURL string
host string
port uint
backend string
fsRoot string
}

// Load parses the given arguments list and return a config object (and/or an
// error in case of failures).
func Load(args []string) (Config, error) {
var cfg Config
fs := flag.NewFlagSet("gcs-emulator", flag.ContinueOnError)
fs.StringVar(&cfg.backend, "backend", filesystemBackend, "storage backend (memory or filesystem)")
fs.StringVar(&cfg.fsRoot, "filesystem-root", "/storage", "filesystem root (required for the filesystem backend). folder will be created if it doesn't exist")
fs.StringVar(&cfg.publicHost, "public-host", "storage.googleapis.com", "Optional URL for public host")
fs.StringVar(&cfg.externalURL, "external-url", "", "optional external URL, returned in the Location header for uploads. Defaults to the address where the server is running")
fs.StringVar(&cfg.host, "host", "0.0.0.0", "host to bind to")
fs.StringVar(&cfg.Seed, "data", "/data", "where to load data from (provided that the directory exists)")
fs.UintVar(&cfg.port, "port", 4443, "port to bind to")
err := fs.Parse(args)
if err != nil {
return cfg, err
}
return cfg, cfg.validate()
}

func (c *Config) validate() error {
if c.backend != memoryBackend && c.backend != filesystemBackend {
return fmt.Errorf(`invalid backend %q, must be either "memory" or "filesystem"`, c.backend)
}
if c.backend == filesystemBackend && c.fsRoot == "" {
return fmt.Errorf("backend %q requires the filesystem-root to be defined", c.backend)
}
if c.port > math.MaxUint16 {
return fmt.Errorf("port %d is too high, maximum value is %d", c.port, math.MaxUint16)
}
return nil
}

func (c *Config) ToFakeGcsOptions() fakestorage.Options {
storageRoot := c.fsRoot
if c.backend == memoryBackend {
storageRoot = ""
}
return fakestorage.Options{
StorageRoot: storageRoot,
Host: c.host,
Port: uint16(c.port),
PublicHost: c.publicHost,
ExternalURL: c.externalURL,
}
}
148 changes: 148 additions & 0 deletions internal/config/config_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,148 @@
// Copyright 2019 Francisco Souza. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package config

import (
"testing"

"github.com/fsouza/fake-gcs-server/fakestorage"
"github.com/google/go-cmp/cmp"
)

func TestLoadConfig(t *testing.T) {
t.Parallel()
tests := []struct {
name string
args []string
expectedConfig Config
expectErr bool
}{
{
name: "all parameters",
args: []string{
"-backend", "memory",
"-filesystem-root", "/tmp/something",
"-public-host", "127.0.0.1.nip.io:8443",
"-external-url", "https://myhost.example.com:8443",
"-host", "127.0.0.1",
"-port", "443",
"-data", "/var/gcs",
},
expectedConfig: Config{
Seed: "/var/gcs",
backend: "memory",
fsRoot: "/tmp/something",
publicHost: "127.0.0.1.nip.io:8443",
externalURL: "https://myhost.example.com:8443",
host: "127.0.0.1",
port: 443,
},
},
{
name: "default parameters",
expectedConfig: Config{
Seed: "/data",
backend: "filesystem",
fsRoot: "/storage",
publicHost: "storage.googleapis.com",
externalURL: "",
host: "0.0.0.0",
port: 4443,
},
},
{
name: "invalid port value type",
args: []string{"-port", "not-a-number"},
expectErr: true,
},
{
name: "invalid port value",
args: []string{"-port", "65536"},
expectErr: true,
},
{
name: "invalid backend",
args: []string{"-backend", "in-memory"},
expectErr: true,
},
{
name: "filesystem backend with no root",
args: []string{"-backend", "filesystem", "-filesystem-root", ""},
expectErr: true,
},
}
for _, test := range tests {
test := test
t.Run(test.name, func(t *testing.T) {
t.Parallel()
cfg, err := Load(test.args)
if err != nil && !test.expectErr {
t.Fatalf("uexpected non-nil error: %v", err)
} else if err == nil && test.expectErr {
t.Fatal("unexpected <nil> error")
}
if diff := cmp.Diff(cfg, test.expectedConfig, cmp.AllowUnexported(Config{})); !test.expectErr && diff != "" {
t.Errorf("wrong config returned\nwant %#v\ngot %#v\ndiff: %v", test.expectedConfig, cfg, diff)
}
})
}
}

func TestToFakeGcsOptions(t *testing.T) {
t.Parallel()
var tests = []struct {
name string
config Config
expected fakestorage.Options
}{
{
"filesystem",
Config{
backend: "filesystem",
fsRoot: "/tmp/something",
publicHost: "127.0.0.1.nip.io:8443",
externalURL: "https://myhost.example.com:8443",
host: "0.0.0.0",
port: 443,
},
fakestorage.Options{
StorageRoot: "/tmp/something",
PublicHost: "127.0.0.1.nip.io:8443",
ExternalURL: "https://myhost.example.com:8443",
Host: "0.0.0.0",
Port: 443,
},
},
{
"memory",
Config{
backend: "memory",
fsRoot: "/tmp/something",
publicHost: "127.0.0.1.nip.io:8443",
externalURL: "https://myhost.example.com:8443",
host: "0.0.0.0",
port: 443,
},
fakestorage.Options{
StorageRoot: "",
PublicHost: "127.0.0.1.nip.io:8443",
ExternalURL: "https://myhost.example.com:8443",
Host: "0.0.0.0",
Port: 443,
},
},
}

for _, test := range tests {
test := test
t.Run(test.name, func(t *testing.T) {
t.Parallel()
opts := test.config.ToFakeGcsOptions()
if diff := cmp.Diff(opts, test.expected); diff != "" {
t.Errorf("wrong set of options returned\nwant %#v\ngot %#v\ndiff: %v", test.expected, opts, diff)
}
})
}
}
Loading

0 comments on commit 7bd4a35

Please sign in to comment.