Skip to content

Commit 5254a12

Browse files
authored
Merge pull request #3 from sarus-suite/rsync-mirror
Rsync mirror
2 parents d66dc22 + 7a9aeb2 commit 5254a12

File tree

2 files changed

+61
-2
lines changed

2 files changed

+61
-2
lines changed

cmd/migration.go

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ func RunMigration(cfg common.Config) (*storage.Image, error) {
3535
if err != nil { return nil, err }
3636
defer cleanupSrcStore()
3737

38-
scratchStore, cleanupScratch, err := setupScratchStore(cfg)
38+
scratchStore, cleanupScratch, err := setupScratchStore(&cfg)
3939
if err != nil { return nil, err }
4040
defer cleanupScratch()
4141

@@ -209,9 +209,19 @@ func setupSrcStore(cfg common.Config) (storage.Store, func(), error) {
209209
return srcStore, cleanup, nil
210210
}
211211

212-
func setupScratchStore(cfg common.Config) (storage.Store, func(), error) {
212+
func setupScratchStore(cfg *common.Config) (storage.Store, func(), error) {
213213
sublog := log.WithField("fn", "setupScratchStore")
214214

215+
// we mirror the RoStoragePath to hide the fact that might be a networkedFS
216+
mirror, mirrorCleanup, err := common.Mirror(cfg.RoStoragePath)
217+
if err != nil {
218+
sublog.Debug("Failed to mount mirror: %v", err)
219+
return nil, nil, err
220+
}
221+
sublog.Infof("Mounted mirror of %s at %s", cfg.RoStoragePath, mirror)
222+
originalPath := cfg.RoStoragePath
223+
cfg.RoStoragePath = mirror
224+
215225
sublog.Info("Setting up scratch Store")
216226
scratchRun, cleanupScratch := common.MustTempDir("scratch-runroot-*")
217227
scratchStore, err := storage.GetStore(storage.StoreOptions{
@@ -224,8 +234,10 @@ func setupScratchStore(cfg common.Config) (storage.Store, func(), error) {
224234
return nil, nil, err
225235
}
226236
cleanup := func() {
237+
cfg.RoStoragePath = originalPath
227238
scratchStore.Shutdown(false)
228239
cleanupScratch()
240+
mirrorCleanup()
229241
}
230242
return scratchStore, cleanup, nil
231243
}
@@ -304,6 +316,8 @@ func putFlattenedLayer(store storage.Store, dummyDir string, digest godigest.Dig
304316
}
305317

306318
func readOverlayLink(layer *storage.Layer, cfg common.Config) (string, error) {
319+
sublog := log.WithField("fn", "readOverlayLink")
320+
sublog.Infof("Reading overlay link from %s", cfg.RoStoragePath)
307321
linkBytes, err := os.ReadFile(filepath.Join(cfg.RoStoragePath, "overlay", layer.ID, "link"))
308322
if err != nil {
309323
return "", fmt.Errorf("read overlay link: %w", err)

common/rsync-mirror.go

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
package common
2+
3+
import (
4+
"fmt"
5+
"os"
6+
"os/exec"
7+
"path/filepath"
8+
)
9+
10+
// Mirror creates a writable mirror of srcDir in a temp directory.
11+
// It returns the mirror path, a cleanup func (which pushes changes back to srcDir),
12+
// and any error from setup.
13+
//
14+
// Note: this requires the "rsync" binary to be installed and in PATH.
15+
func Mirror(srcDir string) (mirrorDir string, cleanup func() error, err error) {
16+
mp, err := os.MkdirTemp("", "rsync-mirror-")
17+
if err != nil {
18+
return "", nil, fmt.Errorf("failed to create temp dir: %w", err)
19+
}
20+
21+
// Ensure the srcDir path ends with a trailing slash for rsync behavior
22+
srcPath := filepath.Clean(srcDir) + string(os.PathSeparator)
23+
mirrorPath := filepath.Clean(mp) + string(os.PathSeparator)
24+
25+
cmd := exec.Command("rsync", "-a", srcPath, mirrorPath)
26+
if out, err2 := cmd.CombinedOutput(); err2 != nil {
27+
os.RemoveAll(mp)
28+
return "", nil, fmt.Errorf("initial rsync failed: %v\n%s", err2, out)
29+
}
30+
31+
cleanup = func() error {
32+
cmdBack := exec.Command("rsync", "-a", "--delete", mirrorPath, srcPath)
33+
if out, err2 := cmdBack.CombinedOutput(); err2 != nil {
34+
return fmt.Errorf("rsync back failed: %v\n%s", err2, out)
35+
}
36+
37+
if err2 := os.RemoveAll(mp); err2 != nil {
38+
return fmt.Errorf("failed to remove temp dir %q: %w", mp, err2)
39+
}
40+
return nil
41+
}
42+
43+
return mp, cleanup, nil
44+
}
45+

0 commit comments

Comments
 (0)