blob: 39975ea6e5eabfe684c3f79cfa3551f898d3dd7a [file] [log] [blame]
// Copyright 2022 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
import (
"fmt"
"os"
"path/filepath"
"sort"
"go.fuchsia.dev/jiri"
"go.fuchsia.dev/jiri/cmdline"
"go.fuchsia.dev/jiri/gitutil"
"go.fuchsia.dev/jiri/project"
)
var cmdCheckClean = &cmdline.Command{
Runner: jiri.RunnerFunc(runCheckClean),
Name: "check-clean",
Short: "Checks if the checkout is clean",
Long: `
Exits non-zero and prints repositories (and their status) if they contain
uncommitted changes.
`,
}
func runCheckClean(jirix *jiri.X, args []string) error {
localProjects, err := project.LocalProjects(jirix, project.FastScan)
if err != nil {
return err
}
cDir, err := os.Getwd()
if err != nil {
return err
}
states, err := project.GetProjectStates(jirix, localProjects, false)
if err != nil {
return err
}
var keys project.ProjectKeys
for key := range localProjects {
keys = append(keys, key)
}
sort.Sort(keys)
dirtyProjects := make(map[string]string)
for _, key := range keys {
localProject := localProjects[key]
state, ok := states[key]
if !ok {
// this should not happen
panic(fmt.Sprintf("State not found for project %q", localProject.Name))
}
if statusFlags.branch != "" && (statusFlags.branch != state.CurrentBranch.Name) {
continue
}
relativePath, err := filepath.Rel(cDir, localProject.Path)
if err != nil {
return err
}
scm := gitutil.New(jirix, gitutil.RootDirOpt(localProject.Path))
changes, err := scm.ShortStatus()
if err != nil {
jirix.Logger.Errorf("%s :%s\n\n", fmt.Sprintf("getting changes for project %s(%s)", localProject.Name, relativePath), err)
jirix.IncrementFailures()
continue
}
if changes != "" {
dirtyProjects[relativePath] = changes
}
}
var finalErr error
if jirix.Failures() != 0 {
finalErr = fmt.Errorf("completed with non-fatal errors")
} else if len(dirtyProjects) > 0 {
finalErr = fmt.Errorf("Checkout is not clean!")
}
if len(dirtyProjects) > 0 {
fmt.Println("Dirty projects:")
for relativePath, changes := range dirtyProjects {
fmt.Printf("%s\n%s\n\n", relativePath, changes)
}
}
return finalErr
}