fix(files): add location to file info

This commit is contained in:
hexxa 2022-09-07 20:19:46 +08:00 committed by Hexxa
parent b226bc6f9f
commit df5c820c68
8 changed files with 127 additions and 63 deletions

View file

@ -73,7 +73,7 @@ type IFileDB interface {
DelFileInfo(ctx context.Context, userId uint64, itemPath string) error DelFileInfo(ctx context.Context, userId uint64, itemPath string) error
GetFileInfo(ctx context.Context, itemPath string) (*FileInfo, error) GetFileInfo(ctx context.Context, itemPath string) (*FileInfo, error)
SetSha1(ctx context.Context, itemPath, sign string) error SetSha1(ctx context.Context, itemPath, sign string) error
MoveFileInfos(ctx context.Context, userId uint64, oldPath, newPath string, isDir bool) error MoveFileInfo(ctx context.Context, userId uint64, oldPath, newPath string, isDir bool) error
ListFileInfos(ctx context.Context, itemPaths []string) (map[string]*FileInfo, error) ListFileInfos(ctx context.Context, itemPaths []string) (map[string]*FileInfo, error)
} }
type IUploadDB interface { type IUploadDB interface {
@ -86,11 +86,11 @@ type IUploadDB interface {
} }
type ISharingDB interface { type ISharingDB interface {
IsSharing(ctx context.Context, userId uint64, dirPath string) (bool, error) IsSharing(ctx context.Context, dirPath string) (bool, error)
GetSharingDir(ctx context.Context, hashID string) (string, error) GetSharingDir(ctx context.Context, hashID string) (string, error)
AddSharing(ctx context.Context, userId uint64, dirPath string) error AddSharing(ctx context.Context, userId uint64, dirPath string) error
DelSharing(ctx context.Context, userId uint64, dirPath string) error DelSharing(ctx context.Context, userId uint64, dirPath string) error
ListUserSharings(ctx context.Context, userId uint64) (map[string]string, error) ListSharingsByLocation(ctx context.Context, location string) (map[string]string, error)
} }
type IConfigDB interface { type IConfigDB interface {

View file

@ -128,19 +128,24 @@ func (st *SQLiteStore) addFileInfo(ctx context.Context, userId uint64, itemPath
return err return err
} }
location, err := getLocation(itemPath)
if err != nil {
return err
}
dirPath, itemName := path.Split(itemPath) dirPath, itemName := path.Split(itemPath)
_, err = st.db.ExecContext( _, err = st.db.ExecContext(
ctx, ctx,
`insert into t_file_info `insert into t_file_info (
(path, user, parent, name, is_dir, size, share_id, info) values (?, ?, ?, ?, ?, ?, ?, ?)`, path, user, location, parent, name,
itemPath, is_dir, size, share_id, info
userId, )
dirPath, values (
itemName, ?, ?, ?, ?, ?,
info.IsDir, ?, ?, ?, ?
info.Size, )`,
info.ShareID, itemPath, userId, location, dirPath, itemName,
infoStr, info.IsDir, info.Size, info.ShareID, infoStr,
) )
return err return err
} }
@ -248,7 +253,7 @@ func (st *SQLiteStore) DelFileInfo(ctx context.Context, userID uint64, itemPath
return err return err
} }
func (st *SQLiteStore) MoveFileInfos(ctx context.Context, userId uint64, oldPath, newPath string, isDir bool) error { func (st *SQLiteStore) MoveFileInfo(ctx context.Context, userId uint64, oldPath, newPath string, isDir bool) error {
st.Lock() st.Lock()
defer st.Unlock() defer st.Unlock()
@ -268,3 +273,12 @@ func (st *SQLiteStore) MoveFileInfos(ctx context.Context, userId uint64, oldPath
} }
return st.addFileInfo(ctx, userId, newPath, info) return st.addFileInfo(ctx, userId, newPath, info)
} }
func getLocation(itemPath string) (string, error) {
// location is taken from item path
itemPathParts := strings.Split(itemPath, "/")
if len(itemPathParts) == 0 {
return "", fmt.Errorf("invalid item path '%s'", itemPath)
}
return itemPathParts[0], nil
}

View file

