package gitpb import ( "errors" "path/filepath" "slices" "strings" "go.wit.com/lib/cobol" "go.wit.com/lib/config" "go.wit.com/lib/env" "go.wit.com/log" timestamppb "google.golang.org/protobuf/types/known/timestamppb" ) // loads what is on disk already. that is all func (r *Repo) LoadRemote(remoteName string) (*Stats, error) { fullname := filepath.Join(r.FullPath, ".git", remoteName+".pb") stats := NewStats() stats.Filename = fullname err := config.ForceCreatePB(stats) return stats, err } var standardFmts []string = []string{"H", "T", "at", "ct", "f", "d"} var standardSeperator string = "___FORGE___" func makeFmts() string { // fmts := strings.Fields(config.GetPanic("standardFmts")) // fmts := strings.Fields(config.GetPanic("standardSeperator")) var all []string for _, fmtvar := range standardFmts { all = append(all, "%"+fmtvar) } return "--format=" + strings.Join(all, standardSeperator) } func makeStat(line string) *Stat { line = strings.TrimSpace(line) parts := strings.Split(line, standardSeperator) if len(parts) != 6 { log.Printf("BAD LINE: len(%d) %s\n", len(parts), line) return nil } newstat := new(Stat) newstat.Hash = parts[0] newstat.TreeHash = parts[1] t, err := cobol.GetTime(parts[2]) _ = err if t != nil { newstat.AuthorTime = timestamppb.New(*t) } t, err = cobol.GetTime(parts[3]) if t != nil { newstat.CommitTime = timestamppb.New(*t) } newstat.SanitizedSubject = parts[4] newstat.Tags = parts[5] return newstat } // makes a new file. File must be empty at start func (r *Repo) MakeRemote(remoteName string) (*Stats, error) { stats, err := r.LoadRemote(remoteName) if err != nil { return stats, err } if stats.Len() != 0 { // file was already created and populated with data return stats, nil } cmd := []string{"git", "log", makeFmts(), "origin/HEAD"} // HEAD is _NOT_ always set if env.True("stats") { log.Info("STATS VERBOSE Run:", cmd) } cmdout := r.Run(cmd) if len(cmdout.Stdout) == 0 { return stats, errors.New("got nothing from git ls-remote") } var counter int for _, line := range cmdout.Stdout { if env.True("stats") { log.Printf("LINE:%s %d %s\n", line, counter, r.FullPath) } counter += 1 newstat := makeStat(line) stats.Append(newstat) } if counter > 0 { stats.SaveByHash() } return stats, nil } // looks for new hashes. Run this after 'git fetch' func (r *Repo) UpdateRemote(remoteName string) error { stats, err := r.LoadRemote(remoteName) if err != nil { return err } if stats.Len() == 0 { return errors.New("need to make file instead") } // cmd := []string{"git", "log", "-n", "100", makeFmts(), "origin/HEAD"} // HEAD is _NOT_ always set cmd := []string{"git", "log", makeFmts(), "origin/HEAD"} // HEAD is _NOT_ always set if env.True("stats") { log.Info("STATS VERBOSE Run:", cmd) } cmdout := r.Run(cmd) if len(cmdout.Stdout) == 0 { return errors.New("got nothing from git ls-remote") } var counter int for _, line := range cmdout.Stdout { if env.True("stats") { log.Printf("LINE:%s %d %s\n", line, counter, r.FullPath) } counter += 1 newstat := makeStat(line) // TODO: convert this protobuf to raw binary, then do a raw BinarySearch() on the hash n, found := slices.BinarySearchFunc(stats.Stats, newstat, func(a, b *Stat) int { return strings.Compare(a.Hash, b.Hash) }) _ = n if found { // log.Info("found", n) continue } stats.Append(newstat) } if counter > 0 { stats.SaveByHash() } return nil }