mirror of
https://github.com/hacdias/webdav.git
synced 2026-09-23 03:31:54 +08:00
feat!: rename 'scope' to 'directory'
Directory makes it more clear of what it is. In addition, this will make it easier when allowing for multiple directories in the future, since we can just name it 'directories', which is more clear than 'scopes'.
This commit is contained in:
+5
-5
@@ -13,7 +13,7 @@ import (
|
||||
)
|
||||
|
||||
const (
|
||||
DefaultScope = "."
|
||||
DefaultDirectory = "."
|
||||
DefaultModify = false
|
||||
DefaultDebug = false
|
||||
DefaultNoSniff = false
|
||||
@@ -74,7 +74,7 @@ func ParseConfig(filename string, flags *pflag.FlagSet) (*Config, error) {
|
||||
// empty or false.
|
||||
|
||||
// Defaults shared with flags
|
||||
v.SetDefault("Scope", DefaultScope)
|
||||
v.SetDefault("Directory", DefaultDirectory)
|
||||
v.SetDefault("Modify", DefaultModify)
|
||||
v.SetDefault("Debug", DefaultDebug)
|
||||
v.SetDefault("NoSniff", DefaultNoSniff)
|
||||
@@ -111,8 +111,8 @@ func ParseConfig(filename string, flags *pflag.FlagSet) (*Config, error) {
|
||||
|
||||
// Cascade user settings
|
||||
for i := range cfg.Users {
|
||||
if !v.IsSet(fmt.Sprintf("Users.%d.Scope", i)) {
|
||||
cfg.Users[i].Scope = cfg.Scope
|
||||
if !v.IsSet(fmt.Sprintf("Users.%d.Directory", i)) {
|
||||
cfg.Users[i].Directory = cfg.Directory
|
||||
}
|
||||
|
||||
if !v.IsSet(fmt.Sprintf("Users.%d.Modify", i)) {
|
||||
@@ -139,7 +139,7 @@ func (c *Config) Validate() error {
|
||||
zap.L().Warn("unprotected config: no users have been set, so no authentication will be used")
|
||||
}
|
||||
|
||||
c.Scope, err = filepath.Abs(c.Scope)
|
||||
c.Directory, err = filepath.Abs(c.Directory)
|
||||
if err != nil {
|
||||
return fmt.Errorf("invalid config: %w", err)
|
||||
}
|
||||
|
||||
+14
-14
@@ -36,7 +36,7 @@ func TestConfigDefaults(t *testing.T) {
|
||||
|
||||
dir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, dir, cfg.Scope)
|
||||
require.Equal(t, dir, cfg.Directory)
|
||||
|
||||
require.EqualValues(t, []string{"*"}, cfg.CORS.AllowedHeaders)
|
||||
require.EqualValues(t, []string{"*"}, cfg.CORS.AllowedHosts)
|
||||
@@ -48,23 +48,23 @@ func TestConfigCascade(t *testing.T) {
|
||||
|
||||
check := func(t *testing.T, cfg *Config) {
|
||||
require.True(t, cfg.Modify)
|
||||
require.Equal(t, "/", cfg.Scope)
|
||||
require.Equal(t, "/", cfg.Directory)
|
||||
require.Len(t, cfg.Rules, 1)
|
||||
|
||||
require.Len(t, cfg.Users, 2)
|
||||
|
||||
require.True(t, cfg.Users[0].Modify)
|
||||
require.Equal(t, "/", cfg.Users[0].Scope)
|
||||
require.Equal(t, "/", cfg.Users[0].Directory)
|
||||
require.Len(t, cfg.Users[0].Rules, 1)
|
||||
|
||||
require.False(t, cfg.Users[1].Modify)
|
||||
require.Equal(t, "/basic", cfg.Users[1].Scope)
|
||||
require.Equal(t, "/basic", cfg.Users[1].Directory)
|
||||
require.Len(t, cfg.Users[1].Rules, 0)
|
||||
}
|
||||
|
||||
t.Run("YAML", func(t *testing.T) {
|
||||
content := `
|
||||
scope: /
|
||||
directory: /
|
||||
modify: true
|
||||
rules:
|
||||
- path: /public/access/
|
||||
@@ -75,7 +75,7 @@ users:
|
||||
password: admin
|
||||
- username: basic
|
||||
password: basic
|
||||
scope: /basic
|
||||
directory: /basic
|
||||
modify: false
|
||||
rules: []`
|
||||
|
||||
@@ -87,7 +87,7 @@ users:
|
||||
|
||||
t.Run("JSON", func(t *testing.T) {
|
||||
content := `{
|
||||
"scope": "/",
|
||||
"directory": "/",
|
||||
"modify": true,
|
||||
"rules": [
|
||||
{
|
||||
@@ -103,7 +103,7 @@ users:
|
||||
{
|
||||
"username": "basic",
|
||||
"password": "basic",
|
||||
"scope": "/basic",
|
||||
"directory": "/basic",
|
||||
"modify": false,
|
||||
"rules": []
|
||||
}
|
||||
@@ -118,7 +118,7 @@ users:
|
||||
|
||||
t.Run("`TOML", func(t *testing.T) {
|
||||
content := `
|
||||
scope = "/"
|
||||
directory = "/"
|
||||
modify = true
|
||||
|
||||
[[rules]]
|
||||
@@ -132,7 +132,7 @@ password = "admin"
|
||||
[[users]]
|
||||
username = "basic"
|
||||
password = "basic"
|
||||
scope = "/basic"
|
||||
directory = "/basic"
|
||||
modify = false
|
||||
rules = []
|
||||
`
|
||||
@@ -172,7 +172,7 @@ cors:
|
||||
|
||||
func TestConfigRules(t *testing.T) {
|
||||
content := `
|
||||
scope: /
|
||||
directory: /
|
||||
modify: true
|
||||
rules:
|
||||
- regex: '^.+\.js$'
|
||||
@@ -198,13 +198,13 @@ func TestConfigEnv(t *testing.T) {
|
||||
require.NoError(t, os.Setenv("WD_PORT", "1234"))
|
||||
require.NoError(t, os.Setenv("WD_DEBUG", "true"))
|
||||
require.NoError(t, os.Setenv("WD_MODIFY", "true"))
|
||||
require.NoError(t, os.Setenv("WD_SCOPE", "/test"))
|
||||
require.NoError(t, os.Setenv("WD_DIRECTORY", "/test"))
|
||||
|
||||
cfg, err := ParseConfig("", nil)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Equal(t, 1234, cfg.Port)
|
||||
assert.Equal(t, "/test", cfg.Scope)
|
||||
assert.Equal(t, "/test", cfg.Directory)
|
||||
assert.Equal(t, true, cfg.Debug)
|
||||
assert.Equal(t, true, cfg.Modify)
|
||||
|
||||
@@ -212,5 +212,5 @@ func TestConfigEnv(t *testing.T) {
|
||||
require.NoError(t, os.Setenv("WD_PORT", ""))
|
||||
require.NoError(t, os.Setenv("WD_DEBUG", ""))
|
||||
require.NoError(t, os.Setenv("WD_MODIFY", ""))
|
||||
require.NoError(t, os.Setenv("WD_SCOPE", ""))
|
||||
require.NoError(t, os.Setenv("WD_DIRECTORY", ""))
|
||||
}
|
||||
|
||||
+2
-2
@@ -28,7 +28,7 @@ func NewHandler(c *Config) (http.Handler, error) {
|
||||
Handler: webdav.Handler{
|
||||
Prefix: c.Prefix,
|
||||
FileSystem: Dir{
|
||||
Dir: webdav.Dir(c.Scope),
|
||||
Dir: webdav.Dir(c.Directory),
|
||||
noSniff: c.NoSniff,
|
||||
},
|
||||
LockSystem: webdav.NewMemLS(),
|
||||
@@ -43,7 +43,7 @@ func NewHandler(c *Config) (http.Handler, error) {
|
||||
Handler: webdav.Handler{
|
||||
Prefix: c.Prefix,
|
||||
FileSystem: Dir{
|
||||
Dir: webdav.Dir(u.Scope),
|
||||
Dir: webdav.Dir(u.Directory),
|
||||
noSniff: c.NoSniff,
|
||||
},
|
||||
LockSystem: webdav.NewMemLS(),
|
||||
|
||||
+6
-6
@@ -50,7 +50,7 @@ func TestServerDefaults(t *testing.T) {
|
||||
"sub/bar.txt": []byte("bar"),
|
||||
})
|
||||
|
||||
srv := makeTestServer(t, "scope: "+dir)
|
||||
srv := makeTestServer(t, "directory: "+dir)
|
||||
client := gowebdav.NewClient(srv.URL, "", "")
|
||||
|
||||
// By default, reading permissions.
|
||||
@@ -90,7 +90,7 @@ func TestServerAuthentication(t *testing.T) {
|
||||
})
|
||||
|
||||
srv := makeTestServer(t, fmt.Sprintf(`
|
||||
scope: %s
|
||||
directory: %s
|
||||
modify: true
|
||||
|
||||
users:
|
||||
@@ -152,7 +152,7 @@ func TestServerRules(t *testing.T) {
|
||||
})
|
||||
|
||||
srv := makeTestServer(t, fmt.Sprintf(`
|
||||
scope: %s
|
||||
directory: %s
|
||||
modify: true
|
||||
|
||||
users:
|
||||
@@ -194,16 +194,16 @@ func TestServerPermissions(t *testing.T) {
|
||||
})
|
||||
|
||||
srv := makeTestServer(t, fmt.Sprintf(`
|
||||
scope: %s
|
||||
directory: %s
|
||||
modify: true
|
||||
|
||||
users:
|
||||
- username: a
|
||||
password: a
|
||||
scope: %s/a
|
||||
directory: %s/a
|
||||
- username: b
|
||||
password: b
|
||||
scope: %s/b
|
||||
directory: %s/b
|
||||
modify: false
|
||||
`, dir, dir, dir))
|
||||
|
||||
|
||||
+11
-3
@@ -4,6 +4,7 @@ import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"path/filepath"
|
||||
"regexp"
|
||||
"strings"
|
||||
)
|
||||
@@ -40,9 +41,9 @@ func (r *Rule) Matches(path string) bool {
|
||||
}
|
||||
|
||||
type Permissions struct {
|
||||
Scope string
|
||||
Modify bool
|
||||
Rules []*Rule
|
||||
Directory string
|
||||
Modify bool
|
||||
Rules []*Rule
|
||||
}
|
||||
|
||||
// Allowed checks if the user has permission to access a directory/file
|
||||
@@ -69,6 +70,13 @@ func (p Permissions) Allowed(r *http.Request) bool {
|
||||
}
|
||||
|
||||
func (p *Permissions) Validate() error {
|
||||
var err error
|
||||
|
||||
p.Directory, err = filepath.Abs(p.Directory)
|
||||
if err != nil {
|
||||
return fmt.Errorf("invalid permissions: %w", err)
|
||||
}
|
||||
|
||||
for _, r := range p.Rules {
|
||||
if err := r.Validate(); err != nil {
|
||||
return fmt.Errorf("invalid permissions: %w", err)
|
||||
|
||||
Reference in New Issue
Block a user