@ -29,11 +29,10 @@ func (st *SQLiteStore) generateShareID(payload string) (string, error) {
return fmt.Sprintf("%x", h.Sum(nil))[:7], nil return fmt.Sprintf("%x", h.Sum(nil))[:7], nil
} }
func (st *SQLiteStore) IsSharing(ctx context.Context, userId uint64, dirPath string) (bool, error) { func (st *SQLiteStore) IsSharing(ctx context.Context, dirPath string) (bool, error) {
st.RLock() st.RLock()
defer st.RUnlock() defer st.RUnlock()
// TODO: userId is not used, becauser it is searcher's userId
var shareId string var shareId string
err := st.db.QueryRowContext( err := st.db.QueryRowContext(
ctx, ctx,
@ -88,6 +87,11 @@ func (st *SQLiteStore) AddSharing(ctx context.Context, userId uint64, dirPath st
return err return err
} }
location, err := getLocation(dirPath)
if err != nil {
return err
}
_, err = st.getFileInfo(ctx, dirPath) _, err = st.getFileInfo(ctx, dirPath)
if err != nil && !errors.Is(err, db.ErrFileInfoNotFound) { if err != nil && !errors.Is(err, db.ErrFileInfoNotFound) {
return err return err
@ -104,9 +108,16 @@ func (st *SQLiteStore) AddSharing(ctx context.Context, userId uint64, dirPath st
_, err = st.db.ExecContext( _, err = st.db.ExecContext(
ctx, ctx,
`insert into t_file_info `insert into t_file_info (
(path, user, parent, name, is_dir, size, share_id, info) values (?, ?, ?, ?, ?, ?, ?, ?)`, path, user, location, parent, name,
dirPath, userId, parentPath, name, true, 0, shareID, infoStr, is_dir, size, share_id, info
)
values (
?, ?, ?, ?, ?,
?, ?, ?, ?
)`,
dirPath, userId, location, parentPath, name,
true, 0, shareID, infoStr,
) )
return err return err
} }
@ -135,7 +146,7 @@ func (st *SQLiteStore) DelSharing(ctx context.Context, userId uint64, dirPath st
return err return err
} }
func (st *SQLiteStore) ListUserSharings(ctx context.Context, userId uint64) (map[string]string, error) { func (st *SQLiteStore) ListSharingsByLocation(ctx context.Context, location string) (map[string]string, error) {
st.RLock() st.RLock()
defer st.RUnlock() defer st.RUnlock()
@ -143,8 +154,8 @@ func (st *SQLiteStore) ListUserSharings(ctx context.Context, userId uint64) (map
ctx, ctx,
`select path, share_id `select path, share_id
from t_file_info from t_file_info
where user=? and share_id <> ''`, where location=? and share_id<>''`,
userId, location,
) )
if err != nil { if err != nil {
return nil, err return nil, err

View file

@ -11,8 +11,12 @@ import (
func (st *SQLiteStore) addUploadInfoOnly(ctx context.Context, userId uint64, tmpPath, filePath string, fileSize int64) error { func (st *SQLiteStore) addUploadInfoOnly(ctx context.Context, userId uint64, tmpPath, filePath string, fileSize int64) error {
_, err := st.db.ExecContext( _, err := st.db.ExecContext(
ctx, ctx,
`insert into t_file_uploading `insert into t_file_uploading (
(real_path, tmp_path, user, size, uploaded) values (?, ?, ?, ?, ?)`, real_path, tmp_path, user, size, uploaded
)
values (
?, ?, ?, ?, ?
)`,
filePath, tmpPath, userId, fileSize, 0, filePath, tmpPath, userId, fileSize, 0,
) )
return err return err

View file

@ -129,6 +129,7 @@ func (st *SQLiteStore) InitFileTables(ctx context.Context) error {
`create table if not exists t_file_info ( `create table if not exists t_file_info (
path varchar not null, path varchar not null,
user bigint not null, user bigint not null,
location varchar not null,
parent varchar not null, parent varchar not null,
name varchar not null, name varchar not null,
is_dir boolean not null, is_dir boolean not null,

View file

@ -18,6 +18,7 @@ func TestFileStore(t *testing.T) {
testSharingMethods := func(t *testing.T, store db.IDBQuickshare) { testSharingMethods := func(t *testing.T, store db.IDBQuickshare) {
dirPaths := []string{"admin/path1", "admin/path1/path2"} dirPaths := []string{"admin/path1", "admin/path1/path2"}
var err error var err error
location := "admin"
ctx := context.TODO() ctx := context.TODO()
adminId := uint64(0) adminId := uint64(0)
@ -43,7 +44,7 @@ func TestFileStore(t *testing.T) {
} }
// list sharings // list sharings
dirToID, err := store.ListUserSharings(ctx, adminId) dirToID, err := store.ListSharingsByLocation(ctx, location)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} else if len(dirToID) != len(dirPaths) { } else if len(dirToID) != len(dirPaths) {
@ -54,7 +55,7 @@ func TestFileStore(t *testing.T) {
if _, ok := dirToID[sharingDir]; !ok { if _, ok := dirToID[sharingDir]; !ok {
t.Fatalf("sharing(%s) not found", sharingDir) t.Fatalf("sharing(%s) not found", sharingDir)
} }
mustTrue, err := store.IsSharing(ctx, adminId, sharingDir) mustTrue, err := store.IsSharing(ctx, sharingDir)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} else if !mustTrue { } else if !mustTrue {
@ -85,7 +86,7 @@ func TestFileStore(t *testing.T) {
} }
// list sharings // list sharings
dirToIDAfterDel, err := store.ListUserSharings(ctx, adminId) dirToIDAfterDel, err := store.ListSharingsByLocation(ctx, location)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} else if len(dirToIDAfterDel) != 0 { } else if len(dirToIDAfterDel) != 0 {
@ -96,7 +97,7 @@ func TestFileStore(t *testing.T) {
if _, ok := dirToIDAfterDel[dirPath]; ok { if _, ok := dirToIDAfterDel[dirPath]; ok {
t.Fatalf("sharing(%s) should not exist", dirPath) t.Fatalf("sharing(%s) should not exist", dirPath)
} }
shared, err := store.IsSharing(ctx, adminId, dirPath) shared, err := store.IsSharing(ctx, dirPath)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} else if shared { } else if shared {
@ -217,7 +218,7 @@ func TestFileStore(t *testing.T) {
newPaths := []string{} newPaths := []string{}
for itemPath, info := range pathInfos { for itemPath, info := range pathInfos {
newItemPath := strings.ReplaceAll(itemPath, "origin", "new") newItemPath := strings.ReplaceAll(itemPath, "origin", "new")
err = store.MoveFileInfos(ctx, adminId, itemPath, newItemPath, info.IsDir) err = store.MoveFileInfo(ctx, adminId, itemPath, newItemPath, info.IsDir)
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }

View file

@ -101,7 +101,7 @@ func (h *FileHandlers) canAccess(ctx context.Context, userId uint64, userName, r
return false return false
} }
isSharing, err := h.deps.FileInfos().IsSharing(ctx, userId, sharedPath) isSharing, err := h.deps.FileInfos().IsSharing(ctx, sharedPath)
if err != nil { if err != nil {
return false // TODO: return error return false // TODO: return error
} }
@ -157,6 +157,7 @@ func (h *FileHandlers) Create(c *gin.Context) {
} }
return return
} }
err = h.deps.FileInfos().MoveUploadingInfos(c, userID, tmpFilePath, fsFilePath) err = h.deps.FileInfos().MoveUploadingInfos(c, userID, tmpFilePath, fsFilePath)
if err != nil { if err != nil {
c.JSON(q.ErrResp(c, 500, err)) c.JSON(q.ErrResp(c, 500, err))
@ -422,7 +423,7 @@ func (h *FileHandlers) Move(c *gin.Context) {
return return
} }
err = h.deps.FileInfos().MoveFileInfos(c, userId, oldPath, newPath, itemInfo.IsDir()) err = h.deps.FileInfos().MoveFileInfo(c, userId, oldPath, newPath, itemInfo.IsDir())
if err != nil { if err != nil {
c.JSON(q.ErrResp(c, 500, err)) c.JSON(q.ErrResp(c, 500, err))
return return
@ -1063,13 +1064,7 @@ func (h *FileHandlers) IsSharing(c *gin.Context) {
return return
} }
userId, err := q.GetUserId(c) exist, err := h.deps.FileInfos().IsSharing(c, dirPath)
if err != nil {
c.JSON(q.ErrResp(c, 500, err))
return
}
exist, err := h.deps.FileInfos().IsSharing(c, userId, dirPath)
if err != nil { if err != nil {
if errors.Is(err, db.ErrFileInfoNotFound) { if errors.Is(err, db.ErrFileInfoNotFound) {
c.JSON(q.Resp(404)) c.JSON(q.Resp(404))
@ -1090,13 +1085,8 @@ type SharingResp struct {
// Deprecated: use ListSharingIDs instead // Deprecated: use ListSharingIDs instead
func (h *FileHandlers) ListSharings(c *gin.Context) { func (h *FileHandlers) ListSharings(c *gin.Context) {
// TODO: move canAccess to authedFS // TODO: move canAccess to authedFS
userId, err := q.GetUserId(c) userName := c.MustGet(q.UserParam).(string)
if err != nil { sharingDirs, err := h.deps.FileInfos().ListSharingsByLocation(c, userName)
c.JSON(q.ErrResp(c, 500, err))
return
}
sharingDirs, err := h.deps.FileInfos().ListUserSharings(c, userId)
if err != nil { if err != nil {
c.JSON(q.ErrResp(c, 500, err)) c.JSON(q.ErrResp(c, 500, err))
return return
@ -1114,13 +1104,8 @@ type SharingIDsResp struct {
} }
func (h *FileHandlers) ListSharingIDs(c *gin.Context) { func (h *FileHandlers) ListSharingIDs(c *gin.Context) {
userId, err := q.GetUserId(c) userName := c.MustGet(q.UserParam).(string)
if err != nil { dirToID, err := h.deps.FileInfos().ListSharingsByLocation(c, userName)
c.JSON(q.ErrResp(c, 500, err))
return
}
dirToID, err := h.deps.FileInfos().ListUserSharings(c, userId)
if err != nil { if err != nil {
c.JSON(q.ErrResp(c, 500, err)) c.JSON(q.ErrResp(c, 500, err))
return return

View file

@ -5,6 +5,7 @@ import (
"fmt" "fmt"
"math/rand" "math/rand"
"os" "os"
"path"
"path/filepath" "path/filepath"
"sync" "sync"
"testing" "testing"
@ -73,6 +74,16 @@ func TestFileHandlers(t *testing.T) {
token := client.GetCookie(resp.Cookies(), q.TokenCookie) token := client.GetCookie(resp.Cookies(), q.TokenCookie)
adminFilesClient := client.NewFilesClient(addr, token) adminFilesClient := client.NewFilesClient(addr, token)
userUsersCl := client.NewUsersClient(addr)
resp, _, errs = userUsersCl.Login("demo", "Quicksh@re")
if len(errs) > 0 {
t.Fatal(errs)
} else if resp.StatusCode != 200 {
t.Fatal(resp.StatusCode)
}
userUsersToken := client.GetCookie(resp.Cookies(), q.TokenCookie)
userFilesCl := client.NewFilesClient(addr, userUsersToken)
var err error var err error
// TODO: remove all files under home folder before testing // TODO: remove all files under home folder before testing
// or the count of files is incorrect // or the count of files is incorrect
@ -406,16 +417,6 @@ func TestFileHandlers(t *testing.T) {
} }
} }
userUsersCl := client.NewUsersClient(addr)
resp, _, errs := userUsersCl.Login("demo", "Quicksh@re")
if len(errs) > 0 {
t.Fatal(errs)
} else if resp.StatusCode != 200 {
t.Fatal(resp.StatusCode)
}
userUsersToken := client.GetCookie(resp.Cookies(), q.TokenCookie)
userFilesCl := client.NewFilesClient(addr, userUsersToken)
for i := 0; i < 2; i++ { for i := 0; i < 2; i++ {
// add sharings // add sharings
sharedPaths := map[string]bool{} sharedPaths := map[string]bool{}
@ -471,7 +472,6 @@ func TestFileHandlers(t *testing.T) {
} }
} }
fmt.Println("\n\n\n", shRes.IDs)
// check isSharing // check isSharing
for dirPath := range sharedPaths { for dirPath := range sharedPaths {
res, _, errs := userFilesCl.IsSharing(dirPath) res, _, errs := userFilesCl.IsSharing(dirPath)
@ -854,6 +854,54 @@ func TestFileHandlers(t *testing.T) {
} }
}) })
t.Run("test sharing for users: AddSharing(admin)-IsSharing(demo)-ListSharing(demo)", func(t *testing.T) {
files := map[string]string{
"demo/files/share_for/f1.md": "111",
"demo/files/share_for/f2.md": "22222",
}
for filePath, content := range files {
// uploaded by user
assertUploadOK(t, filePath, content, addr, userUsersToken)
// shared by admin
fileDir := path.Dir(filePath)
res, _, errs := adminFilesClient.AddSharing(fileDir)
if len(errs) > 0 {
t.Fatal(errs)
} else if res.StatusCode != 200 {
t.Fatal(res.StatusCode)
}
res, _, errs = userFilesCl.IsSharing(fileDir)
if len(errs) > 0 {
t.Fatal(errs)
} else if res.StatusCode != 200 { // should still be in sharing
t.Fatal(res.StatusCode)
}
err = fs.Sync()
if err != nil {
t.Fatal(err)
}
_, lResp, errs := userFilesCl.ListSharings()
if len(errs) > 0 {
t.Fatal(errs)
}
found := false
for _, gotPath := range lResp.SharingDirs {
if fileDir == gotPath {
found = true
break
}
}
if !found {
t.Fatalf("%s not found", filePath)
}
}
})
compareSearchResults := func(expectedPaths map[string]bool, searchItemsResp []string) bool { compareSearchResults := func(expectedPaths map[string]bool, searchItemsResp []string) bool {
if len(expectedPaths) != len(searchItemsResp) { if len(expectedPaths) != len(searchItemsResp) {
return false return false