package main import ( "encoding/base64" "errors" "fmt" "mime" "net/http" "os" "path/filepath" "strings" "github.com/wailsapp/wails/v2/pkg/runtime" "gorm.io/gorm" ) type DisplayImage struct { gorm.Model MIMEType string Content []byte } type ImageResponse struct { DataURI string Base64 string } func (app *App) PickContactImage(contact Contact) (*ImageResponse, error) { filePath, err := runtime.OpenFileDialog(app.ctx, runtime.OpenDialogOptions{ Title: "Select Contact Photo", Filters: []runtime.FileFilter{ { DisplayName: "Images (*.png;*.jpg;*.jpeg;*.gif)", Pattern: "*.png;*.jpg;*.jpeg;*.gif", }, }, }) if err != nil { return nil, fmt.Errorf("file dialog failed: %w", err) } if filePath == "" { return nil, nil } data, err := os.ReadFile(filePath) if err != nil { return nil, fmt.Errorf("failed to read file: %w", err) } ext := strings.ToLower(filepath.Ext(filePath)) mimeType := mime.TypeByExtension(ext) if mimeType == "" { mimeType = "image/png" } base64Str := base64.StdEncoding.EncodeToString(data) dataURI := fmt.Sprintf("data:%s;base64,%s", mimeType, base64Str) return &ImageResponse{DataURI: dataURI, Base64: base64Str}, nil } func (app *App) GetContactImage(contact Contact) (*ImageResponse, error) { if contact.ID == 0 { return nil, nil } var img DisplayImage if err := app.DB.Where("id = ?", contact.DisplayImageID).First(&img).Error; err != nil { if errors.Is(err, gorm.ErrRecordNotFound) { return nil, nil } return nil, err } if len(img.Content) == 0 { return nil, nil } encoded := base64.StdEncoding.EncodeToString(img.Content) dataURI := fmt.Sprintf("data:%s;base64,%s", img.MIMEType, encoded) return &ImageResponse{ DataURI: dataURI, Base64: encoded, }, nil } func (app *App) SaveContactImage(contactID uint, base64Str string) error { if base64Str == "" { return nil } data, err := base64.StdEncoding.DecodeString(base64Str) if err != nil { return fmt.Errorf("invalid base64 image data: %w", err) } mimeType := http.DetectContentType(data) var contact Contact if err := app.DB.First(&contact, contactID).Error; err != nil { return fmt.Errorf("contact %d not found: %w", contactID, err) } img := DisplayImage{ MIMEType: mimeType, Content: data, } if contact.DisplayImageID != 0 { img.Model = gorm.Model{ID: contact.DisplayImageID} } if err := app.DB.Session(&gorm.Session{FullSaveAssociations: true}). Save(&img).Error; err != nil { return fmt.Errorf("failed to save image: %w", err) } contact.DisplayImageID = img.ID if err := app.DB.Save(&contact).Error; err != nil { return fmt.Errorf("failed to link image to contact: %w", err) } return nil }