mirror of
https://github.com/hacdias/webdav.git
synced 2026-09-26 05:01:54 +08:00
Update readme
This commit is contained in:
@@ -0,0 +1,175 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"encoding/json"
|
||||||
|
"io/ioutil"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
"regexp"
|
||||||
|
|
||||||
|
"github.com/hacdias/webdav"
|
||||||
|
wd "golang.org/x/net/webdav"
|
||||||
|
yaml "gopkg.in/yaml.v2"
|
||||||
|
)
|
||||||
|
|
||||||
|
func parseRules(raw []map[string]interface{}) []*webdav.Rule {
|
||||||
|
rules := []*webdav.Rule{}
|
||||||
|
|
||||||
|
for _, r := range raw {
|
||||||
|
rule := &webdav.Rule{
|
||||||
|
Regex: false,
|
||||||
|
Allow: false,
|
||||||
|
Path: "",
|
||||||
|
}
|
||||||
|
|
||||||
|
if regex, ok := r["regex"].(bool); ok {
|
||||||
|
rule.Regex = regex
|
||||||
|
}
|
||||||
|
|
||||||
|
if allow, ok := r["allow"].(bool); ok {
|
||||||
|
rule.Allow = allow
|
||||||
|
}
|
||||||
|
|
||||||
|
path, ok := r["rule"].(string)
|
||||||
|
if !ok {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if rule.Regex {
|
||||||
|
rule.Regexp = regexp.MustCompile(path)
|
||||||
|
} else {
|
||||||
|
rule.Path = path
|
||||||
|
}
|
||||||
|
|
||||||
|
rules = append(rules, rule)
|
||||||
|
}
|
||||||
|
|
||||||
|
return rules
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseUsers(raw []map[string]interface{}, c *cfg) {
|
||||||
|
for _, r := range raw {
|
||||||
|
username, ok := r["username"].(string)
|
||||||
|
if !ok {
|
||||||
|
log.Fatal("user needs an username")
|
||||||
|
}
|
||||||
|
|
||||||
|
password, ok := r["password"].(string)
|
||||||
|
if !ok {
|
||||||
|
log.Fatal("user needs a password")
|
||||||
|
}
|
||||||
|
|
||||||
|
c.auth[username] = password
|
||||||
|
|
||||||
|
user := &webdav.User{
|
||||||
|
Scope: c.webdav.User.Scope,
|
||||||
|
Modify: c.webdav.User.Modify,
|
||||||
|
Rules: c.webdav.User.Rules,
|
||||||
|
}
|
||||||
|
|
||||||
|
if scope, ok := r["scope"].(string); ok {
|
||||||
|
user.Scope = scope
|
||||||
|
}
|
||||||
|
|
||||||
|
if modify, ok := r["modify"].(bool); ok {
|
||||||
|
user.Modify = modify
|
||||||
|
}
|
||||||
|
|
||||||
|
if rules, ok := r["rules"].([]map[string]interface{}); ok {
|
||||||
|
user.Rules = parseRules(rules)
|
||||||
|
}
|
||||||
|
|
||||||
|
user.Handler = &wd.Handler{
|
||||||
|
FileSystem: wd.Dir(user.Scope),
|
||||||
|
LockSystem: wd.NewMemLS(),
|
||||||
|
}
|
||||||
|
|
||||||
|
c.webdav.Users[username] = user
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func getConfig() []byte {
|
||||||
|
if config == "" {
|
||||||
|
for _, v := range defaultConfigs {
|
||||||
|
_, err := os.Stat(v)
|
||||||
|
if err == nil {
|
||||||
|
config = v
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if config == "" {
|
||||||
|
log.Fatal("no config file specified; couldn't find any config.{yaml,json}")
|
||||||
|
}
|
||||||
|
|
||||||
|
file, err := ioutil.ReadFile(config)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
return file
|
||||||
|
}
|
||||||
|
|
||||||
|
type cfg struct {
|
||||||
|
webdav *webdav.Config
|
||||||
|
port string
|
||||||
|
auth map[string]string
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseConfig() *cfg {
|
||||||
|
file := getConfig()
|
||||||
|
|
||||||
|
data := struct {
|
||||||
|
Port string `json:"port" yaml:"port"`
|
||||||
|
Scope string `json:"scope" yaml:"scope"`
|
||||||
|
Modify bool `json:"modify" yaml:"modify"`
|
||||||
|
Rules []map[string]interface{} `json:"rules" yaml:"rules"`
|
||||||
|
Users []map[string]interface{} `json:"users" yaml:"users"`
|
||||||
|
}{
|
||||||
|
Port: "0",
|
||||||
|
Scope: "./",
|
||||||
|
Modify: true,
|
||||||
|
}
|
||||||
|
|
||||||
|
var err error
|
||||||
|
if filepath.Ext(config) == ".json" {
|
||||||
|
err = json.Unmarshal(file, &data)
|
||||||
|
} else {
|
||||||
|
err = yaml.Unmarshal(file, &data)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
config := &cfg{
|
||||||
|
port: data.Port,
|
||||||
|
auth: map[string]string{},
|
||||||
|
webdav: &webdav.Config{
|
||||||
|
BaseURL: "",
|
||||||
|
User: &webdav.User{
|
||||||
|
Scope: data.Scope,
|
||||||
|
Modify: data.Modify,
|
||||||
|
Rules: []*webdav.Rule{},
|
||||||
|
Handler: &wd.Handler{
|
||||||
|
FileSystem: wd.Dir(data.Scope),
|
||||||
|
LockSystem: wd.NewMemLS(),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Users: map[string]*webdav.User{},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(data.Users) == 0 {
|
||||||
|
log.Fatal("no user defined")
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(data.Rules) != 0 {
|
||||||
|
config.webdav.User.Rules = parseRules(data.Rules)
|
||||||
|
}
|
||||||
|
|
||||||
|
parseUsers(data.Users, config)
|
||||||
|
return config
|
||||||
|
}
|
||||||
+17
-174
@@ -1,18 +1,11 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"encoding/json"
|
|
||||||
"errors"
|
|
||||||
"flag"
|
"flag"
|
||||||
"io/ioutil"
|
"fmt"
|
||||||
|
"log"
|
||||||
|
"net"
|
||||||
"net/http"
|
"net/http"
|
||||||
"os"
|
|
||||||
"path/filepath"
|
|
||||||
"regexp"
|
|
||||||
|
|
||||||
"github.com/hacdias/webdav"
|
|
||||||
wd "golang.org/x/net/webdav"
|
|
||||||
"gopkg.in/yaml.v2"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@@ -21,168 +14,7 @@ var (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
flag.StringVar(&config, "config", "config.yaml", "Configuration file")
|
flag.StringVar(&config, "config", "", "Configuration file")
|
||||||
}
|
|
||||||
|
|
||||||
func parseRules(raw []map[string]interface{}) []*webdav.Rule {
|
|
||||||
rules := []*webdav.Rule{}
|
|
||||||
|
|
||||||
for _, r := range raw {
|
|
||||||
rule := &webdav.Rule{
|
|
||||||
Regex: false,
|
|
||||||
Allow: false,
|
|
||||||
Path: "",
|
|
||||||
}
|
|
||||||
|
|
||||||
if regex, ok := r["regex"].(bool); ok {
|
|
||||||
rule.Regex = regex
|
|
||||||
}
|
|
||||||
|
|
||||||
if allow, ok := r["allow"].(bool); ok {
|
|
||||||
rule.Allow = allow
|
|
||||||
}
|
|
||||||
|
|
||||||
path, ok := r["rule"].(string)
|
|
||||||
if !ok {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
if rule.Regex {
|
|
||||||
rule.Regexp = regexp.MustCompile(path)
|
|
||||||
} else {
|
|
||||||
rule.Path = path
|
|
||||||
}
|
|
||||||
|
|
||||||
rules = append(rules, rule)
|
|
||||||
}
|
|
||||||
|
|
||||||
return rules
|
|
||||||
}
|
|
||||||
|
|
||||||
func parseUsers(raw []map[string]interface{}, c *cfg) {
|
|
||||||
for _, r := range raw {
|
|
||||||
username, ok := r["username"].(string)
|
|
||||||
if !ok {
|
|
||||||
panic("user needs an username")
|
|
||||||
}
|
|
||||||
|
|
||||||
password, ok := r["password"].(string)
|
|
||||||
if !ok {
|
|
||||||
panic("user needs a password")
|
|
||||||
}
|
|
||||||
|
|
||||||
c.auth[username] = password
|
|
||||||
|
|
||||||
user := &webdav.User{
|
|
||||||
Scope: c.webdav.User.Scope,
|
|
||||||
Modify: c.webdav.User.Modify,
|
|
||||||
Rules: c.webdav.User.Rules,
|
|
||||||
}
|
|
||||||
|
|
||||||
if scope, ok := r["scope"].(string); ok {
|
|
||||||
user.Scope = scope
|
|
||||||
}
|
|
||||||
|
|
||||||
if modify, ok := r["modify"].(bool); ok {
|
|
||||||
user.Modify = modify
|
|
||||||
}
|
|
||||||
|
|
||||||
if rules, ok := r["rules"].([]map[string]interface{}); ok {
|
|
||||||
user.Rules = parseRules(rules)
|
|
||||||
}
|
|
||||||
|
|
||||||
user.Handler = &wd.Handler{
|
|
||||||
FileSystem: wd.Dir(user.Scope),
|
|
||||||
LockSystem: wd.NewMemLS(),
|
|
||||||
}
|
|
||||||
|
|
||||||
c.webdav.Users[username] = user
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func getConfig() []byte {
|
|
||||||
if config == "" {
|
|
||||||
for _, v := range defaultConfigs {
|
|
||||||
_, err := os.Stat(v)
|
|
||||||
if err == nil {
|
|
||||||
config = v
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if config == "" {
|
|
||||||
panic(errors.New("no config file"))
|
|
||||||
}
|
|
||||||
|
|
||||||
file, err := ioutil.ReadFile(config)
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
return file
|
|
||||||
}
|
|
||||||
|
|
||||||
type cfg struct {
|
|
||||||
webdav *webdav.Config
|
|
||||||
port string
|
|
||||||
auth map[string]string
|
|
||||||
}
|
|
||||||
|
|
||||||
func parseConfig() *cfg {
|
|
||||||
file := getConfig()
|
|
||||||
|
|
||||||
data := struct {
|
|
||||||
Port string `json:"port" yaml:"port"`
|
|
||||||
Scope string `json:"scope" yaml:"scope"`
|
|
||||||
Modify bool `json:"modify" yaml:"modify"`
|
|
||||||
Rules []map[string]interface{} `json:"rules" yaml:"rules"`
|
|
||||||
Users []map[string]interface{} `json:"users" yaml:"users"`
|
|
||||||
}{
|
|
||||||
Port: "80",
|
|
||||||
Scope: "./",
|
|
||||||
Modify: true,
|
|
||||||
}
|
|
||||||
|
|
||||||
var err error
|
|
||||||
if filepath.Ext(config) == ".json" {
|
|
||||||
err = json.Unmarshal(file, &data)
|
|
||||||
} else {
|
|
||||||
err = yaml.Unmarshal(file, &data)
|
|
||||||
}
|
|
||||||
|
|
||||||
if err != nil {
|
|
||||||
panic(err)
|
|
||||||
}
|
|
||||||
|
|
||||||
config := &cfg{
|
|
||||||
port: data.Port,
|
|
||||||
auth: map[string]string{},
|
|
||||||
webdav: &webdav.Config{
|
|
||||||
BaseURL: "",
|
|
||||||
User: &webdav.User{
|
|
||||||
Scope: data.Scope,
|
|
||||||
Modify: data.Modify,
|
|
||||||
Rules: []*webdav.Rule{},
|
|
||||||
Handler: &wd.Handler{
|
|
||||||
FileSystem: wd.Dir(data.Scope),
|
|
||||||
LockSystem: wd.NewMemLS(),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Users: map[string]*webdav.User{},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(data.Users) == 0 {
|
|
||||||
panic("no user defined")
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(data.Rules) != 0 {
|
|
||||||
config.webdav.User.Rules = parseRules(data.Rules)
|
|
||||||
}
|
|
||||||
|
|
||||||
parseUsers(data.Users, config)
|
|
||||||
return config
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func basicAuth(c *cfg) http.Handler {
|
func basicAuth(c *cfg) http.Handler {
|
||||||
@@ -215,7 +47,18 @@ func main() {
|
|||||||
cfg := parseConfig()
|
cfg := parseConfig()
|
||||||
handler := basicAuth(cfg)
|
handler := basicAuth(cfg)
|
||||||
|
|
||||||
if err := http.ListenAndServe(":"+cfg.port, handler); err != nil {
|
// Builds the address and a listener.
|
||||||
panic(err)
|
laddr := ":" + cfg.port
|
||||||
|
listener, err := net.Listen("tcp", laddr)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Tell the user the port in which is listening.
|
||||||
|
fmt.Println("Listening on", listener.Addr().String())
|
||||||
|
|
||||||
|
// Starts the server.
|
||||||
|
if err := http.Serve(listener, handler); err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,3 +1,23 @@
|
|||||||
# webdav
|
# webdav
|
||||||
|
|
||||||
(TODO)
|
[](https://travis-ci.org/hacdias/webdav)
|
||||||
|
[](https://goreportcard.com/report/hacdias/webdav)
|
||||||
|
|
||||||
|
```webdav``` is a simple tool that creates a WebDAV server for you. By default, it runs on a random free port and supports JSON and YAML configuration. Here is a simple YAML configuration example:
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
scope: /path/to/files
|
||||||
|
port: 8080
|
||||||
|
users:
|
||||||
|
- username: admin
|
||||||
|
password: admin
|
||||||
|
- username: basic
|
||||||
|
password: basic
|
||||||
|
modify: false
|
||||||
|
rules:
|
||||||
|
- regex: false
|
||||||
|
- allow: false
|
||||||
|
- path: /some/file
|
||||||
|
```
|
||||||
|
|
||||||
|
You can specify the path to the configuration file using the `--config` flag. By default, it will search for a `config.{yaml,json}` file on your current working directory.
|
||||||
Reference in New Issue
Block a user