gitforgefs/main.go

206 lines
5.3 KiB
Go
Raw Normal View History

2020-12-26 19:36:09 +00:00
package main
2020-12-27 03:30:19 +00:00
import (
"flag"
"fmt"
2020-12-29 02:37:18 +00:00
"net/url"
2020-12-27 03:30:19 +00:00
"os"
2020-12-30 23:00:37 +00:00
"path/filepath"
2020-12-27 03:30:19 +00:00
"github.com/badjware/gitlabfs/fs"
2020-12-29 02:37:18 +00:00
"github.com/badjware/gitlabfs/git"
2020-12-27 03:30:19 +00:00
"github.com/badjware/gitlabfs/gitlab"
2020-12-30 23:00:37 +00:00
"gopkg.in/yaml.v2"
2020-12-27 03:30:19 +00:00
)
2020-12-26 19:36:09 +00:00
2020-12-30 23:00:37 +00:00
const (
OnCloneInit = "init"
OnCloneInitPull = "init-pull"
2020-12-30 23:00:37 +00:00
OnCloneNoCheckout = "no-checkout"
OnCloneCheckout = "checkout"
)
type (
Config struct {
FS FSConfig `yaml:"fs,omitempty"`
Gitlab GitlabConfig `yaml:"gitlab,omitempty"`
Git GitConfig `yaml:"git,omitempty"`
}
FSConfig struct {
Mountpoint string `yaml:"mountpoint,omitempty"`
}
GitlabConfig struct {
URL string `yaml:"url,omitempty"`
Token string `yaml:"token,omitempty"`
GroupIDs []int `yaml:"group_ids,omitempty"`
UserIDs []int `yaml:"user_ids,omitempty"`
IncludeCurrentUser bool `yaml:"include_current_user,omitempty"`
}
GitConfig struct {
CloneLocation string `yaml:"clone_location,omitempty"`
Remote string `yaml:"remote,omitempty"`
PullMethod string `yaml:"pull_method,omitempty"`
OnClone string `yaml:"on_clone,omitempty"`
AutoPull bool `yaml:"auto_pull,omitempty"`
Depth int `yaml:"depth,omitempty"`
CloneQueueSize int `yaml:"clone_queue_size,omitempty"`
CloneWorkerCount int `yaml:"clone_worker_count,omitempty"`
PullQueueSize int `yaml:"pull_queue_size,omitempty"`
PullWorkerCount int `yaml:"pull_worker_count,omitempty"`
2020-12-30 23:00:37 +00:00
}
)
func loadConfig(configPath string) (*Config, error) {
// defaults
dataHome := os.Getenv("XDG_DATA_HOME")
if dataHome == "" {
dataHome = filepath.Join(os.Getenv("HOME"), ".local/share")
}
defaultCloneLocation := filepath.Join(dataHome, "gitlabfs")
config := &Config{
FS: FSConfig{
Mountpoint: "",
},
Gitlab: GitlabConfig{
URL: "https://gitlab.com",
Token: "",
GroupIDs: []int{9970},
UserIDs: []int{},
IncludeCurrentUser: true,
},
Git: GitConfig{
CloneLocation: defaultCloneLocation,
Remote: "origin",
PullMethod: "http",
OnClone: "init",
AutoPull: false,
Depth: 0,
CloneQueueSize: 200,
CloneWorkerCount: 5,
PullQueueSize: 500,
PullWorkerCount: 5,
2020-12-30 23:00:37 +00:00
},
}
if configPath != "" {
f, err := os.Open(configPath)
if err != nil {
return nil, fmt.Errorf("failed to open config file: %v", err)
}
defer f.Close()
d := yaml.NewDecoder(f)
if err := d.Decode(config); err != nil {
return nil, fmt.Errorf("failed to parse config file: %v", err)
}
}
return config, nil
}
func makeGitlabConfig(config *Config) (*gitlab.GitlabClientParam, error) {
// parse pull_method
if config.Git.PullMethod != gitlab.PullMethodHTTP && config.Git.PullMethod != gitlab.PullMethodSSH {
return nil, fmt.Errorf("pull_method must be either \"%v\" or \"%v\"", gitlab.PullMethodHTTP, gitlab.PullMethodSSH)
}
return &gitlab.GitlabClientParam{
PullMethod: config.Git.PullMethod,
}, nil
}
func makeGitConfig(config *Config) (*git.GitClientParam, error) {
// Parse the gilab url
parsedGitlabURL, err := url.Parse(config.Gitlab.URL)
if err != nil {
return nil, err
}
// parse on_clone
pullAfterClone := false
clone := false
2020-12-30 23:00:37 +00:00
checkout := false
if config.Git.OnClone == OnCloneInit {
pullAfterClone = false
clone = false
checkout = false
} else if config.Git.OnClone == OnCloneInitPull {
pullAfterClone = true
clone = false
2020-12-30 23:00:37 +00:00
checkout = false
} else if config.Git.OnClone == OnCloneNoCheckout {
pullAfterClone = false
clone = true
2020-12-30 23:00:37 +00:00
checkout = false
} else if config.Git.OnClone == OnCloneCheckout {
pullAfterClone = false
clone = true
2020-12-30 23:00:37 +00:00
checkout = true
} else {
return nil, fmt.Errorf("on_clone must be either \"%v\", \"%v\" or \"%V\"", OnCloneInit, OnCloneNoCheckout, OnCloneCheckout)
}
return &git.GitClientParam{
CloneLocation: config.Git.CloneLocation,
RemoteName: config.Git.Remote,
RemoteURL: parsedGitlabURL,
PullAfterClone: pullAfterClone,
Clone: clone,
Checkout: checkout,
AutoPull: config.Git.AutoPull,
PullDepth: config.Git.Depth,
CloneBuffSize: config.Git.CloneQueueSize,
CloneWorkerCount: config.Git.CloneWorkerCount,
PullBuffSize: config.Git.PullQueueSize,
PullWorkerCount: config.Git.PullWorkerCount,
2020-12-30 23:00:37 +00:00
}, nil
}
2020-12-26 19:36:09 +00:00
func main() {
2020-12-30 23:00:37 +00:00
configPath := flag.String("config", "", "the config file")
debug := flag.Bool("debug", false, "enable debug logging")
2020-12-27 03:30:19 +00:00
flag.Parse()
2020-12-30 23:00:37 +00:00
config, err := loadConfig(*configPath)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
// Configure mountpoint
mountpoint := config.FS.Mountpoint
if flag.NArg() == 1 {
mountpoint = flag.Arg(0)
}
if mountpoint == "" {
fmt.Printf("usage: %s MOUNTPOINT\n", os.Args[0])
os.Exit(2)
2020-12-27 03:30:19 +00:00
}
2020-12-30 23:00:37 +00:00
// Create the git client
gitClientParam, err := makeGitConfig(config)
2020-12-29 02:37:18 +00:00
if err != nil {
2020-12-30 23:00:37 +00:00
fmt.Println(err)
2020-12-29 02:37:18 +00:00
os.Exit(1)
}
2020-12-30 23:00:37 +00:00
gitClient, _ := git.NewClient(*gitClientParam)
2020-12-27 03:30:19 +00:00
2020-12-29 02:37:18 +00:00
// Create the gitlab client
2020-12-30 23:00:37 +00:00
gitlabClientParam, err := makeGitlabConfig(config)
if err != nil {
fmt.Println(err)
os.Exit(1)
2020-12-29 02:37:18 +00:00
}
2020-12-30 23:00:37 +00:00
gitlabClient, _ := gitlab.NewClient(config.Gitlab.URL, config.Gitlab.Token, *gitlabClientParam)
2020-12-29 02:37:18 +00:00
// Start the filesystem
2020-12-30 23:00:37 +00:00
fs.Start(
mountpoint,
config.Gitlab.GroupIDs,
config.Gitlab.UserIDs,
&fs.FSParam{Git: gitClient, Gitlab: gitlabClient},
*debug,
)
2020-12-26 19:36:09 +00:00
}