2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								package  commands  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								import  (  
						 
					
						
							
								
									
										
										
										
											2021-05-13 02:05:16 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"context" 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									"errors" 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-10 21:43:21 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"fmt" 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									"os" 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-03 20:52:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"path/filepath" 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-29 16:44:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"runtime" 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-13 18:29:43 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"strings" 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-29 03:42:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-02-22 16:24:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/fatih/color" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/cmd/grafana-cli/logger" 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-26 22:13:40 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/cmd/grafana-cli/models" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/cmd/grafana-cli/services" 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-27 16:47:21 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/cmd/grafana-cli/utils" 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-03 20:52:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/plugins" 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-23 17:50:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/plugins/repo" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									"github.com/grafana/grafana/pkg/plugins/storage" 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								)  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-27 16:47:21 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  validateInput ( c  utils . CommandLine ,  pluginFolder  string )  error  {  
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									arg  :=  c . Args ( ) . First ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  arg  ==  ""  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  errors . New ( "please specify plugin to install" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-06-25 02:14:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									pluginsDir  :=  c . PluginDirectory ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-29 03:42:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  pluginsDir  ==  ""  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  errors . New ( "missing pluginsDir flag" ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-03-29 03:42:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									fileInfo ,  err  :=  os . Stat ( pluginsDir ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-11 21:11:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-29 03:42:26 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  err  =  os . MkdirAll ( pluginsDir ,  os . ModePerm ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-17 02:25:48 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  fmt . Errorf ( "pluginsDir (%s) is not a writable directory" ,  pluginsDir ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-11 21:11:25 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ! fileInfo . IsDir ( )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  errors . New ( "path is not a directory" ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-02-22 16:24:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  logRestartNotice ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									logger . Info ( color . GreenString ( "Please restart Grafana after installing or removing plugins. Refer to Grafana documentation for instructions if necessary.\n\n" ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-04 16:52:09 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  installCommand ( c  utils . CommandLine )  error  {  
						 
					
						
							
								
									
										
										
										
											2016-06-25 02:14:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									pluginFolder  :=  c . PluginDirectory ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  err  :=  validateInput ( c ,  pluginFolder ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-04-26 22:13:40 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									pluginID  :=  c . Args ( ) . First ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									version  :=  c . Args ( ) . Get ( 1 ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-22 16:24:13 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  :=  installPlugin ( context . Background ( ) ,  pluginID ,  version ,  c ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  err  ==  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										logRestartNotice ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  err 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-08-23 17:50:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// installPlugin downloads the plugin code as a zip file from the Grafana.com API
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// and then extracts the zip into the plugin's directory.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  installPlugin ( ctx  context . Context ,  pluginID ,  version  string ,  c  utils . CommandLine )  error  {  
						 
					
						
							
								
									
										
										
										
											2023-05-30 17:48:52 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									repository  :=  repo . NewManager ( repo . ManagerCfg { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										SkipTLSVerify :  c . Bool ( "insecure" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										BaseURL :        c . PluginRepoURL ( ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Logger :         services . Logger , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-16 16:49:29 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-08-23 17:50:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									compatOpts  :=  repo . NewCompatOpts ( services . GrafanaVersion ,  runtime . GOOS ,  runtime . GOARCH ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									var  archive  * repo . PluginArchive 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									var  err  error 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									pluginZipURL  :=  c . PluginURL ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  pluginZipURL  !=  ""  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  archive ,  err  =  repository . GetPluginArchiveByURL ( ctx ,  pluginZipURL ,  compatOpts ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  archive ,  err  =  repository . GetPluginArchive ( ctx ,  pluginID ,  version ,  compatOpts ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									pluginFs  :=  storage . FileSystem ( services . Logger ,  c . PluginDirectory ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2023-04-20 17:52:59 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									extractedArchive ,  err  :=  pluginFs . Extract ( ctx ,  pluginID ,  archive . File ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-23 17:50:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  _ ,  dep  :=  range  extractedArchive . Dependencies  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										services . Logger . Infof ( "Fetching %s dependency..." ,  dep . ID ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d ,  err  :=  repository . GetPluginArchive ( ctx ,  dep . ID ,  dep . Version ,  compatOpts ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  fmt . Errorf ( "%v: %w" ,  fmt . Sprintf ( "failed to download plugin %s from repository" ,  dep . ID ) ,  err ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-04-20 17:52:59 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_ ,  err  =  pluginFs . Extract ( ctx ,  dep . ID ,  d . File ) 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-23 17:50:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  nil 
							 
						 
					
						
							
								
									
										
										
										
											2016-02-15 21:09:34 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-03 20:52:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// uninstallPlugin removes the plugin directory
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								func  uninstallPlugin ( _  context . Context ,  pluginID  string ,  c  utils . CommandLine )  error  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									logger . Infof ( "Removing plugin: %v\n" ,  pluginID ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									pluginPath  :=  filepath . Join ( c . PluginDirectory ( ) ,  pluginID ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									fs  :=  plugins . NewLocalFS ( pluginPath ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									logger . Debugf ( "Removing directory %v\n" ,  pluginPath ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									err  :=  fs . Remove ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-07-29 16:44:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  osAndArchString ( )  string  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									osString  :=  strings . ToLower ( runtime . GOOS ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									arch  :=  runtime . GOARCH 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  osString  +  "-"  +  arch 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-08 16:58:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  supportsCurrentArch ( version  models . Version )  bool  {  
						 
					
						
							
								
									
										
										
										
											2019-07-29 16:44:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  version . Arch  ==  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  true 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  arch  :=  range  version . Arch  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  arch  ==  osAndArchString ( )  ||  arch  ==  "any"  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  true 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  false 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-08 16:58:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								func  latestSupportedVersion ( plugin  models . Plugin )  * models . Version  {  
						 
					
						
							
								
									
										
										
										
											2020-06-26 14:46:08 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  _ ,  v  :=  range  plugin . Versions  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ver  :=  v 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-08 16:58:47 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  supportsCurrentArch ( ver )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-29 16:44:58 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  & ver 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}