some cleaning
License: MIT Signed-off-by: Henrique Dias <hacdias@gmail.com>
This commit is contained in:
parent
94cec714ce
commit
f3c1c4b5d2
13
auth/json.go
13
auth/json.go
@ -18,14 +18,14 @@ type jsonCred struct {
|
||||
ReCaptcha string `json:"recaptcha"`
|
||||
}
|
||||
|
||||
// JSONAuth is a json implementaion of an auther.
|
||||
// JSONAuth is a json implementaion of an Auther.
|
||||
type JSONAuth struct {
|
||||
ReCaptcha *ReCaptcha
|
||||
Store *types.UsersVerify `json:"-"`
|
||||
store *types.Storage
|
||||
}
|
||||
|
||||
// Auth authenticates the user via a json in content body.
|
||||
func (a JSONAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
func (a *JSONAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
var cred jsonCred
|
||||
|
||||
if r.Body == nil {
|
||||
@ -50,7 +50,7 @@ func (a JSONAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
}
|
||||
}
|
||||
|
||||
u, err := a.Store.GetByUsername(cred.Username)
|
||||
u, err := a.store.GetUser(cred.Username)
|
||||
if err != nil || !types.CheckPwd(cred.Password, u.Password) {
|
||||
return nil, types.ErrNoPermission
|
||||
}
|
||||
@ -58,6 +58,11 @@ func (a JSONAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
return u, nil
|
||||
}
|
||||
|
||||
// SetStorage attaches the storage information to the auther.
|
||||
func (a *JSONAuth) SetStorage(s *types.Storage) {
|
||||
a.store = s
|
||||
}
|
||||
|
||||
const reCaptchaAPI = "/recaptcha/api/siteverify"
|
||||
|
||||
// ReCaptcha identifies a recaptcha conenction.
|
||||
|
||||
11
auth/none.go
11
auth/none.go
@ -11,10 +11,15 @@ const MethodNoAuth types.AuthMethod = "noauth"
|
||||
|
||||
// NoAuth is no auth implementation of auther.
|
||||
type NoAuth struct {
|
||||
Store *types.UsersVerify `json:"-"`
|
||||
store *types.Storage
|
||||
}
|
||||
|
||||
// Auth uses authenticates user 1.
|
||||
func (a NoAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
return a.Store.Get(1)
|
||||
func (a *NoAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
return a.store.GetUser(1)
|
||||
}
|
||||
|
||||
// SetStorage attaches the storage information to the auther.
|
||||
func (a *NoAuth) SetStorage(s *types.Storage) {
|
||||
a.store = s
|
||||
}
|
||||
|
||||
@ -12,16 +12,21 @@ const MethodProxyAuth types.AuthMethod = "proxy"
|
||||
// ProxyAuth is a proxy implementation of an auther.
|
||||
type ProxyAuth struct {
|
||||
Header string
|
||||
Store *types.UsersVerify `json:"-"`
|
||||
store *types.Storage
|
||||
}
|
||||
|
||||
// Auth authenticates the user via an HTTP header.
|
||||
func (a ProxyAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
func (a *ProxyAuth) Auth(r *http.Request) (*types.User, error) {
|
||||
username := r.Header.Get(a.Header)
|
||||
user, err := a.Store.GetByUsername(username)
|
||||
user, err := a.store.GetUser(username)
|
||||
if err == types.ErrNotExist {
|
||||
return nil, types.ErrNoPermission
|
||||
}
|
||||
|
||||
return user, err
|
||||
}
|
||||
|
||||
// SetStorage attaches the storage information to the auther.
|
||||
func (a *ProxyAuth) SetStorage(s *types.Storage) {
|
||||
a.store = s
|
||||
}
|
||||
|
||||
10
bolt/bolt.go
10
bolt/bolt.go
@ -2,11 +2,7 @@ package bolt
|
||||
|
||||
import "github.com/asdine/storm"
|
||||
|
||||
func Open(path string) (*storm.DB, error) {
|
||||
db, err := storm.Open(path)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return db, nil
|
||||
// Backend implements types.StorageBackend.
|
||||
type Backend struct {
|
||||
DB *storm.DB
|
||||
}
|
||||
|
||||
@ -6,15 +6,8 @@ import (
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
)
|
||||
|
||||
// ConfigStore is a configuration store.
|
||||
type ConfigStore struct {
|
||||
DB *storm.DB
|
||||
Users *types.UsersVerify
|
||||
}
|
||||
|
||||
// Get gets a configuration from the database to an interface.
|
||||
func (c ConfigStore) Get(name string, to interface{}) error {
|
||||
err := c.DB.Get("config", name, to)
|
||||
func (b Backend) get(name string, to interface{}) error {
|
||||
err := b.DB.Get("config", name, to)
|
||||
if err == storm.ErrNotFound {
|
||||
return types.ErrNotExist
|
||||
}
|
||||
@ -22,53 +15,36 @@ func (c ConfigStore) Get(name string, to interface{}) error {
|
||||
return err
|
||||
}
|
||||
|
||||
// Save saves a configuration from an interface to the database.
|
||||
func (c ConfigStore) Save(name string, from interface{}) error {
|
||||
return c.DB.Set("config", name, from)
|
||||
func (b Backend) save(name string, from interface{}) error {
|
||||
return b.DB.Set("config", name, from)
|
||||
}
|
||||
|
||||
// GetSettings is an helper method to get a settings object.
|
||||
func (c ConfigStore) GetSettings() (*types.Settings, error) {
|
||||
func (b Backend) GetSettings() (*types.Settings, error) {
|
||||
settings := &types.Settings{}
|
||||
return settings, c.Get("settings", settings)
|
||||
return settings, b.get("settings", settings)
|
||||
}
|
||||
|
||||
// SaveSettings is an helper method to set the settings object
|
||||
func (c ConfigStore) SaveSettings(s *types.Settings) error {
|
||||
return c.Save("settings", s)
|
||||
func (b Backend) SaveSettings(s *types.Settings) error {
|
||||
return b.save("settings", s)
|
||||
}
|
||||
|
||||
// GetAuther is an helper method to get an auther object.
|
||||
func (c ConfigStore) GetAuther(t types.AuthMethod) (types.Auther, error) {
|
||||
if t == auth.MethodJSONAuth {
|
||||
auther := auth.JSONAuth{}
|
||||
if err := c.Get("auther", &auther); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
auther.Store = &types.UsersVerify{Store: &UsersStore{DB: c.DB}}
|
||||
return &auther, nil
|
||||
func (b Backend) GetAuther(t types.AuthMethod) (types.Auther, error) {
|
||||
var auther types.Auther
|
||||
|
||||
switch t {
|
||||
case auth.MethodJSONAuth:
|
||||
auther = &auth.JSONAuth{}
|
||||
case auth.MethodProxyAuth:
|
||||
auther = &auth.ProxyAuth{}
|
||||
case auth.MethodNoAuth:
|
||||
auther = &auth.NoAuth{}
|
||||
default:
|
||||
return nil, types.ErrInvalidAuthMethod
|
||||
}
|
||||
|
||||
if t == auth.MethodProxyAuth {
|
||||
auther := auth.ProxyAuth{}
|
||||
if err := c.Get("auther", &auther); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return &auther, nil
|
||||
}
|
||||
|
||||
if t == auth.MethodNoAuth {
|
||||
auther := auth.NoAuth{Store: c.Users}
|
||||
if err := c.Get("auther", &auther); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return &auther, nil
|
||||
}
|
||||
|
||||
return nil, types.ErrInvalidAuthMethod
|
||||
return auther, b.get("auther", auther)
|
||||
}
|
||||
|
||||
// SaveAuther is an helper method to set the auther object
|
||||
func (c ConfigStore) SaveAuther(a types.Auther) error {
|
||||
return c.Save("auther", a)
|
||||
func (b Backend) SaveAuther(a types.Auther) error {
|
||||
return b.save("auther", a)
|
||||
}
|
||||
|
||||
@ -6,13 +6,7 @@ import (
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
)
|
||||
|
||||
// ShareStore is a shareable links store.
|
||||
type ShareStore struct {
|
||||
DB *storm.DB
|
||||
}
|
||||
|
||||
// Get gets a Share Link from an hash.
|
||||
func (s ShareStore) Get(hash string) (*types.ShareLink, error) {
|
||||
func (s Backend) GetLinkByHash(hash string) (*types.ShareLink, error) {
|
||||
var v types.ShareLink
|
||||
err := s.DB.One("Hash", hash, &v)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -22,8 +16,7 @@ func (s ShareStore) Get(hash string) (*types.ShareLink, error) {
|
||||
return &v, err
|
||||
}
|
||||
|
||||
// GetPermanent gets the permanent link from a path.
|
||||
func (s ShareStore) GetPermanent(path string) (*types.ShareLink, error) {
|
||||
func (s Backend) GetLinkPermanent(path string) (*types.ShareLink, error) {
|
||||
var v types.ShareLink
|
||||
err := s.DB.Select(q.Eq("Path", path), q.Eq("Expires", false)).First(&v)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -33,8 +26,7 @@ func (s ShareStore) GetPermanent(path string) (*types.ShareLink, error) {
|
||||
return &v, err
|
||||
}
|
||||
|
||||
// GetByPath gets all the links for a specific path.
|
||||
func (s ShareStore) GetByPath(hash string) ([]*types.ShareLink, error) {
|
||||
func (s Backend) GetLinksByPath(hash string) ([]*types.ShareLink, error) {
|
||||
var v []*types.ShareLink
|
||||
err := s.DB.Find("Path", hash, &v)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -44,23 +36,10 @@ func (s ShareStore) GetByPath(hash string) ([]*types.ShareLink, error) {
|
||||
return v, err
|
||||
}
|
||||
|
||||
// Gets retrieves all the shareable links.
|
||||
func (s ShareStore) Gets() ([]*types.ShareLink, error) {
|
||||
var v []*types.ShareLink
|
||||
err := s.DB.All(&v)
|
||||
if err == storm.ErrNotFound {
|
||||
return v, types.ErrNotExist
|
||||
}
|
||||
|
||||
return v, err
|
||||
}
|
||||
|
||||
// Save stores a Share Link on the database.
|
||||
func (s ShareStore) Save(l *types.ShareLink) error {
|
||||
func (s Backend) SaveLink(l *types.ShareLink) error {
|
||||
return s.DB.Save(l)
|
||||
}
|
||||
|
||||
// Delete deletes a Share Link from the database.
|
||||
func (s ShareStore) Delete(hash string) error {
|
||||
func (s Backend) DeleteLink(hash string) error {
|
||||
return s.DB.DeleteStruct(&types.ShareLink{Hash: hash})
|
||||
}
|
||||
|
||||
@ -7,11 +7,7 @@ import (
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
)
|
||||
|
||||
type UsersStore struct {
|
||||
DB *storm.DB
|
||||
}
|
||||
|
||||
func (st UsersStore) Get(id uint) (*types.User, error) {
|
||||
func (st Backend) GetUserByID(id uint) (*types.User, error) {
|
||||
user := &types.User{}
|
||||
err := st.DB.One("ID", id, user)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -25,7 +21,7 @@ func (st UsersStore) Get(id uint) (*types.User, error) {
|
||||
return user, nil
|
||||
}
|
||||
|
||||
func (st UsersStore) GetByUsername(username string) (*types.User, error) {
|
||||
func (st Backend) GetUserByUsername(username string) (*types.User, error) {
|
||||
user := &types.User{}
|
||||
err := st.DB.One("Username", username, user)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -39,7 +35,7 @@ func (st UsersStore) GetByUsername(username string) (*types.User, error) {
|
||||
return user, nil
|
||||
}
|
||||
|
||||
func (st UsersStore) Gets() ([]*types.User, error) {
|
||||
func (st Backend) GetUsers() ([]*types.User, error) {
|
||||
users := []*types.User{}
|
||||
err := st.DB.All(&users)
|
||||
if err == storm.ErrNotFound {
|
||||
@ -53,9 +49,9 @@ func (st UsersStore) Gets() ([]*types.User, error) {
|
||||
return users, err
|
||||
}
|
||||
|
||||
func (st UsersStore) Update(user *types.User, fields ...string) error {
|
||||
func (st Backend) UpdateUser(user *types.User, fields ...string) error {
|
||||
if len(fields) == 0 {
|
||||
return st.Save(user)
|
||||
return st.SaveUser(user)
|
||||
}
|
||||
|
||||
for _, field := range fields {
|
||||
@ -68,7 +64,7 @@ func (st UsersStore) Update(user *types.User, fields ...string) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (st UsersStore) Save(user *types.User) error {
|
||||
func (st Backend) SaveUser(user *types.User) error {
|
||||
err := st.DB.Save(user)
|
||||
if err == storm.ErrAlreadyExists {
|
||||
return types.ErrExist
|
||||
@ -76,12 +72,12 @@ func (st UsersStore) Save(user *types.User) error {
|
||||
return err
|
||||
}
|
||||
|
||||
func (st UsersStore) Delete(id uint) error {
|
||||
func (st Backend) DeleteUserByID(id uint) error {
|
||||
return st.DB.DeleteStruct(&types.User{ID: id})
|
||||
}
|
||||
|
||||
func (st UsersStore) DeleteByUsername(username string) error {
|
||||
user, err := st.GetByUsername(username)
|
||||
func (st Backend) DeleteUserByUsername(username string) error {
|
||||
user, err := st.GetUserByUsername(username)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
@ -21,14 +21,14 @@ var cmdsAddCmd = &cobra.Command{
|
||||
db := getDB()
|
||||
defer db.Close()
|
||||
st := getStore(db)
|
||||
s, err := st.Config.GetSettings()
|
||||
s, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
|
||||
evt := mustGetString(cmd, "event")
|
||||
command := mustGetString(cmd, "command")
|
||||
|
||||
s.Commands[evt] = append(s.Commands[evt], command)
|
||||
err = st.Config.SaveSettings(s)
|
||||
err = st.SaveSettings(s)
|
||||
checkErr(err)
|
||||
printEvents(s.Commands)
|
||||
},
|
||||
|
||||
@ -18,7 +18,7 @@ var cmdsLsCmd = &cobra.Command{
|
||||
db := getDB()
|
||||
defer db.Close()
|
||||
st := getStore(db)
|
||||
s, err := st.Config.GetSettings()
|
||||
s, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
evt := mustGetString(cmd, "event")
|
||||
|
||||
|
||||
@ -21,7 +21,7 @@ var cmdsRmCmd = &cobra.Command{
|
||||
db := getDB()
|
||||
defer db.Close()
|
||||
st := getStore(db)
|
||||
s, err := st.Config.GetSettings()
|
||||
s, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
|
||||
evt := mustGetString(cmd, "event")
|
||||
@ -29,7 +29,7 @@ var cmdsRmCmd = &cobra.Command{
|
||||
checkErr(err)
|
||||
|
||||
s.Commands[evt] = append(s.Commands[evt][:i], s.Commands[evt][i+1:]...)
|
||||
err = st.Config.SaveSettings(s)
|
||||
err = st.SaveSettings(s)
|
||||
checkErr(err)
|
||||
printEvents(s.Commands)
|
||||
},
|
||||
|
||||
@ -55,15 +55,15 @@ func getAuthentication(cmd *cobra.Command) (types.AuthMethod, types.Auther) {
|
||||
if header == "" {
|
||||
panic(errors.New("you must set the flag 'auth.header' for method 'proxy'"))
|
||||
}
|
||||
auther = auth.ProxyAuth{Header: header}
|
||||
auther = &auth.ProxyAuth{Header: header}
|
||||
}
|
||||
|
||||
if method == auth.MethodNoAuth {
|
||||
auther = auth.NoAuth{}
|
||||
auther = &auth.NoAuth{}
|
||||
}
|
||||
|
||||
if method == auth.MethodJSONAuth {
|
||||
jsonAuth := auth.JSONAuth{}
|
||||
jsonAuth := &auth.JSONAuth{}
|
||||
|
||||
host := mustGetString(cmd, "recaptcha.host")
|
||||
key := mustGetString(cmd, "recaptcha.key")
|
||||
|
||||
@ -17,9 +17,9 @@ var configCatCmd = &cobra.Command{
|
||||
db := getDB()
|
||||
defer db.Close()
|
||||
st := getStore(db)
|
||||
s, err := st.Config.GetSettings()
|
||||
s, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
auther, err := st.Config.GetAuther(s.AuthMethod)
|
||||
auther, err := st.GetAuther(s.AuthMethod)
|
||||
checkErr(err)
|
||||
printSettings(s, auther)
|
||||
},
|
||||
|
||||
@ -7,7 +7,6 @@ import (
|
||||
"strings"
|
||||
|
||||
"github.com/asdine/storm"
|
||||
"github.com/filebrowser/filebrowser/bolt"
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
"github.com/spf13/cobra"
|
||||
)
|
||||
@ -51,7 +50,7 @@ override the options.`,
|
||||
},
|
||||
}
|
||||
|
||||
db, err := bolt.Open(databasePath)
|
||||
db, err := storm.Open(databasePath)
|
||||
checkErr(err)
|
||||
defer db.Close()
|
||||
|
||||
@ -68,8 +67,8 @@ need to call the main command to boot up the server.
|
||||
|
||||
func saveConfig(db *storm.DB, s *types.Settings, a types.Auther) {
|
||||
st := getStore(db)
|
||||
err := st.Config.SaveSettings(s)
|
||||
err := st.SaveSettings(s)
|
||||
checkErr(err)
|
||||
err = st.Config.SaveAuther(a)
|
||||
err = st.SaveAuther(a)
|
||||
checkErr(err)
|
||||
}
|
||||
|
||||
@ -24,7 +24,7 @@ you want to change.`,
|
||||
defer db.Close()
|
||||
|
||||
st := getStore(db)
|
||||
s, err := st.Config.GetSettings()
|
||||
s, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
|
||||
auth := false
|
||||
@ -52,14 +52,14 @@ you want to change.`,
|
||||
var auther types.Auther
|
||||
if auth {
|
||||
s.AuthMethod, auther = getAuthentication(cmd)
|
||||
err = st.Config.SaveAuther(auther)
|
||||
err = st.SaveAuther(auther)
|
||||
checkErr(err)
|
||||
} else {
|
||||
auther, err = st.Config.GetAuther(s.AuthMethod)
|
||||
auther, err = st.GetAuther(s.AuthMethod)
|
||||
checkErr(err)
|
||||
}
|
||||
|
||||
err = st.Config.SaveSettings(s)
|
||||
err = st.SaveSettings(s)
|
||||
checkErr(err)
|
||||
printSettings(s, auther)
|
||||
},
|
||||
|
||||
10
cmd/root.go
10
cmd/root.go
@ -10,8 +10,8 @@ import (
|
||||
"os"
|
||||
"strconv"
|
||||
|
||||
"github.com/asdine/storm"
|
||||
"github.com/filebrowser/filebrowser/auth"
|
||||
"github.com/filebrowser/filebrowser/bolt"
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
|
||||
fhttp "github.com/filebrowser/filebrowser/http"
|
||||
@ -61,9 +61,9 @@ listening on loalhost on a random port. Use the flags to change it.`,
|
||||
Store: getStore(db),
|
||||
}
|
||||
|
||||
env.Settings, err = env.Store.Config.GetSettings()
|
||||
env.Settings, err = env.Store.GetSettings()
|
||||
checkErr(err)
|
||||
env.Auther, err = env.Store.Config.GetAuther(env.Settings.AuthMethod)
|
||||
env.Auther, err = env.Store.GetAuther(env.Settings.AuthMethod)
|
||||
checkErr(err)
|
||||
|
||||
startServer(cmd, env)
|
||||
@ -127,14 +127,14 @@ func quickSetup(cmd *cobra.Command) {
|
||||
user.ApplyDefaults(settings.Defaults)
|
||||
user.Perm.Admin = true
|
||||
|
||||
db, err := bolt.Open(databasePath)
|
||||
db, err := storm.Open(databasePath)
|
||||
checkErr(err)
|
||||
defer db.Close()
|
||||
|
||||
saveConfig(db, settings, &auth.JSONAuth{})
|
||||
|
||||
st := getStore(db)
|
||||
err = st.Users.Save(user)
|
||||
err = st.SaveUser(user)
|
||||
checkErr(err)
|
||||
}
|
||||
|
||||
|
||||
@ -40,11 +40,11 @@ var findUsers = func(cmd *cobra.Command, args []string) {
|
||||
var user *types.User
|
||||
|
||||
if username != "" {
|
||||
user, err = st.Users.GetByUsername(username)
|
||||
user, err = st.GetUser(username)
|
||||
} else if id != 0 {
|
||||
user, err = st.Users.Get(id)
|
||||
user, err = st.GetUser(id)
|
||||
} else {
|
||||
users, err = st.Users.Gets()
|
||||
users, err = st.GetUsers()
|
||||
}
|
||||
|
||||
checkErr(err)
|
||||
|
||||
@ -25,7 +25,7 @@ var usersNewCmd = &cobra.Command{
|
||||
defer db.Close()
|
||||
st := getStore(db)
|
||||
|
||||
settings, err := st.Config.GetSettings()
|
||||
settings, err := st.GetSettings()
|
||||
checkErr(err)
|
||||
getUserDefaults(cmd, &settings.Defaults, false)
|
||||
|
||||
@ -41,7 +41,7 @@ var usersNewCmd = &cobra.Command{
|
||||
|
||||
user.ApplyDefaults(settings.Defaults)
|
||||
|
||||
err = st.Users.Save(user)
|
||||
err = st.SaveUser(user)
|
||||
checkErr(err)
|
||||
printUsers([]*types.User{user})
|
||||
},
|
||||
|
||||
@ -28,9 +28,9 @@ var usersRmCmd = &cobra.Command{
|
||||
var err error
|
||||
|
||||
if username != "" {
|
||||
err = st.Users.DeleteByUsername(username)
|
||||
err = st.DeleteUser(username)
|
||||
} else {
|
||||
err = st.Users.Delete(id)
|
||||
err = st.DeleteUser(id)
|
||||
}
|
||||
|
||||
checkErr(err)
|
||||
|
||||
@ -33,9 +33,9 @@ options you want to change.`,
|
||||
var err error
|
||||
|
||||
if id != 0 {
|
||||
user, err = st.Users.Get(id)
|
||||
user, err = st.GetUser(id)
|
||||
} else {
|
||||
user, err = st.Users.GetByUsername(username)
|
||||
user, err = st.GetUser(username)
|
||||
}
|
||||
|
||||
checkErr(err)
|
||||
@ -66,7 +66,7 @@ options you want to change.`,
|
||||
checkErr(err)
|
||||
}
|
||||
|
||||
err = st.Users.Update(user)
|
||||
err = st.UpdateUser(user)
|
||||
checkErr(err)
|
||||
printUsers([]*types.User{user})
|
||||
},
|
||||
|
||||
23
cmd/utils.go
23
cmd/utils.go
@ -34,30 +34,13 @@ func getDB() *storm.DB {
|
||||
panic(errors.New(databasePath + " does not exist. Please run 'filebrowser init' first."))
|
||||
}
|
||||
|
||||
db, err := bolt.Open(databasePath)
|
||||
db, err := storm.Open(databasePath)
|
||||
checkErr(err)
|
||||
return db
|
||||
}
|
||||
|
||||
func getStore(db *storm.DB) *types.Store {
|
||||
usersStore := &types.UsersVerify{
|
||||
Store: bolt.UsersStore{
|
||||
DB: db,
|
||||
},
|
||||
}
|
||||
|
||||
configSore := &types.ConfigVerify{
|
||||
Store: bolt.ConfigStore{
|
||||
DB: db,
|
||||
Users: usersStore,
|
||||
},
|
||||
}
|
||||
|
||||
return &types.Store{
|
||||
Users: usersStore,
|
||||
Config: configSore,
|
||||
Share: bolt.ShareStore{DB: db},
|
||||
}
|
||||
func getStore(db *storm.DB) *types.Storage {
|
||||
return types.NewStorage(&bolt.Backend{DB: db})
|
||||
}
|
||||
|
||||
func generateRandomBytes(n int) []byte {
|
||||
|
||||
@ -67,7 +67,7 @@ func (e *Env) signupHandler(w http.ResponseWriter, r *http.Request) {
|
||||
}
|
||||
|
||||
user.Password = pwd
|
||||
err = e.Store.Users.Save(user)
|
||||
err = e.Store.SaveUser(user)
|
||||
if err == types.ErrExist {
|
||||
httpErr(w, r, http.StatusConflict, nil)
|
||||
return
|
||||
@ -133,7 +133,7 @@ func (e *Env) auth(next http.HandlerFunc) http.HandlerFunc {
|
||||
}
|
||||
|
||||
if !tk.VerifyExpiresAt(time.Now().Add(time.Hour).Unix(), true) {
|
||||
// TODO: chek if user info was modified
|
||||
// TODO: chek if user info was modified use timestap
|
||||
w.Header().Add("X-Renew-Token", "true")
|
||||
}
|
||||
|
||||
|
||||
@ -8,13 +8,14 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/gorilla/websocket"
|
||||
"github.com/filebrowser/filebrowser/types"
|
||||
"github.com/gorilla/mux"
|
||||
"github.com/gorilla/websocket"
|
||||
)
|
||||
|
||||
type key int
|
||||
|
||||
|
||||
const (
|
||||
keyUserID key = iota
|
||||
)
|
||||
@ -28,7 +29,7 @@ type modifyRequest struct {
|
||||
type Env struct {
|
||||
Auther types.Auther
|
||||
Settings *types.Settings
|
||||
Store *types.Store
|
||||
Store *types.Storage
|
||||
mux sync.RWMutex // settings mutex for Settings changes.
|
||||
}
|
||||
|
||||
@ -104,7 +105,7 @@ func renderJSON(w http.ResponseWriter, r *http.Request, data interface{}) {
|
||||
|
||||
func (e *Env) getUser(w http.ResponseWriter, r *http.Request) (*types.User, bool) {
|
||||
id := r.Context().Value(keyUserID).(uint)
|
||||
user, err := e.Store.Users.Get(id)
|
||||
user, err := e.Store.GetUser(id)
|
||||
if err == types.ErrNotExist {
|
||||
httpErr(w, r, http.StatusForbidden, nil)
|
||||
return nil, false
|
||||
|
||||
@ -28,9 +28,6 @@ func parseQueryFiles(r *http.Request, f *types.File, u *types.User) ([]string, e
|
||||
}
|
||||
|
||||
name = fileutils.SlashClean(name)
|
||||
if !u.IsAllowed(name) {
|
||||
continue
|
||||
}
|
||||
files = append(files, filepath.Join(f.Path, name))
|
||||
}
|
||||
}
|
||||
@ -70,7 +67,7 @@ func (e *Env) rawHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
file, err := types.NewFileInfo(user, path)
|
||||
file, err := types.NewFile(user, path)
|
||||
if err != nil {
|
||||
httpErr(w, r, httpFsErr(err), err)
|
||||
return
|
||||
|
||||
@ -42,10 +42,10 @@ func (e *Env) getResourceData(w http.ResponseWriter, r *http.Request, prefix str
|
||||
path = "/"
|
||||
}
|
||||
|
||||
if !user.IsAllowed(path) {
|
||||
/* TODO if !user.IsAllowed(path) {
|
||||
httpErr(w, r, http.StatusForbidden, nil)
|
||||
return "", nil, false
|
||||
}
|
||||
} */
|
||||
|
||||
return path, user, true
|
||||
}
|
||||
@ -56,7 +56,7 @@ func (e *Env) resourceGetHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
file, err := types.NewFileInfo(user, path)
|
||||
file, err := types.NewFile(user, path)
|
||||
if err != nil {
|
||||
httpErr(w, r, httpFsErr(err), err)
|
||||
return
|
||||
|
||||
@ -68,7 +68,7 @@ func (e *Env) settingsPutHandler(w http.ResponseWriter, r *http.Request) {
|
||||
settings.Shell = req.Shell
|
||||
settings.Commands = req.Commands
|
||||
|
||||
err = e.Store.Config.SaveSettings(settings)
|
||||
err = e.Store.SaveSettings(settings)
|
||||
if err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
return
|
||||
|
||||
@ -34,7 +34,7 @@ func (e *Env) shareGetHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
s, err := e.Store.Share.GetByPath(path)
|
||||
s, err := e.Store.GetLinksByPath(path)
|
||||
if err == types.ErrNotExist {
|
||||
renderJSON(w, r, []*types.ShareLink{})
|
||||
return
|
||||
@ -47,7 +47,7 @@ func (e *Env) shareGetHandler(w http.ResponseWriter, r *http.Request) {
|
||||
|
||||
for i, link := range s {
|
||||
if link.Expires && link.ExpireDate.Before(time.Now()) {
|
||||
e.Store.Share.Delete(link.Hash)
|
||||
e.Store.DeleteLink(link.Hash)
|
||||
s = append(s[:i], s[i+1:]...)
|
||||
}
|
||||
}
|
||||
@ -73,7 +73,7 @@ func (e *Env) shareDeleteHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.Store.Share.Delete(hash)
|
||||
err := e.Store.DeleteLink(hash)
|
||||
if err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
return
|
||||
@ -92,7 +92,7 @@ func (e *Env) sharePostHandler(w http.ResponseWriter, r *http.Request) {
|
||||
|
||||
if expire == "" {
|
||||
var err error
|
||||
s, err = e.Store.Share.GetPermanent(path)
|
||||
s, err = e.Store.GetLinkPermanent(path)
|
||||
if err == nil {
|
||||
w.Write([]byte(e.Settings.BaseURL + "/share/" + s.Hash))
|
||||
return
|
||||
@ -136,7 +136,7 @@ func (e *Env) sharePostHandler(w http.ResponseWriter, r *http.Request) {
|
||||
s.ExpireDate = time.Now().Add(add)
|
||||
}
|
||||
|
||||
if err := e.Store.Share.Save(s); err != nil {
|
||||
if err := e.Store.SaveLink(s); err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
return
|
||||
}
|
||||
|
||||
@ -57,7 +57,7 @@ func (e *Env) usersGetHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
users, err := e.Store.Users.Gets()
|
||||
users, err := e.Store.GetUsers()
|
||||
if err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
return
|
||||
@ -100,7 +100,7 @@ func (e *Env) userGetHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
u, err := e.Store.Users.Get(id)
|
||||
u, err := e.Store.GetUser(id)
|
||||
if err == types.ErrNotExist {
|
||||
httpErr(w, r, http.StatusNotFound, nil)
|
||||
return
|
||||
@ -121,7 +121,7 @@ func (e *Env) userDeleteHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
err := e.Store.Users.Delete(id)
|
||||
err := e.Store.DeleteUser(id)
|
||||
if err == types.ErrNotExist {
|
||||
httpErr(w, r, http.StatusNotFound, nil)
|
||||
return
|
||||
@ -160,7 +160,7 @@ func (e *Env) userPostHandler(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
err = e.Store.Users.Save(req.Data)
|
||||
err = e.Store.SaveUser(req.Data)
|
||||
if err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
return
|
||||
@ -198,7 +198,7 @@ func (e *Env) userPutHandler(w http.ResponseWriter, r *http.Request) {
|
||||
req.Data.Password, err = types.HashPwd(req.Data.Password)
|
||||
} else {
|
||||
var suser *types.User
|
||||
suser, err = e.Store.Users.Get(modifiedID)
|
||||
suser, err = e.Store.GetUser(modifiedID)
|
||||
req.Data.Password = suser.Password
|
||||
}
|
||||
|
||||
@ -232,7 +232,7 @@ func (e *Env) userPutHandler(w http.ResponseWriter, r *http.Request) {
|
||||
req.Which[k] = strings.Title(v)
|
||||
}
|
||||
|
||||
err = e.Store.Users.Update(req.Data, req.Which...)
|
||||
err = e.Store.UpdateUser(req.Data, req.Which...)
|
||||
if err != nil {
|
||||
httpErr(w, r, http.StatusInternalServerError, err)
|
||||
}
|
||||
|
||||
@ -139,10 +139,6 @@ func (e *Env) searchHandler(w http.ResponseWriter, r *http.Request) {
|
||||
|
||||
scope := strings.TrimPrefix(r.URL.Path, "/api/search")
|
||||
err = search.Search(user.Fs, scope, value, func(path string, f os.FileInfo) error {
|
||||
if !user.IsAllowed(path) {
|
||||
return nil
|
||||
}
|
||||
|
||||
response, _ := json.Marshal(map[string]interface{}{
|
||||
"dir": f.IsDir(),
|
||||
"path": path,
|
||||
|
||||
@ -2,8 +2,10 @@ package types
|
||||
|
||||
import "net/http"
|
||||
|
||||
// Auther is the interface each authentication method must
|
||||
// implement.
|
||||
// Auther is the authentication interface.
|
||||
type Auther interface {
|
||||
Auth(r *http.Request) (*User, error)
|
||||
// Auth is called to authenticate a request.
|
||||
Auth(*http.Request) (*User, error)
|
||||
// SetStorage gives the Auther the storage.
|
||||
SetStorage(*Storage)
|
||||
}
|
||||
|
||||
@ -13,4 +13,5 @@ var (
|
||||
ErrNoPermission = errors.New("permission denied")
|
||||
ErrInvalidAuthMethod = errors.New("invalid auth method")
|
||||
ErrEmptyKey = errors.New("empty key")
|
||||
ErrInvalidDataType = errors.New("invalid data type")
|
||||
)
|
||||
|
||||
@ -35,8 +35,8 @@ type File struct {
|
||||
Checksums map[string]string `json:"checksums,omitempty"`
|
||||
}
|
||||
|
||||
// NewFileInfo generates a new file info from a user and a path.
|
||||
func NewFileInfo(u *User, path string) (*File, error) {
|
||||
// NewFile generates a new file info from a user and a path.
|
||||
func NewFile(u *User, path string) (*File, error) {
|
||||
f := &File{
|
||||
Path: path,
|
||||
}
|
||||
@ -120,10 +120,6 @@ func (f *File) getDirInfo() error {
|
||||
name := i.Name()
|
||||
path := filepath.Join(f.Path, name)
|
||||
|
||||
if !f.user.IsAllowed(path) {
|
||||
continue
|
||||
}
|
||||
|
||||
if strings.HasPrefix(i.Mode().String(), "L") {
|
||||
// It's a symbolic link. We try to follow it. If it doesn't work,
|
||||
// we stay with the link information instead if the target's.
|
||||
|
||||
139
types/fs.go
Normal file
139
types/fs.go
Normal file
@ -0,0 +1,139 @@
|
||||
package types
|
||||
|
||||
import (
|
||||
"os"
|
||||
"syscall"
|
||||
"time"
|
||||
|
||||
"github.com/spf13/afero"
|
||||
)
|
||||
|
||||
type userFs struct {
|
||||
source afero.Fs
|
||||
user *User
|
||||
settings *Settings
|
||||
}
|
||||
|
||||
func (u *userFs) isAllowed(name string) bool {
|
||||
if !isAllowed(name, u.user.Rules) {
|
||||
return false
|
||||
}
|
||||
|
||||
return isAllowed(name, u.settings.Rules)
|
||||
}
|
||||
|
||||
func (u *userFs) Chtimes(name string, a, m time.Time) error {
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Chtimes(name, a, m)
|
||||
}
|
||||
|
||||
func (u *userFs) Chmod(name string, mode os.FileMode) error {
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Chmod(name, mode)
|
||||
}
|
||||
|
||||
func (u *userFs) Name() string {
|
||||
return "userFs"
|
||||
}
|
||||
|
||||
func (u *userFs) Stat(name string) (os.FileInfo, error) {
|
||||
if !u.isAllowed(name) {
|
||||
return nil, syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Stat(name)
|
||||
}
|
||||
|
||||
func (u *userFs) Rename(oldname, newname string) error {
|
||||
if !u.user.Perm.Rename {
|
||||
return os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(oldname) || !u.isAllowed(newname) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Rename(oldname, newname)
|
||||
}
|
||||
|
||||
func (u *userFs) RemoveAll(name string) error {
|
||||
if !u.user.Perm.Delete {
|
||||
return os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.RemoveAll(name)
|
||||
}
|
||||
|
||||
func (u *userFs) Remove(name string) error {
|
||||
if !u.user.Perm.Delete {
|
||||
return os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Remove(name)
|
||||
}
|
||||
|
||||
func (u *userFs) OpenFile(name string, flag int, perm os.FileMode) (afero.File, error) {
|
||||
if !u.isAllowed(name) {
|
||||
return nil, syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.OpenFile(name, flag, perm)
|
||||
}
|
||||
|
||||
func (u *userFs) Open(name string) (afero.File, error) {
|
||||
if !u.isAllowed(name) {
|
||||
return nil, syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Open(name)
|
||||
}
|
||||
|
||||
func (u *userFs) Mkdir(name string, perm os.FileMode) error {
|
||||
if !u.user.Perm.Create {
|
||||
return os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Mkdir(name, perm)
|
||||
}
|
||||
|
||||
func (u *userFs) MkdirAll(name string, perm os.FileMode) error {
|
||||
if !u.user.Perm.Create {
|
||||
return os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(name) {
|
||||
return syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.MkdirAll(name, perm)
|
||||
}
|
||||
|
||||
func (u *userFs) Create(name string) (afero.File, error) {
|
||||
if !u.user.Perm.Create {
|
||||
return nil, os.ErrPermission
|
||||
}
|
||||
|
||||
if !u.isAllowed(name) {
|
||||
return nil, syscall.ENOENT
|
||||
}
|
||||
|
||||
return u.source.Create(name)
|
||||
}
|
||||
@ -16,11 +16,6 @@ type Settings struct {
|
||||
Rules []Rule `json:"rules"` // TODO: use this add to cli
|
||||
}
|
||||
|
||||
// IsAllowed matches the rules against the url.
|
||||
func (e Settings) IsAllowed(url string) bool {
|
||||
return isAllowed(url, e.Rules)
|
||||
}
|
||||
|
||||
// Sorting contains a sorting order.
|
||||
type Sorting struct {
|
||||
By string `json:"by"`
|
||||
|
||||
230
types/storage.go
230
types/storage.go
@ -1,18 +1,222 @@
|
||||
package types
|
||||
|
||||
// Store is used to persist data.
|
||||
type Store struct {
|
||||
Users *UsersVerify
|
||||
Config *ConfigVerify
|
||||
Share ShareStore
|
||||
import (
|
||||
"strings"
|
||||
)
|
||||
|
||||
// StorageBackend is the interface used to persist data.
|
||||
type StorageBackend interface {
|
||||
GetUserByID(uint) (*User, error)
|
||||
GetUserByUsername(string) (*User, error)
|
||||
GetUsers() ([]*User, error)
|
||||
SaveUser(u *User) error
|
||||
UpdateUser(u *User, fields ...string) error
|
||||
DeleteUserByID(uint) error
|
||||
DeleteUserByUsername(string) error
|
||||
GetSettings() (*Settings, error)
|
||||
SaveSettings(*Settings) error
|
||||
GetAuther(AuthMethod) (Auther, error)
|
||||
SaveAuther(Auther) error
|
||||
GetLinkByHash(hash string) (*ShareLink, error)
|
||||
GetLinkPermanent(path string) (*ShareLink, error)
|
||||
GetLinksByPath(path string) ([]*ShareLink, error)
|
||||
SaveLink(s *ShareLink) error
|
||||
DeleteLink(hash string) error
|
||||
}
|
||||
|
||||
// ShareStore is the interface to manage share links.
|
||||
type ShareStore interface {
|
||||
Get(hash string) (*ShareLink, error)
|
||||
GetPermanent(path string) (*ShareLink, error)
|
||||
GetByPath(path string) ([]*ShareLink, error)
|
||||
Gets() ([]*ShareLink, error)
|
||||
Save(s *ShareLink) error
|
||||
Delete(hash string) error
|
||||
// Storage implements Storage interface and verifies
|
||||
// the data before getting in and out the database.
|
||||
type Storage struct {
|
||||
src StorageBackend
|
||||
}
|
||||
|
||||
// NewStorage creates a Storage from a StorageBackend.
|
||||
func NewStorage(src StorageBackend) *Storage {
|
||||
return &Storage{src: src}
|
||||
}
|
||||
|
||||
// GetUser allows you to get a user by its name or username. The provided
|
||||
// id must be a string for username lookup or a uint for id lookup. If id
|
||||
// is neither, a ErrInvalidDataType will be returned.
|
||||
func (v *Storage) GetUser(id interface{}) (*User, error) {
|
||||
var (
|
||||
user *User
|
||||
err error
|
||||
)
|
||||
|
||||
switch id.(type) {
|
||||
case string:
|
||||
user, err = v.src.GetUserByUsername(id.(string))
|
||||
case uint:
|
||||
user, err = v.src.GetUserByID(id.(uint))
|
||||
default:
|
||||
return nil, ErrInvalidDataType
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
settings, err := v.GetSettings()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
user.clean(settings)
|
||||
return user, err
|
||||
}
|
||||
|
||||
// GetUsers gets a list of all users.
|
||||
func (v *Storage) GetUsers() ([]*User, error) {
|
||||
users, err := v.src.GetUsers()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
settings, err := v.GetSettings()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
for _, user := range users {
|
||||
user.clean(settings)
|
||||
}
|
||||
|
||||
return users, err
|
||||
}
|
||||
|
||||
// UpdateUser updates a user in the database.
|
||||
func (v *Storage) UpdateUser(user *User, fields ...string) error {
|
||||
settings, err := v.GetSettings()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
err = user.clean(settings, fields...)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return v.src.UpdateUser(user, fields...)
|
||||
}
|
||||
|
||||
// SaveUser saves the user in a storage.
|
||||
func (v *Storage) SaveUser(user *User) error {
|
||||
settings, err := v.GetSettings()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if err := user.clean(settings); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return v.src.SaveUser(user)
|
||||
}
|
||||
|
||||
// DeleteUser allows you to delete a user by its name or username. The provided
|
||||
// id must be a string for username lookup or a uint for id lookup. If id
|
||||
// is neither, a ErrInvalidDataType will be returned.
|
||||
func (v *Storage) DeleteUser(id interface{}) (err error) {
|
||||
switch id.(type) {
|
||||
case string:
|
||||
err = v.src.DeleteUserByUsername(id.(string))
|
||||
case uint:
|
||||
err = v.src.DeleteUserByID(id.(uint))
|
||||
default:
|
||||
err = ErrInvalidDataType
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// GetSettings wraps a ConfigStore.GetSettings
|
||||
func (v *Storage) GetSettings() (*Settings, error) {
|
||||
return v.src.GetSettings()
|
||||
}
|
||||
|
||||
// SaveSettings wraps a ConfigStore.SaveSettings
|
||||
func (v *Storage) SaveSettings(s *Settings) error {
|
||||
s.BaseURL = strings.TrimSuffix(s.BaseURL, "/")
|
||||
|
||||
if len(s.Key) == 0 {
|
||||
return ErrEmptyKey
|
||||
}
|
||||
|
||||
if s.Defaults.Locale == "" {
|
||||
s.Defaults.Locale = "en"
|
||||
}
|
||||
|
||||
if s.Defaults.Commands == nil {
|
||||
s.Defaults.Commands = []string{}
|
||||
}
|
||||
|
||||
if s.Defaults.ViewMode == "" {
|
||||
s.Defaults.ViewMode = MosaicViewMode
|
||||
}
|
||||
|
||||
if s.Rules == nil {
|
||||
s.Rules = []Rule{}
|
||||
}
|
||||
|
||||
if s.Shell == nil {
|
||||
s.Shell = []string{}
|
||||
}
|
||||
|
||||
if s.Commands == nil {
|
||||
s.Commands = map[string][]string{}
|
||||
}
|
||||
|
||||
for _, event := range defaultEvents {
|
||||
if _, ok := s.Commands["before_"+event]; !ok {
|
||||
s.Commands["before_"+event] = []string{}
|
||||
}
|
||||
|
||||
if _, ok := s.Commands["after_"+event]; !ok {
|
||||
s.Commands["after_"+event] = []string{}
|
||||
}
|
||||
}
|
||||
|
||||
return v.src.SaveSettings(s)
|
||||
}
|
||||
|
||||
// GetAuther wraps a ConfigStore.GetAuther
|
||||
func (v *Storage) GetAuther(t AuthMethod) (Auther, error) {
|
||||
auther, err := v.src.GetAuther(t)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
auther.SetStorage(v)
|
||||
return auther, nil
|
||||
}
|
||||
|
||||
// SaveAuther wraps a ConfigStore.SaveAuther
|
||||
func (v *Storage) SaveAuther(a Auther) error {
|
||||
return v.src.SaveAuther(a)
|
||||
}
|
||||
|
||||
// GetLinkByHash wraps a Storage.GetLinkByHash.
|
||||
func (v *Storage) GetLinkByHash(hash string) (*ShareLink, error) {
|
||||
return v.src.GetLinkByHash(hash)
|
||||
}
|
||||
|
||||
// GetLinkPermanent wraps a Storage.GetLinkPermanent
|
||||
func (v *Storage) GetLinkPermanent(path string) (*ShareLink, error) {
|
||||
return v.src.GetLinkPermanent(path)
|
||||
}
|
||||
|
||||
// GetLinksByPath wraps a Storage.GetLinksByPath
|
||||
func (v *Storage) GetLinksByPath(path string) ([]*ShareLink, error) {
|
||||
return v.src.GetLinksByPath(path)
|
||||
}
|
||||
|
||||
// SaveLink wraps a Storage.SaveLink
|
||||
func (v *Storage) SaveLink(s *ShareLink) error {
|
||||
return v.src.SaveLink(s)
|
||||
}
|
||||
|
||||
// DeleteLink wraps a Storage.DeleteLink
|
||||
func (v *Storage) DeleteLink(hash string) error {
|
||||
return v.src.DeleteLink(hash)
|
||||
}
|
||||
|
||||
@ -1,76 +0,0 @@
|
||||
package types
|
||||
|
||||
import "strings"
|
||||
|
||||
// ConfigStore is used to manage configurations relativey to a data storage.
|
||||
type ConfigStore interface {
|
||||
GetSettings() (*Settings, error)
|
||||
SaveSettings(*Settings) error
|
||||
GetAuther(AuthMethod) (Auther, error)
|
||||
SaveAuther(Auther) error
|
||||
}
|
||||
|
||||
// ConfigVerify wraps a ConfigStore and makes the verifications needed.
|
||||
type ConfigVerify struct {
|
||||
Store ConfigStore
|
||||
}
|
||||
|
||||
// GetSettings wraps a ConfigStore.GetSettings
|
||||
func (v ConfigVerify) GetSettings() (*Settings, error) {
|
||||
return v.Store.GetSettings()
|
||||
}
|
||||
|
||||
// SaveSettings wraps a ConfigStore.SaveSettings
|
||||
func (v ConfigVerify) SaveSettings(s *Settings) error {
|
||||
s.BaseURL = strings.TrimSuffix(s.BaseURL, "/")
|
||||
|
||||
if len(s.Key) == 0 {
|
||||
return ErrEmptyKey
|
||||
}
|
||||
|
||||
if s.Defaults.Locale == "" {
|
||||
s.Defaults.Locale = "en"
|
||||
}
|
||||
|
||||
if s.Defaults.Commands == nil {
|
||||
s.Defaults.Commands = []string{}
|
||||
}
|
||||
|
||||
if s.Defaults.ViewMode == "" {
|
||||
s.Defaults.ViewMode = MosaicViewMode
|
||||
}
|
||||
|
||||
if s.Rules == nil {
|
||||
s.Rules = []Rule{}
|
||||
}
|
||||
|
||||
if s.Shell == nil {
|
||||
s.Shell = []string{}
|
||||
}
|
||||
|
||||
if s.Commands == nil {
|
||||
s.Commands = map[string][]string{}
|
||||
}
|
||||
|
||||
for _, event := range defaultEvents {
|
||||
if _, ok := s.Commands["before_"+event]; !ok {
|
||||
s.Commands["before_"+event] = []string{}
|
||||
}
|
||||
|
||||
if _, ok := s.Commands["after_"+event]; !ok {
|
||||
s.Commands["after_"+event] = []string{}
|
||||
}
|
||||
}
|
||||
|
||||
return v.Store.SaveSettings(s)
|
||||
}
|
||||
|
||||
// GetAuther wraps a ConfigStore.GetAuther
|
||||
func (v ConfigVerify) GetAuther(t AuthMethod) (Auther, error) {
|
||||
return v.Store.GetAuther(t)
|
||||
}
|
||||
|
||||
// SaveAuther wraps a ConfigStore.SaveAuther
|
||||
func (v ConfigVerify) SaveAuther(a Auther) error {
|
||||
return v.Store.SaveAuther(a)
|
||||
}
|
||||
@ -1,82 +0,0 @@
|
||||
package types
|
||||
|
||||
// UsersStore is used to manage users relativey to a data storage.
|
||||
type UsersStore interface {
|
||||
Get(id uint) (*User, error)
|
||||
GetByUsername(username string) (*User, error)
|
||||
Gets() ([]*User, error)
|
||||
Save(u *User) error
|
||||
Update(u *User, fields ...string) error
|
||||
Delete(id uint) error
|
||||
DeleteByUsername(username string) error
|
||||
}
|
||||
|
||||
// UsersVerify wraps a UsersStore and makes the verifications needed.
|
||||
type UsersVerify struct {
|
||||
Store UsersStore
|
||||
}
|
||||
|
||||
// Get wraps a UsersStore.Get to verify if everything is right.
|
||||
func (v UsersVerify) Get(id uint) (*User, error) {
|
||||
user, err := v.Store.Get(id)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
user.clean()
|
||||
return user, nil
|
||||
}
|
||||
|
||||
// GetByUsername wraps a UsersStore.GetByUsername to verify if everything is right.
|
||||
func (v UsersVerify) GetByUsername(username string) (*User, error) {
|
||||
user, err := v.Store.GetByUsername(username)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
user.clean()
|
||||
return user, nil
|
||||
}
|
||||
|
||||
// Gets wraps a UsersStore.Gets to verify if everything is right.
|
||||
func (v UsersVerify) Gets() ([]*User, error) {
|
||||
users, err := v.Store.Gets()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
for _, user := range users {
|
||||
user.clean()
|
||||
}
|
||||
|
||||
return users, err
|
||||
}
|
||||
|
||||
// Update wraps a UsersStore.Update to verify if everything is right.
|
||||
func (v UsersVerify) Update(user *User, fields ...string) error {
|
||||
err := user.clean(fields...)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return v.Store.Update(user, fields...)
|
||||
}
|
||||
|
||||
// Save wraps a UsersStore.Save to verify if everything is right.
|
||||
func (v UsersVerify) Save(user *User) error {
|
||||
if err := user.clean(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return v.Store.Save(user)
|
||||
}
|
||||
|
||||
// Delete wraps a UsersStore.Delete to verify if everything is right.
|
||||
func (v UsersVerify) Delete(id uint) error {
|
||||
return v.Store.Delete(id)
|
||||
}
|
||||
|
||||
// DeleteByUsername wraps a UsersStore.DeleteByUsername to verify if everything is right.
|
||||
func (v UsersVerify) DeleteByUsername(username string) error {
|
||||
return v.Store.DeleteByUsername(username)
|
||||
}
|
||||
@ -54,7 +54,7 @@ var checkableFields = []string{
|
||||
"Rules",
|
||||
}
|
||||
|
||||
func (u *User) clean(fields ...string) error {
|
||||
func (u *User) clean(settings *Settings, fields ...string) error {
|
||||
if len(fields) == 0 {
|
||||
fields = checkableFields
|
||||
}
|
||||
@ -93,17 +93,16 @@ func (u *User) clean(fields ...string) error {
|
||||
}
|
||||
|
||||
if u.Fs == nil {
|
||||
u.Fs = afero.NewBasePathFs(afero.NewOsFs(), u.Scope)
|
||||
u.Fs = &userFs{
|
||||
user: u,
|
||||
settings: settings,
|
||||
source: afero.NewBasePathFs(afero.NewOsFs(), u.Scope),
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// IsAllowed checks if an user is allowed to go to a certain path.
|
||||
func (u *User) IsAllowed(url string) bool {
|
||||
return isAllowed(url, u.Rules)
|
||||
}
|
||||
|
||||
// CanExecute checks if an user can execute a specific command.
|
||||
func (u *User) CanExecute(command string) bool {
|
||||
if !u.Perm.Execute {
|
||||
|
||||
Loading…
Reference in New Issue
Block a user