github.com/getgauge/gauge@v1.6.9/plugin/pluginInfo/pluginInfo.go (about) 1 /*---------------------------------------------------------------- 2 * Copyright (c) ThoughtWorks, Inc. 3 * Licensed under the Apache License, Version 2.0 4 * See LICENSE in the project root for license information. 5 *----------------------------------------------------------------*/ 6 7 package pluginInfo 8 9 import ( 10 "fmt" 11 "os" 12 "path/filepath" 13 "sort" 14 "strings" 15 16 "github.com/getgauge/common" 17 "github.com/getgauge/gauge/version" 18 ) 19 20 type PluginInfo struct { 21 Name string 22 Version *version.Version 23 Path string 24 } 25 26 type byPluginName []PluginInfo 27 28 func (a byPluginName) Len() int { return len(a) } 29 func (a byPluginName) Swap(i, j int) { a[i], a[j] = a[j], a[i] } 30 func (a byPluginName) Less(i, j int) bool { 31 return a[i].Name < a[j].Name 32 } 33 34 type byPath []PluginInfo 35 36 func (a byPath) Len() int { return len(a) } 37 func (a byPath) Swap(i, j int) { a[i], a[j] = a[j], a[i] } 38 func (a byPath) Less(i, j int) bool { 39 return a[i].Path > a[j].Path 40 } 41 42 func GetPluginsInfo() ([]PluginInfo, error) { 43 allPluginsWithVersion, err := GetAllInstalledPluginsWithVersion() 44 if err != nil { 45 return nil, fmt.Errorf("No plugins found\nPlugins can be installed with `gauge install {plugin-name}`") 46 } 47 return allPluginsWithVersion, nil 48 } 49 50 // GetAllInstalledPluginsWithVersion Fetches Latest version of all installed plugins. 51 var GetAllInstalledPluginsWithVersion = func() ([]PluginInfo, error) { 52 pluginInstallPrefixes, err := common.GetPluginInstallPrefixes() 53 if err != nil { 54 return nil, err 55 } 56 allPlugins := make(map[string]PluginInfo) 57 for _, prefix := range pluginInstallPrefixes { 58 files, err := os.ReadDir(prefix) 59 if err != nil { 60 return nil, err 61 } 62 for _, file := range files { 63 pluginDir, err := os.Stat(filepath.Join(prefix, file.Name())) 64 if err != nil { 65 continue 66 } 67 68 if !pluginDir.IsDir() { 69 continue 70 } 71 latestPlugin, err := GetLatestInstalledPlugin(filepath.Join(prefix, file.Name())) 72 if err != nil { 73 continue 74 } 75 allPlugins[file.Name()] = *latestPlugin 76 } 77 } 78 return sortPlugins(allPlugins), nil 79 } 80 81 func GetLatestInstalledPlugin(pluginDir string) (*PluginInfo, error) { 82 files, err := os.ReadDir(pluginDir) 83 if err != nil { 84 return nil, fmt.Errorf("Error listing files in plugin directory %s: %s", pluginDir, err.Error()) 85 } 86 versionToPlugins := make(map[string][]PluginInfo) 87 pluginName := filepath.Base(pluginDir) 88 89 for _, file := range files { 90 if !file.IsDir() { 91 continue 92 } 93 v := file.Name() 94 if strings.Contains(file.Name(), "nightly") { 95 v = file.Name()[:strings.LastIndex(file.Name(), ".")] 96 } 97 vp, err := version.ParseVersion(v) 98 if err == nil { 99 versionToPlugins[v] = append(versionToPlugins[v], PluginInfo{pluginName, vp, filepath.Join(pluginDir, file.Name())}) 100 } 101 } 102 103 if len(versionToPlugins) < 1 { 104 return nil, fmt.Errorf("No valid versions of plugin %s found in %s", pluginName, pluginDir) 105 } 106 107 var availableVersions []*version.Version 108 for k := range versionToPlugins { 109 vp, _ := version.ParseVersion(k) 110 availableVersions = append(availableVersions, vp) 111 } 112 latestVersion := version.GetLatestVersion(availableVersions) 113 latestBuild := getLatestOf(versionToPlugins[latestVersion.String()], latestVersion) 114 return &latestBuild, nil 115 } 116 117 func getLatestOf(plugins []PluginInfo, latestVersion *version.Version) PluginInfo { 118 for _, v := range plugins { 119 if v.Path == latestVersion.String() { 120 return v 121 } 122 } 123 sort.Sort(byPath(plugins)) 124 return plugins[0] 125 } 126 127 func sortPlugins(allPlugins map[string]PluginInfo) []PluginInfo { 128 var installedPlugins []PluginInfo 129 for _, plugin := range allPlugins { 130 installedPlugins = append(installedPlugins, plugin) 131 } 132 sort.Sort(byPluginName(installedPlugins)) 133 return installedPlugins 134 }