Compare commits

...
3 Commits
7 changed files with 55 additions and 20 deletions
+1 -4
View File
@@ -220,7 +220,6 @@ func main() {
server.SetDNSSettings(persisted.DNSEnabled, persisted.DNSUpstream, persisted.DNSBindAddr)
server.SetSpotifyConfig(config.spotifyClientID, config.spotifyClientSecret, config.spotifyRedirectURI)
server.SetMgmtConfig(config.mgmtUsername, config.mgmtPassword)
server.SetBaseURL(config.baseURL)
if config.spotifyClientID != "" {
spotifyService := spotify.NewSpotifyService(
@@ -357,7 +356,6 @@ type serviceConfig struct {
spotifyRedirectURI string
mgmtUsername string
mgmtPassword string
baseURL string
}
func loadConfig(c *cli.Context) serviceConfig {
@@ -421,7 +419,6 @@ func loadConfig(c *cli.Context) serviceConfig {
spotifyRedirectURI := c.String("spotify-redirect-uri")
mgmtUsername := c.String("mgmt-username")
mgmtPassword := c.String("mgmt-password")
baseURL := c.String("base-url")
return serviceConfig{
port: port,
@@ -446,7 +443,6 @@ func loadConfig(c *cli.Context) serviceConfig {
spotifyRedirectURI: spotifyRedirectURI,
mgmtUsername: mgmtUsername,
mgmtPassword: mgmtPassword,
baseURL: baseURL,
}
}
@@ -713,6 +709,7 @@ func setupRouter(server *handlers.Server) *chi.Mux {
r.Delete("/interactions/sessions", server.HandleCleanupSessions)
r.Get("/dns-discoveries", server.HandleGetDNSDiscoveries)
r.Get("/dns-discoveries/download", server.HandleDownloadDNSDiscoveries)
r.Delete("/dns-discoveries", server.HandleClearDNSDiscoveries)
r.Get("/devices/{deviceId}/events", server.HandleGetDeviceEvents)
+1
View File
@@ -155,6 +155,7 @@ func (d *DNSDiscovery) shouldIntercept(hostname string) bool {
"marge.bose.com",
"bmx.bose.com",
"streaming.bose.com",
"streamingoauth.bose.com",
"updates.bose.com",
"stats.bose.com",
"content.api.bose.io",
+18
View File
@@ -38,6 +38,24 @@ func TestDNSDiscovery_Interception(t *testing.T) {
t.Errorf("Expected A record, got %T", rw.msg.Answer[0])
}
// Test intercepting streamingoauth.bose.com
m3 := new(dns.Msg)
m3.SetQuestion("streamingoauth.bose.com.", dns.TypeA)
rw3 := &mockResponseWriter{}
d.ServeDNS(rw3, m3)
if rw3.msg == nil || len(rw3.msg.Answer) == 0 {
t.Fatal("Expected response for streamingoauth.bose.com")
}
if a, ok := rw3.msg.Answer[0].(*dns.A); ok {
if a.A.String() != serviceIP {
t.Errorf("Expected intercepted IP %s for streamingoauth.bose.com, got %s", serviceIP, a.A.String())
}
} else {
t.Errorf("Expected A record for streamingoauth.bose.com, got %T", rw3.msg.Answer[0])
}
// Test aftertouch.test
m2 := new(dns.Msg)
m2.SetQuestion("aftertouch.test.", dns.TypeA)
+27 -6
View File
@@ -419,6 +419,32 @@ func (s *Server) HandleRevertMigration(w http.ResponseWriter, r *http.Request) {
// HandleGetDNSDiscoveries returns recorded DNS discoveries.
func (s *Server) HandleGetDNSDiscoveries(w http.ResponseWriter, _ *http.Request) {
result := s.getMergedDNSDiscoveries()
w.Header().Set("Content-Type", "application/json")
if err := json.NewEncoder(w).Encode(result); err != nil {
http.Error(w, "Failed to encode response", http.StatusInternalServerError)
return
}
}
// HandleDownloadDNSDiscoveries returns recorded DNS discoveries as a downloadable JSON file.
func (s *Server) HandleDownloadDNSDiscoveries(w http.ResponseWriter, _ *http.Request) {
result := s.getMergedDNSDiscoveries()
w.Header().Set("Content-Type", "application/json")
w.Header().Set("Content-Disposition", "attachment; filename=\"dns-discoveries.json\"")
encoder := json.NewEncoder(w)
encoder.SetIndent("", " ")
if err := encoder.Encode(result); err != nil {
log.Printf("Error encoding DNS discoveries for download: %v", err)
}
}
func (s *Server) getMergedDNSDiscoveries() []datastore.DNSDiscoveryEntry {
// 1. Get current in-memory discoveries
inMemory := s.GetDNSDiscovery()
@@ -469,12 +495,7 @@ func (s *Server) HandleGetDNSDiscoveries(w http.ResponseWriter, _ *http.Request)
log.Printf("Warning: Failed to persist merged DNS discoveries: %v", err)
}
w.Header().Set("Content-Type", "application/json")
if err := json.NewEncoder(w).Encode(result); err != nil {
http.Error(w, "Failed to encode response", http.StatusInternalServerError)
return
}
return result
}
// HandleClearDNSDiscoveries clears recorded DNS discoveries.
-9
View File
@@ -46,7 +46,6 @@ type Server struct {
spotifyClientID string
spotifyClientSecret string
spotifyRedirectURI string
baseURL string
spotifyService *spotify.Service
}
@@ -242,14 +241,6 @@ func (s *Server) SetMgmtConfig(username, password string) {
s.mgmtPassword = password
}
// SetBaseURL sets the external base URL for OAuth callbacks.
func (s *Server) SetBaseURL(baseURL string) {
s.mu.Lock()
defer s.mu.Unlock()
s.baseURL = baseURL
}
// SetSpotifyService sets the Spotify OAuth service.
func (s *Server) SetSpotifyService(ss *spotify.Service) {
s.mu.Lock()
+4 -1
View File
@@ -406,7 +406,10 @@
<div id="dns-discoveries" class="summary-box" style="margin-top: 20px;">
<div style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 15px;">
<h3 style="margin: 0;">DNS Discoveries</h3>
<button onclick="clearDNSDiscoveries()" class="btn-danger">Clear DNS Logs</button>
<div style="display: flex; gap: 10px;">
<button onclick="downloadDNSDiscoveries()" class="btn-info">Download JSON</button>
<button onclick="clearDNSDiscoveries()" class="btn-danger">Clear DNS Logs</button>
</div>
</div>
<p style="font-size: 0.85em; color: #666;">Hosts discovered via the AfterTouch DNS server. "Self" means the domain was intercepted and redirected to this service.</p>
<div id="dns-discoveries-list-container" style="max-height: 400px; overflow-y: auto;">
+4
View File
@@ -585,6 +585,10 @@ async function clearDNSDiscoveries() {
}
}
function downloadDNSDiscoveries() {
window.location.href = '/setup/dns-discoveries/download';
}
async function showDeviceEvents() {
const overlay = document.getElementById('device-events-overlay');
overlay.style.display = 'block';