github.com/abayer/test-infra@v0.0.5/mungegithub/features/server.go (about) 1 /* 2 Copyright 2017 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 package features 18 19 import ( 20 "net/http" 21 "os" 22 23 "github.com/NYTimes/gziphandler" 24 "github.com/prometheus/client_golang/prometheus" 25 "github.com/prometheus/client_golang/prometheus/promhttp" 26 27 "k8s.io/apimachinery/pkg/util/sets" 28 "k8s.io/test-infra/mungegithub/github" 29 "k8s.io/test-infra/mungegithub/mungeopts" 30 "k8s.io/test-infra/mungegithub/options" 31 "k8s.io/test-infra/mungegithub/sharedmux" 32 ) 33 34 const ( 35 ServerFeatureName = "server" 36 ) 37 38 // ServerFeature runs a server and allows mungers to register handlers for paths, or 39 // prometheus metrics. 40 type ServerFeature struct { 41 *sharedmux.ConcurrentMux 42 Enabled bool 43 44 Address string 45 WWWRoot string 46 47 prometheus struct { 48 loops prometheus.Counter 49 tokenUsage prometheus.Gauge 50 } 51 52 getTokenUsage func() int 53 } 54 55 func init() { 56 s := &ServerFeature{} 57 RegisterFeature(s) 58 } 59 60 // Name is just going to return the name mungers use to request this feature 61 func (s *ServerFeature) Name() string { 62 return ServerFeatureName 63 } 64 65 // Initialize will initialize the feature. 66 func (s *ServerFeature) Initialize(config *github.Config) error { 67 config.ServeDebugStats("/stats") 68 s.ConcurrentMux = sharedmux.NewConcurrentMux(http.DefaultServeMux) 69 if len(s.Address) == 0 { 70 return nil 71 } 72 if len(s.WWWRoot) > 0 { 73 wwwStat, err := os.Stat(s.WWWRoot) 74 if !os.IsNotExist(err) && wwwStat.IsDir() { 75 s.ConcurrentMux.Handle("/", gziphandler.GzipHandler(http.FileServer(http.Dir(s.WWWRoot)))) 76 } 77 } 78 // config indicates that ServerFeature should be enabled. 79 s.Enabled = true 80 81 s.prometheus.loops = prometheus.NewCounter(prometheus.CounterOpts{ 82 Name: "mungegithub_loops", 83 Help: "Number of loops performed by the munger", 84 ConstLabels: map[string]string{"org": config.Org, "repo": config.Project, "app": mungeopts.App}, 85 }) 86 s.prometheus.tokenUsage = prometheus.NewGauge(prometheus.GaugeOpts{ 87 Name: "github_token_usage", 88 Help: "Number of github tokens used by the munger", 89 ConstLabels: map[string]string{"org": config.Org, "repo": config.Project, "app": mungeopts.App}, 90 }) 91 prometheus.MustRegister(s.prometheus.loops) 92 prometheus.MustRegister(s.prometheus.tokenUsage) 93 s.getTokenUsage = config.GetTokenUsage 94 s.ConcurrentMux.Handle("/prometheus", promhttp.Handler()) 95 96 go http.ListenAndServe(s.Address, s.ConcurrentMux) 97 return nil 98 } 99 100 // EachLoop is called at the start of every munge loop 101 func (s *ServerFeature) EachLoop() error { 102 s.prometheus.loops.Inc() 103 s.prometheus.tokenUsage.Set(float64(s.getTokenUsage())) 104 return nil 105 } 106 107 // RegisterOptions registers options for this feature; returns any that require a restart when changed. 108 func (s *ServerFeature) RegisterOptions(opts *options.Options) sets.String { 109 opts.RegisterString(&s.Address, "address", ":8080", "The address to listen on for HTTP Status") 110 opts.RegisterString(&s.WWWRoot, "www", "www", "Path to static web files to serve from the webserver") 111 return sets.NewString("address", "www") 112 }