maatma: interface for domain delegation (mostly)
This commit is contained in:
parent
5f83c5cd2c
commit
7ebbf79bda
5 changed files with 406 additions and 23 deletions
|
|
@ -1,6 +1,7 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"log"
|
||||
|
|
@ -12,6 +13,11 @@ import (
|
|||
"github.com/julienschmidt/httprouter"
|
||||
)
|
||||
|
||||
const (
|
||||
AssociatedDomainSuffix = "adlin2020.p0m.fr"
|
||||
DelegatedDomainSuffix = "srs.p0m.fr"
|
||||
)
|
||||
|
||||
func init() {
|
||||
router.GET("/api/adomains/", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.GetAssociatedDomains(), nil
|
||||
|
|
@ -24,10 +30,56 @@ func init() {
|
|||
}))
|
||||
|
||||
router.GET("/api/ddomains/", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.GetDelegatedDomains()
|
||||
return []string{student.MyDelegatedDomain()}, nil
|
||||
}))
|
||||
router.GET("/api/ddomains/:dn", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.GetDelegatedDomain(ps.ByName("dn"))
|
||||
router.GET("/api/ddomains/:dn/", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.getRRDelegatedDomain(ps.ByName("dn"), "")
|
||||
}))
|
||||
router.GET("/api/ddomains/:dn/NS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.getRRDelegatedDomain(ps.ByName("dn"), "NS")
|
||||
}))
|
||||
router.POST("/api/ddomains/:dn/NS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
var ue Entry
|
||||
if err := json.Unmarshal(body, &ue); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return true, student.UpdateNSDelegatedDomain(ps.ByName("dn"), ue.TTL, ue.Values[0])
|
||||
}))
|
||||
router.DELETE("/api/ddomains/:dn/NS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return true, student.DeleteRRDelegatedDomain(ps.ByName("dn"), "NS")
|
||||
}))
|
||||
router.GET("/api/ddomains/:dn/GLUE", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.getRRDelegatedDomain(ps.ByName("dn"), "AAAA")
|
||||
}))
|
||||
router.POST("/api/ddomains/:dn/AAAA", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
var ue Entry
|
||||
if err := json.Unmarshal(body, &ue); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return true, student.UpdateGLUEDelegatedDomain(ps.ByName("dn"), ue.TTL, ue.Values[0])
|
||||
}))
|
||||
router.POST("/api/ddomains/:dn/GLUE", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
var ue Entry
|
||||
if err := json.Unmarshal(body, &ue); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return true, student.UpdateGLUEDelegatedDomain(ps.ByName("dn"), ue.TTL, ue.Values[0])
|
||||
}))
|
||||
router.DELETE("/api/ddomains/:dn/AAAA", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return true, student.DeleteRRDelegatedDomain(ps.ByName("dn"), "AAAA")
|
||||
}))
|
||||
router.GET("/api/ddomains/:dn/DS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return student.getRRDelegatedDomain(ps.ByName("dn"), "DS")
|
||||
}))
|
||||
router.POST("/api/ddomains/:dn/DS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
var ue Entry
|
||||
if err := json.Unmarshal(body, &ue); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return true, student.UpdateDSDelegatedDomain(ps.ByName("dn"), ue.TTL, ue.Values)
|
||||
}))
|
||||
router.DELETE("/api/ddomains/:dn/DS", apiAuthHandler(func (student Student, ps httprouter.Params, body []byte) (interface{}, error) {
|
||||
return true, student.DeleteRRDelegatedDomain(ps.ByName("dn"), "DS")
|
||||
}))
|
||||
}
|
||||
|
||||
|
|
@ -69,13 +121,13 @@ func parseKnotZoneRead(args ...string) (rr []Entry, err error) {
|
|||
}
|
||||
|
||||
func (student Student) myAssociatedDomain() (string) {
|
||||
return fmt.Sprintf("%s.adlin2020.p0m.fr.", student.Login)
|
||||
return fmt.Sprintf("%s.%s.", student.Login, AssociatedDomainSuffix)
|
||||
}
|
||||
|
||||
func (student Student) GetAssociatedDomains() (ds []string) {
|
||||
studentDomain := student.myAssociatedDomain()
|
||||
|
||||
if _, err := parseKnotZoneRead("adlin2020.p0m.fr", studentDomain); err == nil {
|
||||
if _, err := parseKnotZoneRead(AssociatedDomainSuffix, studentDomain); err == nil {
|
||||
ds = append(ds, studentDomain)
|
||||
}
|
||||
|
||||
|
|
@ -95,7 +147,7 @@ func (student Student) GetAssociatedDomain(dn string) (rrs []Entry, err error) {
|
|||
err = errors.New(fmt.Sprintf("Unable to find domain %q.", dn))
|
||||
}
|
||||
|
||||
rrs, err = parseKnotZoneRead("adlin2020.p0m.fr", dn)
|
||||
rrs, err = parseKnotZoneRead(AssociatedDomainSuffix, dn)
|
||||
|
||||
return
|
||||
}
|
||||
|
|
@ -103,16 +155,17 @@ func (student Student) GetAssociatedDomain(dn string) (rrs []Entry, err error) {
|
|||
func (student Student) AddAssociatedDomains() (err error) {
|
||||
for _, d := range []string{student.myAssociatedDomain()} {
|
||||
for _, cmd := range [][]string{
|
||||
[]string{"zone-begin", "adlin2020.p0m.fr"},
|
||||
[]string{"zone-set", "adlin2020.p0m.fr", d, "900", "A", "82.64.31.248"},
|
||||
[]string{"zone-set", "adlin2020.p0m.fr", d, "900", "AAAA", studentIP(student.Id) + "1"},
|
||||
[]string{"zone-commit", "adlin2020.p0m.fr"},
|
||||
[]string{"zone-begin", AssociatedDomainSuffix},
|
||||
[]string{"zone-set", AssociatedDomainSuffix, d, "900", "A", "82.64.31.248"},
|
||||
[]string{"zone-set", AssociatedDomainSuffix, d, "900", "AAAA", studentIP(student.Id) + "1"},
|
||||
[]string{"zone-commit", AssociatedDomainSuffix},
|
||||
} {
|
||||
var out []byte
|
||||
out, err = runKnotc(cmd...)
|
||||
if err != nil {
|
||||
err = errors.New(fmt.Sprintf("An error occurs on command '%s': %s", strings.Join(cmd, " "), err.Error()))
|
||||
log.Println(string(out))
|
||||
runKnotc("zone-abort", AssociatedDomainSuffix)
|
||||
return
|
||||
}
|
||||
}
|
||||
|
|
@ -122,14 +175,137 @@ func (student Student) AddAssociatedDomains() (err error) {
|
|||
}
|
||||
|
||||
|
||||
type DelegatedDomain struct {
|
||||
|
||||
func (student Student) MyDelegatedDomain() (string) {
|
||||
return fmt.Sprintf("%s.%s.", student.Login, DelegatedDomainSuffix)
|
||||
}
|
||||
|
||||
func (student Student) GetDelegatedDomain(dn string) (d DelegatedDomain, err error) {
|
||||
func (student Student) getRRDelegatedDomain(dn string, rr string) (rrs []Entry, err error) {
|
||||
domains := []string{student.MyDelegatedDomain()}
|
||||
found := false
|
||||
for _, d := range domains {
|
||||
if d == dn {
|
||||
found = true
|
||||
}
|
||||
}
|
||||
|
||||
if !found {
|
||||
err = errors.New(fmt.Sprintf("Unable to find domain %q.", dn))
|
||||
}
|
||||
|
||||
rrs, err = parseKnotZoneRead(DelegatedDomainSuffix, dn, rr)
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (student Student) GetDelegatedDomains() (ds []DelegatedDomain, err error) {
|
||||
func (student Student) UpdateNSDelegatedDomain(dn string, ttl uint64, ns string) (err error) {
|
||||
for _, d := range []string{student.MyDelegatedDomain()} {
|
||||
for _, cmd := range [][]string{
|
||||
[]string{"zone-begin", DelegatedDomainSuffix},
|
||||
[]string{"zone-unset", DelegatedDomainSuffix, d, "NS"},
|
||||
[]string{"zone-set", DelegatedDomainSuffix, d, fmt.Sprintf("%d", ttl), "NS", ns},
|
||||
[]string{"zone-commit", DelegatedDomainSuffix},
|
||||
} {
|
||||
var out []byte
|
||||
out, err = runKnotc(cmd...)
|
||||
if err != nil && cmd[0] != "zone-unset" {
|
||||
err = errors.New(fmt.Sprintf("An error occurs on command '%s': %s", strings.Join(cmd, " "), err.Error()))
|
||||
log.Println(string(out))
|
||||
runKnotc("zone-abort", DelegatedDomainSuffix)
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
func (student Student) UpdateGLUEDelegatedDomain(dn string, ttl uint64, aaaa string) (err error) {
|
||||
domains := []string{student.MyDelegatedDomain()}
|
||||
found := false
|
||||
for _, d := range domains {
|
||||
if strings.HasSuffix(dn, d) {
|
||||
found = true
|
||||
}
|
||||
}
|
||||
|
||||
if !found {
|
||||
err = errors.New(fmt.Sprintf("Unable to find domain %q in your whitelist.", dn))
|
||||
return
|
||||
}
|
||||
|
||||
for _, cmd := range [][]string{
|
||||
[]string{"zone-begin", DelegatedDomainSuffix},
|
||||
[]string{"zone-unset", DelegatedDomainSuffix, student.MyDelegatedDomain(), "AAAA"},
|
||||
[]string{"zone-unset", DelegatedDomainSuffix, dn, "AAAA"},
|
||||
[]string{"zone-set", DelegatedDomainSuffix, dn, fmt.Sprintf("%d", ttl), "AAAA", aaaa},
|
||||
[]string{"zone-commit", DelegatedDomainSuffix},
|
||||
} {
|
||||
var out []byte
|
||||
out, err = runKnotc(cmd...)
|
||||
if err != nil && cmd[0] != "zone-unset" {
|
||||
err = errors.New(fmt.Sprintf("An error occurs on command '%s': %s", strings.Join(cmd, " "), err.Error()))
|
||||
log.Println(string(out))
|
||||
runKnotc("zone-abort", DelegatedDomainSuffix)
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
func (student Student) UpdateDSDelegatedDomain(dn string, ttl uint64, ds []string) (err error) {
|
||||
for _, d := range []string{student.MyDelegatedDomain()} {
|
||||
for _, cmd := range [][]string{
|
||||
[]string{"zone-begin", DelegatedDomainSuffix},
|
||||
[]string{"zone-unset", DelegatedDomainSuffix, d, "DS"},
|
||||
[]string{"zone-set", DelegatedDomainSuffix, d, fmt.Sprintf("%d", ttl), "DS", strings.Join(ds, " ")},
|
||||
[]string{"zone-commit", DelegatedDomainSuffix},
|
||||
} {
|
||||
var out []byte
|
||||
out, err = runKnotc(cmd...)
|
||||
if err != nil && cmd[0] != "zone-unset" {
|
||||
err = errors.New(fmt.Sprintf("An error occurs on command '%s': %s", strings.Join(cmd, " "), err.Error()))
|
||||
log.Println(string(out))
|
||||
runKnotc("zone-abort", DelegatedDomainSuffix)
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
|
||||
func (student Student) DeleteRRDelegatedDomain(dn string, rr string) (err error) {
|
||||
domains := []string{student.MyDelegatedDomain()}
|
||||
found := false
|
||||
for _, d := range domains {
|
||||
if strings.HasSuffix(dn, d) {
|
||||
found = true
|
||||
}
|
||||
}
|
||||
|
||||
if !found {
|
||||
err = errors.New(fmt.Sprintf("Unable to find domain %q in your whitelist.", dn))
|
||||
return
|
||||
}
|
||||
|
||||
for _, cmd := range [][]string{
|
||||
[]string{"zone-begin", DelegatedDomainSuffix},
|
||||
[]string{"zone-unset", DelegatedDomainSuffix, dn, rr},
|
||||
[]string{"zone-commit", DelegatedDomainSuffix},
|
||||
} {
|
||||
var out []byte
|
||||
out, err = runKnotc(cmd...)
|
||||
if err != nil {
|
||||
err = errors.New(fmt.Sprintf("An error occurs on command '%s': %s", strings.Join(cmd, " "), err.Error()))
|
||||
log.Println(string(out))
|
||||
runKnotc("zone-abort", DelegatedDomainSuffix)
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
|
|
|||
Reference in a new issue