feat: auto-refresh non-IP module updates and add full project manual
CI / changes (push) Successful in 7s
CI / openapi (push) Has been skipped
CI / go (push) Successful in 38s
CI / docker-web (deploy/docker/evobgp-web/Dockerfile, , evobgp-web) (push) Successful in 1m4s
CI / docker-web (deploy/docker/evobgp-web/Dockerfile, evobgp-all, evobgp-web-all) (push) Successful in 1m3s
CI / docker-bird (push) Has been skipped
CI / bird2 (push) Successful in 16s
CI / docker-go-prime (push) Successful in 23s
CI / docker-go (deploy/docker/evobgp-agent/Dockerfile, , evobgp-agent) (push) Successful in 1m1s
CI / docker-go (evobgp-all, 1, deploy/docker/gobinary/Dockerfile, , evobgp-all) (push) Successful in 2m7s
CI / docker-go (evobgp-api, 1, deploy/docker/gobinary/Dockerfile, , evobgp-api) (push) Successful in 1m21s
CI / docker-go (evobgp-deploy, 0, deploy/docker/gobinary/Dockerfile, , evobgp-deploy) (push) Successful in 1m18s
CI / docker-go (evobgp-ingest, 0, deploy/docker/gobinary/Dockerfile, , evobgp-ingest) (push) Successful in 1m22s
CI / docker-go (evobgp-node, 0, deploy/docker/gobinary/Dockerfile, , evobgp-node) (push) Successful in 1m5s
CI / docker-go (evobgp-render, 0, deploy/docker/gobinary/Dockerfile, , evobgp-render) (push) Successful in 1m28s
CI / docker-go (evobgp-scheduler, 0, deploy/docker/gobinary/Dockerfile, , evobgp-scheduler) (push) Successful in 1m19s
CI / changes (push) Successful in 7s
CI / openapi (push) Has been skipped
CI / go (push) Successful in 38s
CI / docker-web (deploy/docker/evobgp-web/Dockerfile, , evobgp-web) (push) Successful in 1m4s
CI / docker-web (deploy/docker/evobgp-web/Dockerfile, evobgp-all, evobgp-web-all) (push) Successful in 1m3s
CI / docker-bird (push) Has been skipped
CI / bird2 (push) Successful in 16s
CI / docker-go-prime (push) Successful in 23s
CI / docker-go (deploy/docker/evobgp-agent/Dockerfile, , evobgp-agent) (push) Successful in 1m1s
CI / docker-go (evobgp-all, 1, deploy/docker/gobinary/Dockerfile, , evobgp-all) (push) Successful in 2m7s
CI / docker-go (evobgp-api, 1, deploy/docker/gobinary/Dockerfile, , evobgp-api) (push) Successful in 1m21s
CI / docker-go (evobgp-deploy, 0, deploy/docker/gobinary/Dockerfile, , evobgp-deploy) (push) Successful in 1m18s
CI / docker-go (evobgp-ingest, 0, deploy/docker/gobinary/Dockerfile, , evobgp-ingest) (push) Successful in 1m22s
CI / docker-go (evobgp-node, 0, deploy/docker/gobinary/Dockerfile, , evobgp-node) (push) Successful in 1m5s
CI / docker-go (evobgp-render, 0, deploy/docker/gobinary/Dockerfile, , evobgp-render) (push) Successful in 1m28s
CI / docker-go (evobgp-scheduler, 0, deploy/docker/gobinary/Dockerfile, , evobgp-scheduler) (push) Successful in 1m19s
Queue module refresh jobs after AS, domain, and CDN source mutations (including CSV imports) to keep revisions current across all source types, and introduce a comprehensive project manual covering runtime modules, flows, and API operations. Made-with: Cursor
This commit is contained in:
@@ -254,11 +254,13 @@ func (s *Server) handlePostCDNSource(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.CreateCDNSource(a.TenantID, r.PathValue("module_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.CreateCDNSource(a.TenantID, mid, &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "cdn_source_create")
|
||||
writeJSON(w, http.StatusCreated, cdnSourceJSON(x))
|
||||
}
|
||||
|
||||
@@ -272,11 +274,13 @@ func (s *Server) handlePatchCDNSource(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.UpdateCDNSource(a.TenantID, r.PathValue("module_id"), r.PathValue("source_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.UpdateCDNSource(a.TenantID, mid, r.PathValue("source_id"), &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "cdn_source_patch")
|
||||
writeJSON(w, http.StatusOK, cdnSourceJSON(x))
|
||||
}
|
||||
|
||||
@@ -285,10 +289,12 @@ func (s *Server) handleDeleteCDNSource(w http.ResponseWriter, r *http.Request) {
|
||||
if !ok || !s.requireAtLeast(w, a, "editor") {
|
||||
return
|
||||
}
|
||||
if err := s.store.DeleteCDNSource(a.TenantID, r.PathValue("module_id"), r.PathValue("source_id")); err != nil {
|
||||
mid := r.PathValue("module_id")
|
||||
if err := s.store.DeleteCDNSource(a.TenantID, mid, r.PathValue("source_id")); err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "cdn_source_delete")
|
||||
w.WriteHeader(http.StatusNoContent)
|
||||
}
|
||||
|
||||
@@ -344,11 +350,13 @@ func (s *Server) handlePostAS(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.CreateASEntry(a.TenantID, r.PathValue("module_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.CreateASEntry(a.TenantID, mid, &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "as_entry_create")
|
||||
writeJSON(w, http.StatusCreated, asEntryJSON(x))
|
||||
}
|
||||
|
||||
@@ -362,11 +370,13 @@ func (s *Server) handlePatchAS(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.UpdateASEntry(a.TenantID, r.PathValue("module_id"), r.PathValue("entry_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.UpdateASEntry(a.TenantID, mid, r.PathValue("entry_id"), &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "as_entry_patch")
|
||||
writeJSON(w, http.StatusOK, asEntryJSON(x))
|
||||
}
|
||||
|
||||
@@ -375,10 +385,12 @@ func (s *Server) handleDeleteAS(w http.ResponseWriter, r *http.Request) {
|
||||
if !ok || !s.requireAtLeast(w, a, "editor") {
|
||||
return
|
||||
}
|
||||
if err := s.store.DeleteASEntry(a.TenantID, r.PathValue("module_id"), r.PathValue("entry_id")); err != nil {
|
||||
mid := r.PathValue("module_id")
|
||||
if err := s.store.DeleteASEntry(a.TenantID, mid, r.PathValue("entry_id")); err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "as_entry_delete")
|
||||
w.WriteHeader(http.StatusNoContent)
|
||||
}
|
||||
|
||||
@@ -419,11 +431,13 @@ func (s *Server) handlePostDomain(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.CreateDomainEntry(a.TenantID, r.PathValue("module_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.CreateDomainEntry(a.TenantID, mid, &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "domain_entry_create")
|
||||
writeJSON(w, http.StatusCreated, domainEntryJSON(x))
|
||||
}
|
||||
|
||||
@@ -437,11 +451,13 @@ func (s *Server) handlePatchDomain(w http.ResponseWriter, r *http.Request) {
|
||||
writeProblem(w, http.StatusBadRequest, "Bad Request", "invalid json")
|
||||
return
|
||||
}
|
||||
x, err := s.store.UpdateDomainEntry(a.TenantID, r.PathValue("module_id"), r.PathValue("entry_id"), &body)
|
||||
mid := r.PathValue("module_id")
|
||||
x, err := s.store.UpdateDomainEntry(a.TenantID, mid, r.PathValue("entry_id"), &body)
|
||||
if err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "domain_entry_patch")
|
||||
writeJSON(w, http.StatusOK, domainEntryJSON(x))
|
||||
}
|
||||
|
||||
@@ -450,10 +466,12 @@ func (s *Server) handleDeleteDomain(w http.ResponseWriter, r *http.Request) {
|
||||
if !ok || !s.requireAtLeast(w, a, "editor") {
|
||||
return
|
||||
}
|
||||
if err := s.store.DeleteDomainEntry(a.TenantID, r.PathValue("module_id"), r.PathValue("entry_id")); err != nil {
|
||||
mid := r.PathValue("module_id")
|
||||
if err := s.store.DeleteDomainEntry(a.TenantID, mid, r.PathValue("entry_id")); err != nil {
|
||||
writeStoreErr(w, err)
|
||||
return
|
||||
}
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, mid, "domain_entry_delete")
|
||||
w.WriteHeader(http.StatusNoContent)
|
||||
}
|
||||
|
||||
@@ -713,6 +731,9 @@ func (s *Server) handleImportModuleEntriesCSV(w http.ResponseWriter, r *http.Req
|
||||
}
|
||||
imported++
|
||||
}
|
||||
if imported > 0 {
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, moduleID, "as_entry_import_csv")
|
||||
}
|
||||
case "DOMAINS":
|
||||
for i := start; i < len(rows); i++ {
|
||||
rec := rows[i]
|
||||
@@ -740,6 +761,9 @@ func (s *Server) handleImportModuleEntriesCSV(w http.ResponseWriter, r *http.Req
|
||||
}
|
||||
imported++
|
||||
}
|
||||
if imported > 0 {
|
||||
s.enqueueModuleRefreshIfEnabled(a.TenantID, moduleID, "domain_entry_import_csv")
|
||||
}
|
||||
case "IP_RANGES":
|
||||
for i := start; i < len(rows); i++ {
|
||||
rec := rows[i]
|
||||
|
||||
Reference in New Issue
Block a user