You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							211 lines
						
					
					
						
							4.3 KiB
						
					
					
				
			
		
		
		
			
			
			
		
		
	
	
							211 lines
						
					
					
						
							4.3 KiB
						
					
					
				| package main | |
| 
 | |
| import ( | |
| 	"embed" | |
| 	"fmt" | |
| 	"io" | |
| 	"io/fs" | |
| 	"os" | |
| 	"strings" | |
| 	"sync" | |
| 	"text/template" | |
| 	"time" | |
| 	"unicode" | |
| 	"unicode/utf8" | |
| 
 | |
| 	weed_server "github.com/seaweedfs/seaweedfs/weed/server" | |
| 	"github.com/seaweedfs/seaweedfs/weed/util" | |
| 	flag "github.com/seaweedfs/seaweedfs/weed/util/fla9" | |
| 
 | |
| 	"github.com/getsentry/sentry-go" | |
| 	"github.com/seaweedfs/seaweedfs/weed/command" | |
| 	"github.com/seaweedfs/seaweedfs/weed/glog" | |
| 	util_http "github.com/seaweedfs/seaweedfs/weed/util/http" | |
| ) | |
| 
 | |
| var IsDebug *bool | |
| 
 | |
| var commands = command.Commands | |
| 
 | |
| var exitStatus = 0 | |
| var exitMu sync.Mutex | |
| 
 | |
| func setExitStatus(n int) { | |
| 	exitMu.Lock() | |
| 	if exitStatus < n { | |
| 		exitStatus = n | |
| 	} | |
| 	exitMu.Unlock() | |
| } | |
| 
 | |
| //go:embed static | |
| var static embed.FS | |
| 
 | |
| func init() { | |
| 	weed_server.StaticFS, _ = fs.Sub(static, "static") | |
| 
 | |
| 	flag.Var(&util.ConfigurationFileDirectory, "config_dir", "directory with toml configuration files") | |
| } | |
| 
 | |
| func main() { | |
| 	glog.MaxSize = 1024 * 1024 * 10 | |
| 	glog.MaxFileCount = 5 | |
| 	flag.Usage = usage | |
| 
 | |
| 	err := sentry.Init(sentry.ClientOptions{ | |
| 		SampleRate:       0.1, | |
| 		EnableTracing:    true, | |
| 		TracesSampleRate: 0.1, | |
| 	}) | |
| 	if err != nil { | |
| 		fmt.Fprintf(os.Stderr, "sentry.Init: %v", err) | |
| 	} | |
| 	// Flush buffered events before the program terminates. | |
| 	// Set the timeout to the maximum duration the program can afford to wait. | |
| 	defer sentry.Flush(2 * time.Second) | |
| 
 | |
| 	if command.AutocompleteMain(commands) { | |
| 		return | |
| 	} | |
| 
 | |
| 	flag.Parse() | |
| 
 | |
| 	args := flag.Args() | |
| 	if len(args) < 1 { | |
| 		usage() | |
| 	} | |
| 
 | |
| 	if args[0] == "help" { | |
| 		help(args[1:]) | |
| 		for _, cmd := range commands { | |
| 			if len(args) >= 2 && cmd.Name() == args[1] && cmd.Run != nil { | |
| 				fmt.Fprintf(os.Stderr, "Default Parameters:\n") | |
| 				cmd.Flag.PrintDefaults() | |
| 			} | |
| 		} | |
| 		return | |
| 	} | |
| 
 | |
| 	util_http.InitGlobalHttpClient() | |
| 	for _, cmd := range commands { | |
| 		if cmd.Name() == args[0] && cmd.Run != nil { | |
| 			cmd.Flag.Usage = func() { cmd.Usage() } | |
| 			cmd.Flag.Parse(args[1:]) | |
| 			args = cmd.Flag.Args() | |
| 			IsDebug = cmd.IsDebug | |
| 			if !cmd.Run(cmd, args) { | |
| 				fmt.Fprintf(os.Stderr, "\n") | |
| 				cmd.Flag.Usage() | |
| 				fmt.Fprintf(os.Stderr, "Default Parameters:\n") | |
| 				cmd.Flag.PrintDefaults() | |
| 				// Command execution failed - general error | |
| 				setExitStatus(1) | |
| 			} | |
| 			exit() | |
| 			return | |
| 		} | |
| 	} | |
| 
 | |
| 	// Unknown command - syntax error | |
| 	fmt.Fprintf(os.Stderr, "weed: unknown subcommand %q\nRun 'weed help' for usage.\n", args[0]) | |
| 	setExitStatus(2) | |
| 	exit() | |
| } | |
| 
 | |
