func mainDiff(args []string) int { f := flag.NewFlagSet("status", flag.ExitOnError) opt_from := f.String("from", "", "Specify the source directory") opt_to := f.String("to", "", "Specify the destination directory") f.Usage = func() { fmt.Print(usageMissing) f.PrintDefaults() } f.Parse(args) src, dst := findSourceDest(*opt_from, *opt_to, f.Args()) srcfiles, err := commit.ReadCommit(src) if err != nil { fmt.Fprintf(os.Stderr, "%s: %s", src, err.Error()) } dstfiles, err := commit.ReadCommit(dst) if err != nil { fmt.Fprintf(os.Stderr, "%s: %s", dst, err.Error()) } var filelist []string for file := range srcfiles.ByPath { filelist = append(filelist, file) } for file := range dstfiles.ByPath { if _, ok := srcfiles.ByPath[file]; !ok { filelist = append(filelist, file) } } sort.Strings(filelist) for _, file := range filelist { var s, d commit.Entry sid, hassrc := srcfiles.ByPath[file] did, hasdst := dstfiles.ByPath[file] if hassrc { s = srcfiles.Entries[sid] } if hasdst { d = dstfiles.Entries[did] } if hassrc && !hasdst { fmt.Printf("- %s\t%s\n", s.HashText(), commit.EncodePath(file)) } else if !hassrc && hasdst { fmt.Printf("+ %s\t%s\n", d.HashText(), commit.EncodePath(file)) } else if !bytes.Equal(s.Hash, d.Hash) { fmt.Printf("- %s\t%s\n", s.HashText(), commit.EncodePath(file)) fmt.Printf("+ %s\t%s\n", d.HashText(), commit.EncodePath(file)) } } return 0 }
func copyTree(srcdir, dstdir string, src, dst *commit.Commit, p Progress) ([]commit.Entry, error, []error) { var errs []error var success []commit.Entry okdirs := map[string]bool{} if p != nil { p.SetProgress(2, 4, "Prepare copy: open "+dstdir) } c, err := commit.OpenDirAppend(dstdir) if err != nil { return success, err, errs } defer c.Close() if p != nil { p.SetProgress(2, 4, "Prepare copy: compute how many files to copy") } numfiles := len(src.Entries) if p != nil { numfiles = 0 for _, s := range src.Entries { if wantCopy(s, src, dst) { numfiles = numfiles + 1 } } } if p != nil { p.SetProgress(2, numfiles+4, fmt.Sprintf("Prepare copy: starting copy for %d files...", numfiles)) } for _, s := range src.Entries { // Cannot copy, skip if !wantCopy(s, src, dst) { continue } // Find destination file name var d commit.Entry = commit.Entry(s) _, conflict := dst.ByPath[s.Path] if conflict { d.Path = commit.FindConflictFileName(s, dst) if d.Path == "" { continue } } srcpath := filepath.Join(srcdir, s.Path) dstpath := filepath.Join(dstdir, d.Path) if p != nil { p.SetProgress(len(success)+3, numfiles+4, "Copy "+d.Path) } // Create parent dirs err, ers := makeParentDirs(srcdir, dstdir, s.Path, okdirs) errs = append(errs, ers...) if err != nil { return success, err, errs } // Copy file err, ers = CopyFileNoReplace(srcpath, dstpath) errs = append(errs, ers...) if err != nil { return success, err, errs } // In case of conflicts, mark the file as a conflict if conflict { errs = append(errs, repo.MarkConflict(filepath.Join(dstdir, s.Path), dstpath)...) } // Add to commit file err = c.Add(d) if err != nil { errs = append(errs, err) } success = append(success, d) } return success, nil, errs }