func (m *Mux) Mount(path string, sub *Mux) {
	if !isValidPath(path) {
		panic("res: invalid path")
	}
	if sub.parent != nil {
		panic("res: already mounted")
	}
	if sub.s != nil {
		panic("res: already registered to a service")
	}
	spath := mergePattern(path, sub.path)
	if spath == "" {
		panic("res: attempting to mount to root")
	}
	n, _ := m.fetch(spath, sub.root)
	if n != sub.root {
		panic("res: attempting to mount to existing pattern: " + mergePattern(m.path, spath))
	}
	sub.mountp = path
	sub.root.mounted = true
	sub.parent = m
	sub.callOnRegister()
}
Mount attaches another Mux at a given path.
When mounting, any path set on the sub Mux will be suffixed to the path.
package res
import (
	"errors"
	"fmt"
	"strings"
)
const (
	pmark = '$'
	pwild = '*'
	fwild = '>'
	btsep = '.'
)
const invalidPattern = "res: invalid pattern"
type Mux struct {
	path   string
	root   *node
	parent *Mux
	mountp string
	s      *Service  
}
type Event struct {
	Name string
	Resource Resource
	NewValues map[string]interface{}
	OldValues map[string]interface{}
	Value interface{}
	Idx int
	Data interface{}
	Payload interface{}
}
type Match struct {
	Handler   Handler
	Listeners []func(*Event)
	Params    map[string]string
	Group     string
}
type regHandler struct {
	Handler
	group group
}
type node struct {
	hs        *regHandler  
	params    []pathParam  
	nodes     map[string]*node
	param     *node
	wild      *node  
	mounted   bool
	listeners []func(*Event)
}
type pathParam struct {
	name string  
	idx  int     
}
type nodeMatch struct {
	n        *node
	params   map[string]string
	mountIdx int
}
func NewMux(path string) *Mux {
	if !isValidPath(path) {
		panic("res: invalid path")
	}
	return &Mux{
		path: path,
		root: &node{},
	}
}
func (m *Mux) Path() string {
	return m.path
}
func (m *Mux) FullPath() string {
	if m.parent == nil {
		return m.path
	}
	return mergePattern(mergePattern(m.parent.FullPath(), m.mountp), m.path)
}
func (m *Mux) Register(s *Service) {
	if m.parent != nil {
		panic("res: already mounted")
	}
	if m.s != nil {
		panic("res: already registered to a service")
	}
	m.s = s
	m.callOnRegister()
}
func (m *Mux) registeredService() *Service {
	if m.parent != nil {
		return m.parent.registeredService()
	}
	return m.s
}
func (m *Mux) callOnRegister() {
	s := m.registeredService()
	if s == nil {
		return
	}
	fp := m.FullPath()
	traverse(m.root, make([]string, 0, 32), 0, func(n *node, path []string, mountIdx int) {
		if n.hs != nil && n.hs.OnRegister != nil {
			n.hs.OnRegister(s, Pattern(mergePattern(fp, pathSliceToString(n, path, mountIdx))), n.hs.Handler)
		}
	})
}
func (m *Mux) Handle(pattern string, hf ...Option) {
	var h Handler
	for _, f := range hf {
		f.SetOption(&h)
	}
	m.AddHandler(pattern, h)
}
func (m *Mux) AddHandler(pattern string, hs Handler) {
	h := regHandler{
		Handler: hs,
		group:   parseGroup(hs.Group, pattern),
	}
	m.add(pattern, &h)
}
func (m *Mux) AddListener(pattern string, handler func(*Event)) {
	if handler == nil {
		panic("nil event handler")
	}
	n, params := m.fetch(pattern, nil)
	setAndValidateParams(n, params)
	n.listeners = append(n.listeners, handler)
}