github.com/zppinho/prow@v0.0.0-20240510014325-1738badeb017/test/integration/cmd/fakegcsserver/main.go (about) 1 /* 2 Copyright 2022 The Kubernetes Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 // fakegcsserver runs the open source GCS emulator from 18 // https://github.com/fsouza/fake-gcs-server. 19 package main 20 21 import ( 22 "flag" 23 "fmt" 24 "os" 25 26 "github.com/fsouza/fake-gcs-server/fakestorage" 27 "github.com/sirupsen/logrus" 28 29 configflagutil "sigs.k8s.io/prow/pkg/flagutil/config" 30 "sigs.k8s.io/prow/pkg/interrupts" 31 "sigs.k8s.io/prow/pkg/logrusutil" 32 "sigs.k8s.io/prow/pkg/pjutil" 33 ) 34 35 type options struct { 36 // config is the Prow configuration. We need this to read in GCS 37 // configurations under plank's default_decoration_config_entries field set 38 // in the integration test's Prow configuration, because we have to 39 // initialize (create) these buckets before we upload into them with 40 // initupload. 41 config configflagutil.ConfigOptions 42 emulatorPort uint 43 emulatorPublicHost string 44 emulatorStorageRoot string 45 } 46 47 func (o *options) validate() error { 48 if o.emulatorPort > 65535 { 49 return fmt.Errorf("-emulator-port range (got %d) must be 0 - 65535", o.emulatorPort) 50 } 51 52 return nil 53 } 54 55 func flagOptions() *options { 56 o := &options{config: configflagutil.ConfigOptions{ConfigPath: "/etc/config/config.yaml"}} 57 fs := flag.NewFlagSet(os.Args[0], flag.ExitOnError) 58 59 fs.UintVar(&o.emulatorPort, "emulator-port", 8888, "Port to use for the GCS emulator.") 60 fs.StringVar(&o.emulatorPublicHost, "emulator-public-host", "fakegcsserver.default:80", "Address of the GCS emulator as seen by other Prow components in the test cluster.") 61 fs.StringVar(&o.emulatorStorageRoot, "emulator-storage-root", "/gcs", "Folder to store GCS buckets and objects.") 62 o.config.AddFlags(fs) 63 64 fs.Parse(os.Args[1:]) 65 66 return o 67 } 68 69 func main() { 70 logrusutil.ComponentInit() 71 72 o := flagOptions() 73 if err := o.validate(); err != nil { 74 logrus.WithError(err).Fatal("Invalid arguments.") 75 } 76 77 health := pjutil.NewHealth() 78 health.ServeReady() 79 80 defer interrupts.WaitForGracefulShutdown() 81 82 initialObjects, err := getInitialObjects(o) 83 if err != nil { 84 logrus.WithError(err).Fatal("Could not initialize emulator state") 85 } 86 87 logrus.Info("Starting server...") 88 89 server, err := fakestorage.NewServerWithOptions(fakestorage.Options{ 90 Scheme: "http", 91 Host: "0.0.0.0", 92 Port: uint16(o.emulatorPort), 93 PublicHost: o.emulatorPublicHost, 94 Writer: logrus.New().Writer(), 95 StorageRoot: o.emulatorStorageRoot, 96 InitialObjects: *initialObjects, 97 }) 98 if err != nil { 99 panic(err) 100 } 101 102 logrus.Infof("Server started at %s", server.URL()) 103 logrus.Infof("PublicURL: %s", server.PublicURL()) 104 } 105 106 // getInitialObjects creates GCS buckets, because every time the emulator 107 // starts, it starts off from a clean slate. 108 func getInitialObjects(o *options) (*[]fakestorage.Object, error) { 109 initialObjects := []fakestorage.Object{} 110 configAgent, err := o.config.ConfigAgent() 111 if err != nil { 112 return &initialObjects, fmt.Errorf("Error starting config agent: %v", err) 113 } 114 115 ddcs := configAgent.Config().Plank.DefaultDecorationConfigs 116 117 for _, ddc := range ddcs { 118 logrus.Infof("detected bucket %q from configuration", ddc.Config.GCSConfiguration.Bucket) 119 initialObjects = append(initialObjects, fakestorage.Object{ 120 BucketName: ddc.Config.GCSConfiguration.Bucket, 121 Name: "placeholder", 122 Content: []byte("This file is here so that we can create the parent directory."), 123 }) 124 } 125 126 return &initialObjects, nil 127 }