Files
kopia/cli/command_index_recover.go
Jarek Kowalski c8fcae93aa logging: refactored logging
This is mostly mechanical and changes how loggers are instantiated.

Logger is now associated with a context, passed around all methods,
(most methods had ctx, but had to add it in a few missing places).

By default Kopia does not produce any logs, but it can be overridden,
either locally for a nested context, by calling

ctx = logging.WithLogger(ctx, newLoggerFunc)

To override logs globally, call logging.SetDefaultLogger(newLoggerFunc)

This refactoring allowed removing dependency from Kopia repo
and go-logging library (the CLI still uses it, though).

It is now also possible to have all test methods emit logs using
t.Logf() so that they show up in failure reports, which should make
debugging of test failures suck less.
2020-02-25 17:24:44 -08:00

68 lines
2.0 KiB
Go

package cli
import (
"context"
"github.com/pkg/errors"
"github.com/kopia/kopia/repo"
"github.com/kopia/kopia/repo/blob"
"github.com/kopia/kopia/repo/content"
)
var (
blockIndexRecoverCommand = indexCommands.Command("recover", "Recover indexes from pack blobs")
blockIndexRecoverBlobIDs = blockIndexRecoverCommand.Flag("blobs", "Names of pack blobs to recover from (default=all packs)").Strings()
blockIndexRecoverCommit = blockIndexRecoverCommand.Flag("commit", "Commit recovered content").Bool()
)
func runRecoverBlockIndexesAction(ctx context.Context, rep *repo.Repository) error {
var totalCount int
defer func() {
if totalCount == 0 {
log(ctx).Infof("No blocks recovered.")
return
}
if !*blockIndexRecoverCommit {
log(ctx).Infof("Found %v blocks to recover, but not committed. Re-run with --commit", totalCount)
} else {
log(ctx).Infof("Recovered %v blocks.", totalCount)
}
}()
if len(*blockIndexRecoverBlobIDs) == 0 {
for _, prefix := range content.PackBlobIDPrefixes {
err := rep.Blobs.ListBlobs(ctx, prefix, func(bm blob.Metadata) error {
recoverIndexFromSinglePackFile(ctx, rep, bm.BlobID, bm.Length, &totalCount)
return nil
})
if err != nil {
return errors.Wrapf(err, "recovering indexes from prefix %q", prefix)
}
}
}
for _, packFile := range *blockIndexRecoverBlobIDs {
recoverIndexFromSinglePackFile(ctx, rep, blob.ID(packFile), 0, &totalCount)
}
return nil
}
func recoverIndexFromSinglePackFile(ctx context.Context, rep *repo.Repository, blobID blob.ID, length int64, totalCount *int) {
recovered, err := rep.Content.RecoverIndexFromPackBlob(ctx, blobID, length, *blockIndexRecoverCommit)
if err != nil {
log(ctx).Warningf("unable to recover index from %v: %v", blobID, err)
return
}
*totalCount += len(recovered)
log(ctx).Infof("Recovered %v entries from %v (commit=%v)", len(recovered), blobID, *blockIndexRecoverCommit)
}
func init() {
blockIndexRecoverCommand.Action(repositoryAction(runRecoverBlockIndexesAction))
}