Remove zeebo/bencode dependency because of anacrolix/torrent usage

This commit is contained in:
Širhoe Biazhkovič
2021-09-05 16:17:21 +03:00
parent 8580bb37e0
commit cb4ac3c7f8
6 changed files with 80 additions and 98 deletions

View File

@@ -1,7 +1,7 @@
package http package http
import ( import (
"github.com/zeebo/bencode" "github.com/anacrolix/torrent/bencode"
"net/http" "net/http"
"github.com/chihaya/chihaya/bittorrent" "github.com/chihaya/chihaya/bittorrent"

2
go.mod
View File

@@ -7,7 +7,6 @@ require (
github.com/alicebob/gopher-json v0.0.0-20180125190556-5a6b3ba71ee6 // indirect github.com/alicebob/gopher-json v0.0.0-20180125190556-5a6b3ba71ee6 // indirect
github.com/alicebob/miniredis v2.5.0+incompatible github.com/alicebob/miniredis v2.5.0+incompatible
github.com/anacrolix/torrent v1.28.0 github.com/anacrolix/torrent v1.28.0
github.com/fsnotify/fsnotify v1.4.9
github.com/go-redsync/redsync v1.4.2 github.com/go-redsync/redsync v1.4.2
github.com/gomodule/redigo v2.0.0+incompatible github.com/gomodule/redigo v2.0.0+incompatible
github.com/julienschmidt/httprouter v1.3.0 github.com/julienschmidt/httprouter v1.3.0
@@ -19,6 +18,5 @@ require (
github.com/spf13/cobra v1.1.3 github.com/spf13/cobra v1.1.3
github.com/stretchr/testify v1.7.0 github.com/stretchr/testify v1.7.0
github.com/yuin/gopher-lua v0.0.0-20191220021717-ab39c6098bdb // indirect github.com/yuin/gopher-lua v0.0.0-20191220021717-ab39c6098bdb // indirect
github.com/zeebo/bencode v1.0.0
gopkg.in/yaml.v2 v2.4.0 gopkg.in/yaml.v2 v2.4.0
) )

View File

@@ -8,28 +8,30 @@ import (
"sync" "sync"
) )
type Builder interface { type Constructor func () Configuration
New() (Container, error)
type Configuration interface {
Build() (Container, error)
} }
var ( var (
buildersMU sync.Mutex constructorsMU sync.Mutex
builders = make(map[string]Builder) constructors = make(map[string]Constructor)
ErrContainerDoesNotExist = errors.New("torrent hash container with that name does not exist") ErrContainerDoesNotExist = errors.New("torrent hash container with that name does not exist")
) )
func Register(n string, c Builder) { func Register(n string, c Constructor) {
if len(n) == 0 { if len(n) == 0 {
panic("middleware: could not register a Container with an empty name") panic("middleware: could not register a Container with an empty name")
} }
if c == nil { if c == nil {
panic("middleware: could not register a Container with nil builder") panic("middleware: could not register a Container with nil builder constructor")
} }
buildersMU.Lock() constructorsMU.Lock()
defer buildersMU.Unlock() defer constructorsMU.Unlock()
builders[n] = c constructors[n] = c
} }
type Container interface { type Container interface {
@@ -38,15 +40,16 @@ type Container interface {
} }
func GetContainer(name string, confBytes []byte) (Container, error) { func GetContainer(name string, confBytes []byte) (Container, error) {
buildersMU.Lock() constructorsMU.Lock()
defer buildersMU.Unlock() defer constructorsMU.Unlock()
var err error var err error
var cn Container var cn Container
if builder, exist := builders[name]; !exist { if getConfig, exist := constructors[name]; !exist {
err = ErrContainerDoesNotExist err = ErrContainerDoesNotExist
} else { } else {
if err = yaml.Unmarshal(confBytes, &cn); err == nil { conf := getConfig()
cn, err = builder.New() if err = yaml.Unmarshal(confBytes, &conf); err == nil {
cn, err = conf.Build()
} }
} }
return cn, err return cn, err

View File

@@ -2,103 +2,65 @@ package directory
import ( import (
"fmt" "fmt"
"github.com/chihaya/chihaya/bittorrent" "github.com/anacrolix/torrent/util/dirwatch"
"github.com/chihaya/chihaya/middleware/torrentapproval/container" "github.com/chihaya/chihaya/middleware/torrentapproval/container"
"github.com/chihaya/chihaya/middleware/torrentapproval/container/list" "github.com/chihaya/chihaya/middleware/torrentapproval/container/list"
"github.com/chihaya/chihaya/pkg/log"
"github.com/chihaya/chihaya/pkg/stop" "github.com/chihaya/chihaya/pkg/stop"
"github.com/fsnotify/fsnotify"
"os"
"path/filepath"
"sync" "sync"
) )
func init() { func init() {
container.Register("list", builder{}) container.Register("list", func() container.Configuration {
return Config{}
})
} }
type builder struct { type Config struct {
WhitelistPath string `yaml:"whitelist_path"` WhitelistPath string `yaml:"whitelist_path"`
BlacklistPath string `yaml:"blacklist_path"` BlacklistPath string `yaml:"blacklist_path"`
} }
func (b builder) New() (container.Container, error) { func (b Config) Build() (container.Container, error) {
if len(b.WhitelistPath) > 0 && len(b.BlacklistPath) > 0 { if len(b.WhitelistPath) > 0 && len(b.BlacklistPath) > 0 {
return nil, fmt.Errorf("using both whitelist and blacklist is invalid") return nil, fmt.Errorf("using both whitelist and blacklist is invalid")
} }
var err error var err error
dirLister := &directory{ lst := &directory{
List: list.List{ List: list.List{
Hashes: sync.Map{}, Hashes: sync.Map{},
Invert: len(b.WhitelistPath) == 0, Invert: len(b.WhitelistPath) == 0,
}, },
files: sync.Map{},
root: b.WhitelistPath,
watcher: nil, watcher: nil,
} }
if dirLister.Invert { dir := b.WhitelistPath
dirLister.root = b.BlacklistPath if lst.Invert {
dir = b.BlacklistPath
} }
var w *fsnotify.Watcher var w *dirwatch.Instance
if w, err = fsnotify.NewWatcher(); err != nil { w, err = dirwatch.New(dir)
return nil, fmt.Errorf("unable to initialize fsnotify mechanism") if w, err = dirwatch.New(dir); err != nil {
return nil, fmt.Errorf("unable to initialize directory watch")
} }
if dirContent, err := os.ReadDir(dirLister.root); err != nil { lst.watcher = w
return nil, err
} else {
for _, f := range dirContent {
if !f.IsDir() {
if err = dirLister.processFile(f.Name(), false); err != nil {
log.Warn(err)
}
}
}
}
if err = w.Add(dirLister.root); err != nil {
_ = w.Close()
dirLister = nil
}
return dirLister, err
}
func (d *directory) watch() {
go func() { go func() {
for err := range d.watcher.Errors { for event := range lst.watcher.Events {
log.Error(err) switch event.Change {
case dirwatch.Added:
lst.Hashes.Store(event.InfoHash, list.DUMMY)
case dirwatch.Removed:
lst.Hashes.Delete(event.InfoHash)
}
} }
}() }()
go func() { return lst, err
for event := range d.watcher.Events {
log.Debug(event.String())
//todo: implement event type parsing
}
}()
}
func (d *directory) processFile(name string, delete bool) error {
fullName := filepath.Join(d.root, name)
if delete {
if hash, found := d.files.Load(fullName); found{
d.Hashes.Delete(hash)
}
} else {
var hashBytes []byte
info := bittorrent.InfoHashFromBytes(hashBytes)
d.files.Store(fullName, info)
d.Hashes.Store(info, list.DUMMY)
}
return nil
} }
type directory struct { type directory struct {
list.List list.List
files sync.Map watcher *dirwatch.Instance
root string
watcher *fsnotify.Watcher
} }
func (d *directory) Stop() stop.Result { func (d *directory) Stop() stop.Result {
ch := make(stop.Channel) d.watcher.Close()
go ch.Done(d.watcher.Close()) return stop.AlreadyStopped
return ch.Result()
} }

View File

@@ -10,29 +10,31 @@ import (
) )
func init() { func init() {
container.Register("list", Builder{}) container.Register("list", func() container.Configuration {
return Config{}
})
} }
type Builder struct { type Config struct {
Whitelist []string `yaml:"whitelist"` Whitelist []string `yaml:"whitelist"`
Blacklist []string `yaml:"blacklist"` Blacklist []string `yaml:"blacklist"`
} }
var DUMMY struct{} var DUMMY struct{}
func (b Builder) New() (container.Container, error) { func (c Config) Build() (container.Container, error) {
if len(b.Whitelist) > 0 && len(b.Blacklist) > 0 { if len(c.Whitelist) > 0 && len(c.Blacklist) > 0 {
return nil, fmt.Errorf("using both whitelist and blacklist is invalid") return nil, fmt.Errorf("using both whitelist and blacklist is invalid")
} }
l := &List{ l := &List{
Hashes: sync.Map{}, Hashes: sync.Map{},
Invert: len(b.Whitelist) == 0, Invert: len(c.Whitelist) == 0,
} }
hashList := b.Whitelist hashList := c.Whitelist
if l.Invert { if l.Invert {
l.Invert = true l.Invert = true
hashList = b.Blacklist hashList = c.Blacklist
} }
for _, hashString := range hashList { for _, hashString := range hashList {

View File

@@ -4,6 +4,8 @@ import (
"context" "context"
"encoding/hex" "encoding/hex"
"fmt" "fmt"
"github.com/chihaya/chihaya/middleware"
"gopkg.in/yaml.v2"
"testing" "testing"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
@@ -12,38 +14,50 @@ import (
) )
var cases = []struct { var cases = []struct {
cfg Config cfg middleware.Config
ih string ih string
approved bool approved bool
}{ }{
// Infohash is whitelisted // Infohash is whitelisted
{ {
Config{ middleware.Config{
Whitelist: []string{"3532cf2d327fad8448c075b4cb42c8136964a435"}, Name: "list",
Options: map[string]interface{}{
"Whitelist": []string{"3532cf2d327fad8448c075b4cb42c8136964a435"},
},
}, },
"3532cf2d327fad8448c075b4cb42c8136964a435", "3532cf2d327fad8448c075b4cb42c8136964a435",
true, true,
}, },
// Infohash is not whitelisted // Infohash is not whitelisted
{ {
Config{ middleware.Config{
Whitelist: []string{"3532cf2d327fad8448c075b4cb42c8136964a435"}, Name: "list",
Options: map[string]interface{}{
"Whitelist": []string{"3532cf2d327fad8448c075b4cb42c8136964a435"},
},
}, },
"4532cf2d327fad8448c075b4cb42c8136964a435", "4532cf2d327fad8448c075b4cb42c8136964a435",
false, false,
}, },
// Infohash is not blacklisted // Infohash is not blacklisted
{ {
Config{ middleware.Config{
Blacklist: []string{"3532cf2d327fad8448c075b4cb42c8136964a435"}, Name: "list",
Options: map[string]interface{}{
"Blacklist": []string{"3532cf2d327fad8448c075b4cb42c8136964a435"},
},
}, },
"4532cf2d327fad8448c075b4cb42c8136964a435", "4532cf2d327fad8448c075b4cb42c8136964a435",
true, true,
}, },
// Infohash is blacklisted // Infohash is blacklisted
{ {
Config{ middleware.Config{
Blacklist: []string{"3532cf2d327fad8448c075b4cb42c8136964a435"}, Name: "list",
Options: map[string]interface{}{
"Blacklist": []string{"3532cf2d327fad8448c075b4cb42c8136964a435"},
},
}, },
"3532cf2d327fad8448c075b4cb42c8136964a435", "3532cf2d327fad8448c075b4cb42c8136964a435",
false, false,
@@ -53,7 +67,10 @@ var cases = []struct {
func TestHandleAnnounce(t *testing.T) { func TestHandleAnnounce(t *testing.T) {
for _, tt := range cases { for _, tt := range cases {
t.Run(fmt.Sprintf("testing hash %s", tt.ih), func(t *testing.T) { t.Run(fmt.Sprintf("testing hash %s", tt.ih), func(t *testing.T) {
h, err := NewHook(tt.cfg) d := driver{}
cfg, err := yaml.Marshal(tt)
require.Nil(t, err)
h, err := d.NewHook(cfg)
require.Nil(t, err) require.Nil(t, err)
ctx := context.Background() ctx := context.Background()