95c821deb2
Add detailed [DEBUG] logging to every controller module when logging.level is set to "debug". Each module with stateful debug uses SetDebug(bool) wired from main.go. Covers stacks, backup, cloudflare, integrations, system, monitor, settings, scheduler, web handlers, storage, metrics, API, selfupdate, and assets. Also includes the app export/import (.fab bundles) feature from v0.32.0 and its debug page integration. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
121 lines
3.9 KiB
Go
121 lines
3.9 KiB
Go
package integrations
|
|
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
)
|
|
|
|
// OnlyOfficeFileBrowserHandler enables/disables OnlyOffice document editing in FileBrowser Quantum.
|
|
type OnlyOfficeFileBrowserHandler struct{}
|
|
|
|
func (h *OnlyOfficeFileBrowserHandler) Apply(ac *ApplyContext) error {
|
|
jwtSecret := ac.ProviderEnv["JWT_SECRET"]
|
|
if jwtSecret == "" {
|
|
return fmt.Errorf("OnlyOffice JWT_SECRET nincs beállítva — telepítsd újra az alkalmazást")
|
|
}
|
|
|
|
subdomain := ac.ProviderEnv["SUBDOMAIN"]
|
|
if subdomain == "" && ac.ProviderMeta != nil {
|
|
subdomain = ac.ProviderMeta.Subdomain
|
|
}
|
|
if subdomain == "" {
|
|
return fmt.Errorf("OnlyOffice aldomain nem ismert")
|
|
}
|
|
|
|
configPath := filepath.Join(ac.StacksDir, "filebrowser", "config.yaml")
|
|
officeURL := fmt.Sprintf("https://%s.%s", subdomain, ac.Domain)
|
|
|
|
ac.Logger.Printf("[DEBUG] [integrations] OnlyOfficeFileBrowser.Apply: jwtSecretPresent=%v subdomain=%s configPath=%s officeURL=%s", jwtSecret != "", subdomain, configPath, officeURL)
|
|
|
|
configData, err := os.ReadFile(configPath)
|
|
if err != nil {
|
|
return fmt.Errorf("FileBrowser config olvasási hiba: %w", err)
|
|
}
|
|
|
|
// Remove any existing integrations section, then append the new one
|
|
configStr := removeIntegrationsSection(string(configData))
|
|
|
|
internalURL := "http://onlyoffice:80"
|
|
|
|
integrationsBlock := fmt.Sprintf("integrations:\n office:\n url: %q\n internalUrl: %q\n secret: %q\n viewOnly: false\n",
|
|
officeURL, internalURL, jwtSecret)
|
|
|
|
configStr = strings.TrimRight(configStr, "\n") + "\n" + integrationsBlock
|
|
|
|
// Atomic write
|
|
tmpPath := configPath + ".tmp"
|
|
if err := os.WriteFile(tmpPath, []byte(configStr), 0644); err != nil {
|
|
return fmt.Errorf("config írási hiba: %w", err)
|
|
}
|
|
if err := os.Rename(tmpPath, configPath); err != nil {
|
|
_ = os.Remove(tmpPath)
|
|
return fmt.Errorf("config átnevezési hiba: %w", err)
|
|
}
|
|
|
|
ac.Logger.Printf("[INFO] FileBrowser config updated with OnlyOffice integration")
|
|
return ac.RestartStack("filebrowser")
|
|
}
|
|
|
|
func (h *OnlyOfficeFileBrowserHandler) Revoke(ac *ApplyContext) error {
|
|
configPath := filepath.Join(ac.StacksDir, "filebrowser", "config.yaml")
|
|
ac.Logger.Printf("[DEBUG] [integrations] OnlyOfficeFileBrowser.Revoke: configPath=%s", configPath)
|
|
|
|
configData, err := os.ReadFile(configPath)
|
|
if err != nil {
|
|
if os.IsNotExist(err) {
|
|
return nil
|
|
}
|
|
return fmt.Errorf("config olvasási hiba: %w", err)
|
|
}
|
|
|
|
cleaned := removeIntegrationsSection(string(configData))
|
|
hadIntegrations := cleaned != string(configData)
|
|
ac.Logger.Printf("[DEBUG] [integrations] OnlyOfficeFileBrowser.Revoke: integrationsSectionFound=%v", hadIntegrations)
|
|
if !hadIntegrations {
|
|
return nil // no integrations section, nothing to remove
|
|
}
|
|
|
|
tmpPath := configPath + ".tmp"
|
|
if err := os.WriteFile(tmpPath, []byte(cleaned), 0644); err != nil {
|
|
return fmt.Errorf("config írási hiba: %w", err)
|
|
}
|
|
if err := os.Rename(tmpPath, configPath); err != nil {
|
|
_ = os.Remove(tmpPath)
|
|
return fmt.Errorf("config átnevezési hiba: %w", err)
|
|
}
|
|
|
|
ac.Logger.Printf("[INFO] FileBrowser config cleaned — OnlyOffice integration removed")
|
|
return ac.RestartStack("filebrowser")
|
|
}
|
|
|
|
// removeIntegrationsSection strips the integrations: YAML block from a config string.
|
|
// It removes from the line starting with "integrations:" to the next unindented key or EOF.
|
|
func removeIntegrationsSection(config string) string {
|
|
lines := strings.Split(config, "\n")
|
|
var result []string
|
|
inBlock := false
|
|
for _, line := range lines {
|
|
if strings.HasPrefix(line, "integrations:") {
|
|
inBlock = true
|
|
continue
|
|
}
|
|
if inBlock {
|
|
trimmed := strings.TrimRight(line, " \t\r")
|
|
if trimmed == "" {
|
|
continue // skip blank lines within block
|
|
}
|
|
if line[0] != ' ' && line[0] != '\t' {
|
|
// New top-level key — end of integrations block
|
|
inBlock = false
|
|
result = append(result, line)
|
|
}
|
|
// else: still inside indented block, skip
|
|
continue
|
|
}
|
|
result = append(result, line)
|
|
}
|
|
return strings.Join(result, "\n")
|
|
}
|