package main

import (
	"crypto/tls"
	"flag"
	"fmt"
	"net/http"
	"regexp"
	"strings"
	"sync"

	"github.com/golang/glog"
	ldap "gopkg.in/ldap.v3"

	"code.hackerspace.pl/hscloud/go/mirko"
)

type server struct {
	mu   sync.Mutex
	ldap *ldap.Conn
}

var reURL = regexp.MustCompile(`^/([a-zA-Z0-9\-_]+)/([a-zA-Z0-9\-_]+)$`)

func (s *server) handle(rw http.ResponseWriter, req *http.Request) {
	if req.Method != "GET" {
		rw.WriteHeader(http.StatusMethodNotAllowed)
		fmt.Fprintf(rw, "method not allowed")
		return
	}

	reqParts := reURL.FindStringSubmatch(req.URL.Path)
	if len(reqParts) != 3 {
		fmt.Fprintf(rw, "usage: GET /capability/user, eg. GET /staff/q3k")
		return
	}
	c := reqParts[1]
	u := reqParts[2]

	res, err := s.capacify(c, u)
	l := ""
	r := ""
	switch {
	case err != nil:
		l = fmt.Sprintf("%v", err)
		r = "ERROR"
		rw.WriteHeader(500)
	case res:
		l = "yes"
		r = "YES"
		rw.WriteHeader(200)
	default:
		l = "no"
		r = "NO"
		rw.WriteHeader(401)
	}
	glog.Infof("%s: GET /%s/%s: %s", req.RemoteAddr, c, u, l)
	fmt.Fprintf(rw, "%s", r)
}

func (s *server) capacify(c, u string) (bool, error) {
	switch c {
	case "xmpp":
		return s.checkLdap(u, "cn=xmpp-users,ou=Group,dc=hackerspace,dc=pl")
	case "wiki_admin":
		return s.checkLdap(u, "cn=admin,dc=wiki,dc=hackerspace,dc=pl")
	case "twitter":
		return s.checkLdap(u, "cn=twitter,ou=Group,dc=hackerspace,dc=pl")
	case "lulzbot_access":
		return s.checkLdap(u, "cn=lulzbot-access,ou=Group,dc=hackerspace,dc=pl")
	case "staff":
		return s.checkLdap(u, "cn=staff,ou=Group,dc=hackerspace,dc=pl")
	case "kasownik_access":
		return s.checkLdap(u, "cn=kasownik-access,ou=Group,dc=hackerspace,dc=pl")
	case "starving":
		return s.checkLdap(u, "cn=starving,ou=Group,dc=hackerspace,dc=pl")
	case "fatty":
		return s.checkLdap(u, "cn=fatty,ou=Group,dc=hackerspace,dc=pl")
	case "member":
		// Where we're going we don't need applicatives.
		res, err := s.capacify("fatty", u)
		if err != nil {
			return false, err
		}
		if res {
			return true, nil
		}
		return s.capacify("starving", u)
	default:
		return false, nil
	}
}

func (s *server) getLdap() (*ldap.Conn, error) {
	s.mu.Lock()
	defer s.mu.Unlock()
	if s.ldap == nil {
		lconn, err := connectLdap()
		if err != nil {
			return nil, err
		}
		s.ldap = lconn
	}
	return s.ldap, nil
}

func (s *server) closeLdap() {
	s.mu.Lock()
	defer s.mu.Unlock()
	if s.ldap != nil {
		s.ldap.Close()
		s.ldap = nil
	}
}

func (s *server) checkLdap(u, dn string) (bool, error) {
	lconn, err := s.getLdap()
	if err != nil {
		return false, err
	}

	if strings.ContainsAny(u, `\#+<>,;"=`) {
		return false, nil
	}
	filter := fmt.Sprintf("(uniqueMember=uid=%s,ou=People,dc=hackerspace,dc=pl)", u)
	search := ldap.NewSearchRequest(
		dn,
		ldap.ScopeWholeSubtree, ldap.NeverDerefAliases, 0, 0, false,
		filter, []string{"dn", "cn"}, nil,
	)
	sr, err := lconn.Search(search)
	if err != nil {
		s.closeLdap()
		return false, fmt.Errorf("search failed: %w", err)
	}

	for _, entry := range sr.Entries {
		if entry.DN == dn {
			return true, nil
		}
	}

	return false, nil
}

func init() {
	flag.Set("logtostderr", "true")
}

var (
	flagLDAPServer string
	flagLDAPBindDN string
	flagLDAPBindPW string
	flagListen     string
)

func connectLdap() (*ldap.Conn, error) {
	tlsConfig := &tls.Config{}
	lconn, err := ldap.DialTLS("tcp", flagLDAPServer, tlsConfig)
	if err != nil {
		return nil, fmt.Errorf("ldap.DialTLS: %v", err)
	}

	if err := lconn.Bind(flagLDAPBindDN, flagLDAPBindPW); err != nil {
		lconn.Close()
		return nil, fmt.Errorf("ldap.Bind: %v", err)
	}
	return lconn, nil
}

func main() {
	flag.StringVar(&flagListen, "api_listen", ":2137", "Address to listen on for API requests")
	flag.StringVar(&flagLDAPServer, "ldap_server", "ldap.hackerspace.pl:636", "LDAP server address")
	flag.StringVar(&flagLDAPBindDN, "ldap_bind_dn", "cn=capacifier,ou=Services,dc=hackerspace,dc=pl", "LDAP bind DN")
	flag.StringVar(&flagLDAPBindPW, "ldap_bind_pw", "", "LDAP bind password")
	flag.Parse()

	if flagLDAPBindPW == "" {
		glog.Exitf("-ldap_bind_pw must be set")
	}

	m := mirko.New()
	if err := m.Listen(); err != nil {
		glog.Exitf("Listen(): %v", err)
	}

	s := &server{}
	mux := http.NewServeMux()
	mux.HandleFunc("/", s.handle)

	go func() {
		glog.Infof("API Listening on %s", flagListen)
		if err := http.ListenAndServe(flagListen, mux); err != nil {
			glog.Exitf("API Listen failed: %v", err)
		}
	}()

	if err := m.Serve(); err != nil {
		glog.Exitf("Serve(): %v", err)
	}

	<-m.Done()
}