| var usageTemplate = ` | |
| SeaweedFS: store billions of files and serve them fast! | |
|  | |
| Usage: | |
|  | |
| 	weed command [arguments] | |
|  | |
| The commands are: | |
| {{range .}}{{if .Runnable}} | |
|     {{.Name | printf "%-11s"}} {{.Short}}{{end}}{{end}} | |
|  | |
| Use "weed help [command]" for more information about a command. | |
|  | |
| ` | |
| 
 | |
| var helpTemplate = `{{if .Runnable}}Usage: weed {{.UsageLine}} | |
| {{end}} | |
|   {{.Long}} | |
| ` | |
| 
 | |
| // tmpl executes the given template text on data, writing the result to w. | |
| func tmpl(w io.Writer, text string, data interface{}) { | |
| 	t := template.New("top") | |
| 	t.Funcs(template.FuncMap{"trim": strings.TrimSpace, "capitalize": capitalize}) | |
| 	template.Must(t.Parse(text)) | |
| 	if err := t.Execute(w, data); err != nil { | |
| 		panic(err) | |
| 	} | |
| } | |
| 
 | |
| func capitalize(s string) string { | |
| 	if s == "" { | |
| 		return s | |
| 	} | |
| 	r, n := utf8.DecodeRuneInString(s) | |
| 	return string(unicode.ToTitle(r)) + s[n:] | |
| } | |
| 
 | |
| func printUsage(w io.Writer) { | |
| 	tmpl(w, usageTemplate, commands) | |
| } | |
| 
 | |
| func usage() { | |
| 	printUsage(os.Stderr) | |
| 	fmt.Fprintf(os.Stderr, "For Logging, use \"weed [logging_options] [command]\". The logging options are:\n") | |
| 	flag.PrintDefaults() | |
| 	// Invalid command line usage - syntax error | |
| 	setExitStatus(2) | |
| 	exit() | |
| } | |
| 
 | |
| // help implements the 'help' command. | |
| func help(args []string) { | |
| 	if len(args) == 0 { | |
| 		printUsage(os.Stdout) | |
| 		// Success - help displayed correctly | |
| 		return | |
| 	} | |
| 	if len(args) != 1 { | |
| 		fmt.Fprintf(os.Stderr, "usage: weed help command\n\nToo many arguments given.\n") | |
| 		// Invalid help usage - syntax error | |
| 		setExitStatus(2) | |
| 		exit() | |
| 	} | |
| 
 | |
| 	arg := args[0] | |
| 
 | |
| 	for _, cmd := range commands { | |
| 		if cmd.Name() == arg { | |
| 			tmpl(os.Stdout, helpTemplate, cmd) | |
| 			// Success - help for specific command displayed correctly | |
| 			return | |
| 		} | |
| 	} | |
| 
 | |
| 	fmt.Fprintf(os.Stderr, "Unknown help topic %#q.  Run 'weed help'.\n", arg) | |
| 	// Unknown help topic - syntax error | |
| 	setExitStatus(2) | |
| 	exit() | |
| } | |
| 
 | |
| var atexitFuncs []func() | |
| 
 | |
| func atexit(f func()) { | |
| 	atexitFuncs = append(atexitFuncs, f) | |
| } | |
| 
 | |
| func exit() { | |
| 	for _, f := range atexitFuncs { | |
| 		f() | |
| 	} | |
| 	os.Exit(exitStatus) | |
| } | |
| 
 | |
| func debug(params ...interface{}) { | |
| 	glog.V(4).Infoln(params...) | |
| }
 |