verstak/internal/core/plugins/manager_test.go

163 lines
3.7 KiB
Go

package plugins
import (
"os"
"path/filepath"
"testing"
)
type fsDir struct {
name string
files map[string][]byte
dirs map[string]*fsDir
}
func setupPluginDir(t *testing.T, plugins map[string]*fsDir) string {
t.Helper()
base := filepath.Join(t.TempDir(), ".verstak", "plugins")
os.MkdirAll(base, 0o750)
for name, plugin := range plugins {
pDir := filepath.Join(base, name)
os.MkdirAll(pDir, 0o750)
for fname, content := range plugin.files {
os.WriteFile(filepath.Join(pDir, fname), content, 0o640)
}
for dname, d := range plugin.dirs {
dDir := filepath.Join(pDir, dname)
os.MkdirAll(dDir, 0o750)
for fname, content := range d.files {
os.WriteFile(filepath.Join(dDir, fname), content, 0o640)
}
}
}
return filepath.Dir(filepath.Dir(base)) // vault root
}
func TestDiscover(t *testing.T) {
root := setupPluginDir(t, map[string]*fsDir{
"client": {
files: map[string][]byte{
"plugin.json": []byte(`{
"name": "client",
"version": "1.0.0",
"description": "Client template",
"templates": ["client"]
}`),
},
dirs: map[string]*fsDir{
"templates": {
files: map[string][]byte{
"client.json": []byte(`{
"name": "Клиент",
"root_type": "case",
"tree": [
{"type": "folder", "title": "Документы"},
{"type": "note", "title": "Overview"},
{"type": "folder", "title": "Переписка"}
]
}`),
},
},
},
},
"empty-dir": {},
"no-json": {
files: map[string][]byte{"README.md": []byte("hi")},
},
})
mgr := NewManager(root)
mgr.Discover()
plugins := mgr.Plugins()
if len(plugins) != 1 {
t.Errorf("plugins = %d, want 1", len(plugins))
}
if len(plugins) > 0 && plugins[0].Meta.Name != "client" {
t.Errorf("plugin name = %q", plugins[0].Meta.Name)
}
// Templates.
tmpls := mgr.Templates()
if len(tmpls) != 1 {
t.Errorf("templates = %d, want 1", len(tmpls))
}
if len(tmpls) > 0 {
tmpl := tmpls[0]
if tmpl.Name != "Клиент" {
t.Errorf("template name = %q", tmpl.Name)
}
if tmpl.Plugin != "client" {
t.Errorf("template plugin = %q", tmpl.Plugin)
}
if len(tmpl.Tree) != 3 {
t.Errorf("template tree = %d items, want 3", len(tmpl.Tree))
}
}
}
func TestEnableDisable(t *testing.T) {
root := setupPluginDir(t, map[string]*fsDir{
"plugin-a": {
files: map[string][]byte{
"plugin.json": []byte(`{"name": "a", "version": "1.0"}`),
},
},
"plugin-b": {
files: map[string][]byte{
"plugin.json": []byte(`{"name": "b", "version": "1.0"}`),
},
},
})
mgr := NewManager(root)
mgr.Discover()
if len(mgr.Plugins()) != 2 {
t.Fatalf("plugins = %d, want 2", len(mgr.Plugins()))
}
// All active by default.
if len(mgr.Active()) != 2 {
t.Errorf("active = %d, want 2", len(mgr.Active()))
}
// Disable one.
mgr.Disable("a")
if len(mgr.Active()) != 1 {
t.Errorf("active after disable = %d, want 1", len(mgr.Active()))
}
// Re-enable.
mgr.Enable("a")
if len(mgr.Active()) != 2 {
t.Errorf("active after enable = %d, want 2", len(mgr.Active()))
}
}
func TestActiveNames(t *testing.T) {
root := setupPluginDir(t, map[string]*fsDir{
"p1": {files: map[string][]byte{"plugin.json": []byte(`{"name":"p1"}`)}},
"p2": {files: map[string][]byte{"plugin.json": []byte(`{"name":"p2"}`)}},
})
mgr := NewManager(root)
mgr.Discover()
mgr.Disable("p1")
names := mgr.ActiveNames()
if len(names) != 1 || names[0] != "p2" {
t.Errorf("active names = %v, want [p2]", names)
}
}
func TestNoPluginsDir(t *testing.T) {
root := t.TempDir()
mgr := NewManager(root)
mgr.Discover() // Should not crash.
if len(mgr.Plugins()) != 0 {
t.Errorf("plugins = %d, want 0", len(mgr.Plugins()))
}
}