Skip to content

Commit 23b6a24

Browse files
authored
Distinguish local and remote files (#58)
# Changes ## Primary change N/A ## Supporting changes Split code used for local/remote data and DRY it up. ## Future work Separate packges?
1 parent d8ca9ab commit 23b6a24

File tree

9 files changed

+158
-86
lines changed

9 files changed

+158
-86
lines changed
File renamed without changes.

src/go/svcfs/json_meta_repo.go

Lines changed: 46 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -10,15 +10,15 @@ import (
1010

1111
func NewJsonMetaRepo(repositoryPath string) *JsonMetaRepo {
1212
return &JsonMetaRepo{
13-
localDataFile: localDataFile(repositoryPath),
14-
metaDataFile: metaDataFile(repositoryPath),
13+
localDataFile: localDataFile(repositoryPath),
14+
sharedDataFile: sharedDataFile(repositoryPath),
1515
}
1616
}
1717

1818
// A meta repo that stores meta data in JSON files in the specified directory.
1919
type JsonMetaRepo struct {
20-
localDataFile string
21-
metaDataFile string
20+
localDataFile string
21+
sharedDataFile string
2222
}
2323

2424
/* Local repositories */
@@ -43,18 +43,27 @@ func (repo *JsonMetaRepo) AddLocals(localPaths []string) error {
4343
}
4444

4545
func (repo *JsonMetaRepo) addLocal(localPath string) error {
46-
return updateFile(repo.localDataFile, func(rootObject *rootObjectData) {
47-
rootObject.MetaRepo.AppendLocalRepository(localRepositoryData{Path: localPath})
48-
})
46+
return updateFile(
47+
repo.localDataFile,
48+
ReadLocalMetaRepoFile,
49+
func(rootObject *localRootObjectData) {
50+
rootObject.MetaRepo.AppendLocalRepository(localRepositoryData{Path: localPath})
51+
},
52+
func(rootObject *localRootObjectData, dataFile string) error {
53+
return rootObject.WriteTo(dataFile)
54+
},
55+
)
4956
}
5057

5158
func (repo *JsonMetaRepo) ListLocal() (core.Repositories, error) {
5259
return queryFile(
5360
repo.localDataFile,
5461
core.NoRepositories(),
55-
func(rootObject *rootObjectData) (core.Repositories, error) {
62+
ReadLocalMetaRepoFile,
63+
func(rootObject *localRootObjectData) (core.Repositories, error) {
5664
return rootObject.MetaRepo.MapLocalRepositories()
57-
})
65+
},
66+
)
5867
}
5968

6069
/* Remote repositories */
@@ -79,28 +88,37 @@ func (repo *JsonMetaRepo) AddRemotes(hostUrls []*url.URL) error {
7988
}
8089

8190
func (repo *JsonMetaRepo) addRemote(hostUrl *url.URL) error {
82-
return updateFile(repo.metaDataFile, func(rootObject *rootObjectData) {
83-
rootObject.MetaRepo.AppendRemoteRepository(remoteRepositoryData{Url: hostUrl.String()})
84-
})
91+
return updateFile(
92+
repo.sharedDataFile,
93+
ReadSharedMetaRepoFile,
94+
func(rootObject *sharedRootObjectData) {
95+
rootObject.MetaRepo.AppendRemoteRepository(remoteRepositoryData{Url: hostUrl.String()})
96+
},
97+
func(rootObject *sharedRootObjectData, dataFile string) error {
98+
return rootObject.WriteTo(dataFile)
99+
},
100+
)
85101
}
86102

87103
func (repo *JsonMetaRepo) ListRemote() (core.Repositories, error) {
88104
return queryFile(
89-
repo.metaDataFile,
105+
repo.sharedDataFile,
90106
core.NoRepositories(),
91-
func(rootObject *rootObjectData) (core.Repositories, error) {
107+
ReadSharedMetaRepoFile,
108+
func(rootObject *sharedRootObjectData) (core.Repositories, error) {
92109
return rootObject.MetaRepo.MapRemoteRepositories()
93110
})
94111
}
95112

96113
/* I/O */
97114

98-
func queryFile[V any](
115+
func queryFile[RootObject any, Result any](
99116
dataFile string,
100-
defaultValue V,
101-
queryData func(*rootObjectData) (V, error),
102-
) (V, error) {
103-
if rootObject, readErr := ReadMetaRepoFile(dataFile); readErr != nil {
117+
defaultValue Result,
118+
fetchData func(string) (RootObject, error),
119+
queryData func(RootObject) (Result, error),
120+
) (Result, error) {
121+
if rootObject, readErr := fetchData(dataFile); readErr != nil {
104122
return defaultValue, fmt.Errorf("failed to read file %s; %w", dataFile, readErr)
105123
} else if result, queryErr := queryData(rootObject); queryErr != nil {
106124
return defaultValue, fmt.Errorf("failed to query data; %w", queryErr)
@@ -109,17 +127,20 @@ func queryFile[V any](
109127
}
110128
}
111129

112-
type updateDataFn = func(*rootObjectData)
113-
114-
func updateFile(dataFile string, updateData updateDataFn) error {
115-
var rootObject *rootObjectData
116-
rootObject, readErr := ReadMetaRepoFile(dataFile)
130+
func updateFile[RootObject any](
131+
dataFile string,
132+
fetchData func(string) (RootObject, error),
133+
updateData func(RootObject),
134+
writeData func(RootObject, string) error,
135+
) error {
136+
var rootObject RootObject
137+
rootObject, readErr := fetchData(dataFile)
117138
if readErr != nil {
118139
return fmt.Errorf("failed to read file %s; %w", dataFile, readErr)
119140
}
120141

121142
updateData(rootObject)
122-
if writeErr := rootObject.WriteTo(dataFile); writeErr != nil {
143+
if writeErr := writeData(rootObject, dataFile); writeErr != nil {
123144
return fmt.Errorf("failed to write file %s; %w", dataFile, writeErr)
124145
} else {
125146
return nil

src/go/svcfs/json_meta_repo_admin.go

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -22,18 +22,19 @@ type JsonMetaRepoAdmin struct {
2222
func (admin *JsonMetaRepoAdmin) Create(repositoryDir string) error {
2323
return initDirectory(
2424
localDataFile(repositoryDir),
25-
metaDataFile(repositoryDir),
26-
InitMetaRepoData(admin.version))
25+
sharedDataFile(repositoryDir),
26+
InitLocalMetaRepoData(admin.version),
27+
InitSharedMetaRepoData(admin.version))
2728
}
2829

29-
func initDirectory(localDataFile string, metaDataFile string, rootObject *rootObjectData) error {
30-
metaDataDir := path.Dir(metaDataFile)
30+
func initDirectory(localDataFile string, sharedDataFile string, localRootObject *localRootObjectData, sharedRootObject *sharedRootObjectData) error {
31+
metaDataDir := path.Dir(sharedDataFile)
3132
if dirErr := os.MkdirAll(metaDataDir, fs.ModePerm); dirErr != nil {
3233
return fmt.Errorf("failed to make directory %s; %w", metaDataDir, dirErr)
33-
} else if writeMetaDataErr := rootObject.WriteTo(metaDataFile); writeMetaDataErr != nil {
34-
return fmt.Errorf("failed to write shared meta data file %s; %w", metaDataFile, writeMetaDataErr)
34+
} else if writeMetaDataErr := sharedRootObject.WriteTo(sharedDataFile); writeMetaDataErr != nil {
35+
return fmt.Errorf("failed to write shared meta data file %s; %w", sharedDataFile, writeMetaDataErr)
3536
} else {
36-
return rootObject.WriteTo(localDataFile)
37+
return localRootObject.WriteTo(localDataFile)
3738
}
3839
}
3940

src/go/svcfs/meta_repo_file.go

Lines changed: 0 additions & 45 deletions
This file was deleted.

src/go/svcfs/meta_repo_file_io.go

Lines changed: 31 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,24 +6,49 @@ import (
66
"os"
77
)
88

9-
func ReadMetaRepoFile(filename string) (*rootObjectData, error) {
9+
func ReadLocalMetaRepoFile(filename string) (*localRootObjectData, error) {
10+
root := &localRootObjectData{}
11+
if err := readMetaRepoFile(filename, root); err != nil {
12+
return nil, err
13+
} else {
14+
return root, nil
15+
}
16+
}
17+
18+
func ReadSharedMetaRepoFile(filename string) (*sharedRootObjectData, error) {
19+
root := &sharedRootObjectData{}
20+
if err := readMetaRepoFile(filename, root); err != nil {
21+
return nil, err
22+
} else {
23+
return root, nil
24+
}
25+
}
26+
27+
func readMetaRepoFile(filename string, root any) error {
1028
var decoder *json.Decoder
1129
if file, openErr := os.Open(filename); openErr != nil {
12-
return nil, fmt.Errorf("failed to open file %s; %w", filename, openErr)
30+
return fmt.Errorf("failed to open file %s; %w", filename, openErr)
1331
} else {
1432
defer file.Close()
1533
decoder = json.NewDecoder(file)
1634
}
1735

18-
var root rootObjectData
1936
if decodeErr := decoder.Decode(&root); decodeErr != nil {
20-
return nil, fmt.Errorf("failed to decode %s; %w", filename, decodeErr)
37+
return fmt.Errorf("failed to decode %s; %w", filename, decodeErr)
2138
} else {
22-
return &root, nil
39+
return nil
2340
}
2441
}
2542

26-
func (root *rootObjectData) WriteTo(filename string) error {
43+
func (root *localRootObjectData) WriteTo(filename string) error {
44+
return writeTo(root, filename)
45+
}
46+
47+
func (root *sharedRootObjectData) WriteTo(filename string) error {
48+
return writeTo(root, filename)
49+
}
50+
51+
func writeTo(root any, filename string) error {
2752
var encoder *json.Encoder
2853
if file, fileErr := os.Create(filename); fileErr != nil {
2954
return fmt.Errorf("failed to create file %s; %w", filename, fileErr)
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
package svcfs
2+
3+
/* Constructors */
4+
5+
// Construct a meta repo file with only minimal information; e.g. no Git repositories.
6+
func InitLocalMetaRepoData(version string) *localRootObjectData {
7+
return &localRootObjectData{
8+
MetaRepo: &localMetaRepoData{
9+
LocalRepositories: make([]localRepositoryData, 0),
10+
},
11+
Version: version,
12+
}
13+
}
14+
15+
/* Structure */
16+
17+
// Top-level object in the meta data file and its representation in JSON.
18+
type localRootObjectData struct {
19+
MetaRepo *localMetaRepoData `json:"meta_repo"`
20+
Version string `json:"version"`
21+
}
22+
23+
type localMetaRepoData struct {
24+
LocalRepositories []localRepositoryData `json:"local_repositories"`
25+
}
26+
27+
type localRepositoryData struct {
28+
Path string `json:"path"`
29+
}
30+
31+
/* Updates */
32+
33+
func (metaRepo *localMetaRepoData) AppendLocalRepository(localRepository localRepositoryData) {
34+
metaRepo.LocalRepositories = append(metaRepo.LocalRepositories, localRepository)
35+
}

src/go/svcfs/meta_repo_file_mapping.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import (
88

99
/* Local repositories */
1010

11-
func (metaRepo *metaRepoData) MapLocalRepositories() (corerepository.Repositories, error) {
11+
func (metaRepo *localMetaRepoData) MapLocalRepositories() (corerepository.Repositories, error) {
1212
repositories := make([]corerepository.Repository, len(metaRepo.LocalRepositories))
1313
for i, localRepositoryData := range metaRepo.LocalRepositories {
1414
repositories[i] = corerepository.LocalRepository(localRepositoryData.Path)
@@ -23,7 +23,7 @@ func (localRepo *localRepositoryData) ToCoreRepository() (corerepository.Reposit
2323

2424
/* Remote repositories */
2525

26-
func (metaRepo *metaRepoData) MapRemoteRepositories() (corerepository.Repositories, error) {
26+
func (metaRepo *sharedMetaRepoData) MapRemoteRepositories() (corerepository.Repositories, error) {
2727
repositories := make([]corerepository.Repository, len(metaRepo.RemoteRepositories))
2828
for i, remoteRepositoryData := range metaRepo.RemoteRepositories {
2929
if repository, mapErr := remoteRepositoryData.ToCoreRepository(); mapErr != nil {
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
package svcfs
2+
3+
/* Constructors */
4+
5+
// Construct a meta repo file with only minimal information; e.g. no Git repositories.
6+
func InitSharedMetaRepoData(version string) *sharedRootObjectData {
7+
return &sharedRootObjectData{
8+
MetaRepo: &sharedMetaRepoData{
9+
RemoteRepositories: make([]remoteRepositoryData, 0),
10+
},
11+
Version: version,
12+
}
13+
}
14+
15+
/* Structure */
16+
17+
// Top-level object in the meta data file and its representation in JSON.
18+
type sharedRootObjectData struct {
19+
MetaRepo *sharedMetaRepoData `json:"meta_repo"`
20+
Version string `json:"version"`
21+
}
22+
23+
type sharedMetaRepoData struct {
24+
RemoteRepositories []remoteRepositoryData `json:"remote_repositories"`
25+
}
26+
27+
type remoteRepositoryData struct {
28+
Url string `json:"url"`
29+
}
30+
31+
/* Updates */
32+
33+
func (metaRepo *sharedMetaRepoData) AppendRemoteRepository(remoteRepository remoteRepositoryData) {
34+
metaRepo.RemoteRepositories = append(metaRepo.RemoteRepositories, remoteRepository)
35+
}

src/go/svcfs/paths.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,6 @@ func localDataFile(metaRepoDir string) string {
1313
}
1414

1515
// Path to the specific file where Marmot stores shared data.
16-
func metaDataFile(metaRepoDir string) string {
16+
func sharedDataFile(metaRepoDir string) string {
1717
return filepath.Join(metaDataDir(metaRepoDir), "meta-repo.json")
1818
}

0 commit comments

Comments
 (0)