Skip to content

Commit

Permalink
fix: restructuring viper processing to accommodate processing of vari…
Browse files Browse the repository at this point in the history
…ables and unmarshalling viper
  • Loading branch information
shairozan committed Jan 3, 2024
1 parent 238a493 commit 7aa51be
Showing 1 changed file with 66 additions and 92 deletions.
158 changes: 66 additions & 92 deletions cmd/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ import (
"time"
)

const(
const (
ServiceName string = "gridengine_prometheus"
viperSGEKey string = "sge."
)
Expand All @@ -28,21 +28,21 @@ var entropy rand.Source
var random *rand.Rand

var RootCmd = &cobra.Command{
Use: "gridengine_prometheus",
Short: "Start the exporter",
Long: "Start the prometheus exporter and listen for requests",
Example: `gridengine_prometheus --pidfile /var/run/gridengine_prometheus.pid --port 9018`,
Run: Start,
Use: "gridengine_prometheus",
Short: "Start the exporter",
Long: "Start the prometheus exporter and listen for requests",
Example: `gridengine_prometheus --pidfile /var/run/gridengine_prometheus.pid --port 9018`,
RunE: Start,
}

func Start( cmd *cobra.Command, args []string){
func Start(cmd *cobra.Command, args []string) error {

entropy = rand.NewSource(time.Now().UnixNano())
random = rand.New(entropy)

if viper.GetBool("test") {
//set the underlying gogridengine variable
err := os.Setenv("GOGRIDENGINE_TEST","true")
err := os.Setenv("GOGRIDENGINE_TEST", "true")

if err != nil {
log.Fatalf("Attempting to set Gogridengine test variables failed: %s", err)
Expand All @@ -52,34 +52,36 @@ func Start( cmd *cobra.Command, args []string){
if len(viper.GetString("config")) > 0 {
err := readProvidedConfig(viper.GetString("config"))
if err != nil {
log.Fatalf("Attempting to open config file %s failed with error %s", viper.GetString("config"),err)
log.Fatalf("Attempting to open config file %s failed with error %s", viper.GetString("config"), err)
}
}

if viper.GetBool("debug"){
config := Config{}
viper.Unmarshal(&config)
log.Info(config)
var config Config

if err := viper.Unmarshal(&config); err != nil {
return fmt.Errorf("failed to retrieve viper details: %w", err)
}

if config.Debug {
viper.Debug()
}

//Die if we don't have all the SGE configurations required.
err := validateSGE()
err := validateSGE(config)
if err != nil {
log.Fatal(err)
return fmt.Errorf("failed to validate SGE configuration: %w", err)
}

//Set the SGE Envs for the application
err = setSGEEnvironmentVariables()
err = setSGEEnvironmentVariables(config)
if err != nil {
log.Fatalf("Unable to set SGE environment variables. Details: %s",err)
log.Fatalf("Unable to set SGE environment variables. Details: %s", err)
}


if len(viper.GetString("pidfile")) > 0 {
err := writePidFile(viper.GetString("pidfile"))
if len(config.Pidfile) > 0 {
err = writePidFile(viper.GetString("pidfile"))
if err != nil {
log.Error("Unable to setup PID. Continuing without a PID File")
log.Error("Unable to setup PID. Continuing without a PID File. Failure caused by: %w", err.Error())
}
}

Expand All @@ -90,54 +92,28 @@ func Start( cmd *cobra.Command, args []string){

log.Infof("Getting ready to start exporter on port %d", viper.GetInt("port"))

log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d",viper.GetInt("port")), nil))
log.Fatal(http.ListenAndServe(fmt.Sprintf(":%d", viper.GetInt("port")), nil))

return nil
}

func init(){
func init() {
pidFileIdentifier := "pidfile"
RootCmd.PersistentFlags().String(pidFileIdentifier,"/var/run/" + ServiceName,"Location in which to store a pidfile. Most useful for SystemV daemons")
viper.BindPFlag(pidFileIdentifier, RootCmd.PersistentFlags().Lookup(pidFileIdentifier))

listenPortIdentifier := "port"
RootCmd.PersistentFlags().Int(listenPortIdentifier,9081,"The port on which the collector should listen")
viper.BindPFlag(listenPortIdentifier,RootCmd.PersistentFlags().Lookup(listenPortIdentifier))

testModeIdentifier := "test"
RootCmd.PersistentFlags().Bool(testModeIdentifier,false,"Indicates whether the underlying gogridengine should be run in test mode")
viper.BindPFlag(testModeIdentifier,RootCmd.PersistentFlags().Lookup(testModeIdentifier))

configFileIdentifier := "config"
RootCmd.PersistentFlags().String(configFileIdentifier,"", "Specifies a viper config to load. Should be in yaml format")
viper.BindPFlag(configFileIdentifier,RootCmd.PersistentFlags().Lookup(configFileIdentifier))

debugIdentifier := "debug"
RootCmd.PersistentFlags().Bool(debugIdentifier,false,"Whether or not debug is on")
viper.BindPFlag(debugIdentifier, RootCmd.PersistentFlags().Lookup(debugIdentifier))
RootCmd.PersistentFlags().String(pidFileIdentifier, "/var/run/"+ServiceName, "Location in which to store a pidfile. Most useful for SystemV daemons")
RootCmd.PersistentFlags().Int("port", 9081, "The port on which the collector should listen")
RootCmd.PersistentFlags().Bool("test", false, "Indicates whether the underlying gogridengine should be run in test mode")
RootCmd.PersistentFlags().String("config", "", "Specifies a viper config to load. Should be in yaml format")
RootCmd.PersistentFlags().Bool("debug", false, "Whether or not debug is on")

//SGE Configurations
sgeArchIdentifier := "sge_arch"
RootCmd.PersistentFlags().String(sgeArchIdentifier,"lx-amd64","Identifies the architecture of the Sun Grid Engine")
viper.BindPFlag(viperSGEKey + "arch",RootCmd.PersistentFlags().Lookup(sgeArchIdentifier))

sgeCellIdentifier := "sge_cell"
RootCmd.PersistentFlags().String(sgeCellIdentifier,"default","The SGE Cell to use")
viper.BindPFlag(viperSGEKey + "cell", RootCmd.PersistentFlags().Lookup(sgeCellIdentifier))

sgeExecDPortIdentifier := "sge_execd_port"
RootCmd.PersistentFlags().Int(sgeExecDPortIdentifier,6445,"Port for the execution daemon in the grid engine")
viper.BindPFlag(viperSGEKey + "execd_port", RootCmd.PersistentFlags().Lookup(sgeExecDPortIdentifier))

sgeQmasterPortIdentifier := "sge_qmaster_port"
RootCmd.PersistentFlags().Int(sgeQmasterPortIdentifier,6445,"Port for the master scheduling daemon in the grid engine")
viper.BindPFlag(viperSGEKey + "qmaster_port", RootCmd.PersistentFlags().Lookup(sgeQmasterPortIdentifier))

sgeRootIdentifier := "sge_root"
RootCmd.PersistentFlags().String(sgeRootIdentifier,"/opt/sge", "The root location for SGE bianries")
viper.BindPFlag(viperSGEKey + "root", RootCmd.PersistentFlags().Lookup(sgeRootIdentifier))

sgeClusterNameIdentifier := "sge_cluster_name"
RootCmd.PersistentFlags().String(sgeClusterNameIdentifier,"p6444","Name of the SGE Cluster to bind to")
viper.BindPFlag(viperSGEKey + "cluster_name",RootCmd.PersistentFlags().Lookup(sgeClusterNameIdentifier))
RootCmd.PersistentFlags().String("sge_arch", "lx-amd64", "Identifies the architecture of the Sun Grid Engine")
RootCmd.PersistentFlags().String("sge_cell", "default", "The SGE Cell to use")
RootCmd.PersistentFlags().Int("sge_execd_port", 6445, "Port for the execution daemon in the grid engine")
RootCmd.PersistentFlags().Int("sge_qmaster_port", 6445, "Port for the master scheduling daemon in the grid engine")
RootCmd.PersistentFlags().String("sge_root", "/opt/sge", "The root location for SGE bianries")
RootCmd.PersistentFlags().String("sge_cluster_name", "p6444", "Name of the SGE Cluster to bind to")

_ = viper.BindPFlags(RootCmd.PersistentFlags())
}

func writePidFile(pidFile string) error {
Expand All @@ -161,7 +137,6 @@ func writePidFile(pidFile string) error {
return ioutil.WriteFile(location, []byte(fmt.Sprintf("%d", os.Getpid())), 0664)
}

//TODO Test
func readProvidedConfig(path string) error {
viper.SetConfigType("yaml")

Expand All @@ -175,72 +150,72 @@ func readProvidedConfig(path string) error {
return viper.ReadConfig(file)
}

func validateSGE() error {
func validateSGE(config Config) error {

if len(viper.GetString("sge.arch")) == 0{
if len(config.SGE.Arch) == 0 {
return errors.New("the SGE architecture has not been provided")
}

if len(viper.GetString("sge.cell")) == 0 {
if len(config.SGE.Cell) == 0 {
return errors.New("no valid SGE cell has been configured")
}

if viper.GetInt("sge.execd_port") == 0 {
if config.SGE.ExecdPort == 0 {
return errors.New("no ExecD port has been specified for SGE binding")
}

if viper.GetInt("sge.qmaster_port") == 0 {
if config.SGE.QmasterPort == 0 {
return errors.New("no Qmaster port has been specified for SGE Binding")
}

if len(viper.GetString("sge.cluster_name")) == 0 {
if len(config.SGE.ClusterName) == 0 {
return errors.New("no SGE cluster name has been provided")
}

return nil
}

func setSGEEnvironmentVariables() error {
err := os.Setenv("SGE_ARCH",viper.GetString("sge.arch"))
func setSGEEnvironmentVariables(config Config) error {
err := os.Setenv("SGE_ARCH", config.SGE.Arch)
if err != nil {
return err
}

err = os.Setenv("SGE_CELL", viper.GetString("sge.cell"))
err = os.Setenv("SGE_CELL", config.SGE.Cell)

if err != nil {
return err
}

err = os.Setenv("SGE_EXECD_PORT",string(rune(viper.GetInt("sge.execd_port"))))
err = os.Setenv("SGE_EXECD_PORT", strconv.Itoa(config.SGE.ExecdPort))

if err != nil {
return err
}

err = os.Setenv("SGE_QMASTER_PORT",string(rune(viper.GetInt("sge.qmaster_port"))))
err = os.Setenv("SGE_QMASTER_PORT", strconv.Itoa(config.SGE.QmasterPort))

if err != nil {
return err
}

err = os.Setenv("SGE_ROOT", viper.GetString("sge.root"))
err = os.Setenv("SGE_ROOT", config.SGE.Root)

if err != nil {
return err
}

//Update Path to include SGE_ROOT BIN and any dirs matching arch path
path := os.Getenv("PATH")
binPath := filepath.Join(viper.GetString("sge.root"),"bin")
archPath := filepath.Join(binPath,viper.GetString("sge.arch"))
err = os.Setenv("PATH", path + ":" + binPath + ":" + archPath)
binPath := filepath.Join(config.SGE.Root, "bin")
archPath := filepath.Join(binPath, config.SGE.Arch)
err = os.Setenv("PATH", path+":"+binPath+":"+archPath)

if err != nil {
return err
}

err = os.Setenv("SGE_CLUSTER_NAME", viper.GetString("sge.cluster_name"))
err = os.Setenv("SGE_CLUSTER_NAME", config.SGE.ClusterName)

if err != nil {
return err
Expand All @@ -249,20 +224,19 @@ func setSGEEnvironmentVariables() error {
return nil
}


type Config struct {
Test bool `yaml:"test" json:"test"`
Port int `yaml:"port" josn:"port"`
Test bool `yaml:"test" json:"test"`
Port int `yaml:"port" josn:"port"`
Pidfile string `yaml:"pidfile" json:"pidfile"`
SGE SGE `mapstructure:"sge"`

SGE SGE `mapstructure:"sge"`
Debug bool `mapstructure:"debug" yaml:"debug"`
}

type SGE struct {
Arch string `yaml:"arch" json:"arch"`
Cell string `yaml:"cell" json:"cell"`
ExecdPort int `yaml:"execd_port" json:"execd_port" mapstructure:"execd_port"`
QmasterPort int `yaml:"qmaster_port" json:"qmaster_port" mapstructure:"qmaster_port"`
Root string `yaml:"root" json:"root"`
Arch string `yaml:"arch" json:"arch"`
Cell string `yaml:"cell" json:"cell"`
ExecdPort int `yaml:"execd_port" json:"execd_port" mapstructure:"execd_port"`
QmasterPort int `yaml:"qmaster_port" json:"qmaster_port" mapstructure:"qmaster_port"`
Root string `yaml:"root" json:"root"`
ClusterName string `yaml:"cluster_name" json:"cluster_name" mapstructure:"cluster_name"`
}
}

0 comments on commit 7aa51be

Please sign in to comment.