package exporting import ( "archive/zip" "encoding/json" "errors" "fmt" "os" "path" "strings" "code.nonshy.com/nonshy/website/pkg/log" "code.nonshy.com/nonshy/website/pkg/models" "code.nonshy.com/nonshy/website/pkg/photo" ) // ExportUser creates a data export archive of ALL data stored about a user account.. func ExportUser(user *models.User, filename string) error { if !strings.HasSuffix(filename, ".zip") { return errors.New("output file should be a .zip file") } // Prepare the output zip writer. fh, err := os.Create(filename) if err != nil { return fmt.Errorf("creating output file (%s): %s", filename, err) } zw := zip.NewWriter(fh) defer zw.Close() // Export all their database tables into the zip. return ExportModels(zw, user) } // ZipJson serializes a JSON file into the zipfile. func ZipJson(zw *zip.Writer, filename string, v any) error { fh, err := zw.Create(filename) if err != nil { return err } encoder := json.NewEncoder(fh) encoder.SetIndent("", " ") return encoder.Encode(v) } // ZipPhoto copies a user photo into the ZIP archive. func ZipPhoto(zw *zip.Writer, prefix, filename string) error { var ( diskPath = photo.DiskPath(filename) data, err = os.ReadFile(diskPath) ) if err != nil { if os.IsNotExist(err) { // Not fatal but log it. log.Error("ZipPhoto(%s): read from disk: %s", diskPath, err) return nil } return fmt.Errorf("ZipPhoto(%s): read from disk: %s", diskPath, err) } outfh, err := zw.Create(path.Join(prefix, filename)) if err != nil { return fmt.Errorf("ZipPhoto(%s): create in zip: %s", filename, err) } log.Info("Add photo to zip: %s", filename) _, err = outfh.Write(data) return err }