Skip to content

Commit

Permalink
docs: add better error messages
Browse files Browse the repository at this point in the history
  • Loading branch information
dpolakovics committed Dec 16, 2024
1 parent ebf4410 commit 9af6619
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 31 deletions.
33 changes: 13 additions & 20 deletions internal/logic/sync.go
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
package logic

import (
"io"
"bufio"
"context"
"fmt"
"io"
"io/ioutil"
"os"
"os/exec"
Expand All @@ -15,7 +15,6 @@ import (

"fyne.io/fyne/v2/widget"
"github.com/dhowden/tag"

ff "github.com/dpolakovics/soundscape-sync/internal/ffmpeg"
)

Expand All @@ -40,23 +39,20 @@ func getAudioFiles(folder string) ([]string, error) {
return audioFiles, nil
}

// Add a statusCallback parameter to allow updates on what is happening
func CombineFiles(folder1 string, folder2 string, outputFolder string, progress *widget.ProgressBar, soundscapeVolume float64, statusCallback func(string)) error {
// Adjust volume to range [0.5, 1.0]
soundscapeVolume = 0.5 + (soundscapeVolume / 100.0 * 0.5)

// Get list of audio files from both folders
files1, err := getAudioFiles(folder1)
if err != nil {
return err
return fmt.Errorf("failed to read audio files from folder1 (%s): %w. Check folder permissions or file formats and try again.", folder1, err)
}
files2, err := getAudioFiles(folder2)
if err != nil {
return err
return fmt.Errorf("failed to read audio files from folder2 (%s): %w. Check folder permissions or file formats and try again.", folder2, err)
}

if len(files1) != len(files2) {
return fmt.Errorf("the number of audio files in the two folders must be the same")
return fmt.Errorf("the number of audio files in the two folders does not match: folder1 has %d files, folder2 has %d files. Please ensure both folders contain the same number of audio files and that they are in the correct order before retrying.", len(files1), len(files2))
}

ffmpeg := ff.FFmpegPath()
Expand All @@ -65,7 +61,7 @@ func CombineFiles(folder1 string, folder2 string, outputFolder string, progress
for index, file := range files1 {
statusCallback(fmt.Sprintf("Preparing to combine file %d of %d: %s", index+1, total, filepath.Base(file)))

channel , err := getChannelAmount(file)
channel, err := getChannelAmount(file)
if err != nil {
return err
}
Expand All @@ -79,12 +75,10 @@ func CombineFiles(folder1 string, folder2 string, outputFolder string, progress
return err
}

// Get output file name
ext := filepath.Ext(file)
newFileName := outputFolder + "/" + filepath.Base(files2[index])
newFileName = newFileName[:len(newFileName)-4] + "_synced" + ext

// Construct FFmpeg command
ctx, _ := context.WithCancel(context.Background())
arguments := []string{
"-i", file,
Expand All @@ -96,27 +90,26 @@ func CombineFiles(folder1 string, folder2 string, outputFolder string, progress
arguments = append(arguments, getCoverArtArguments(file, files2[index])...)
}
arguments = append(arguments, newFileName)

cmd := exec.CommandContext(ctx, ffmpeg, arguments...)
cmd.SysProcAttr = getSysProcAttr()
stdout, err := cmd.StdoutPipe()
if err != nil {
// prepend error with text
err = fmt.Errorf("error creating ffmpeg command: %w", err)
err = fmt.Errorf("error creating FFmpeg command pipeline (arguments: %v): %w. Consider running with more detailed logging or contacting the developer if the problem persists.", cmd.Args, err)
return err
}

statusCallback(fmt.Sprintf("Combining file %d of %d...", index+1, total))

// Execute FFmpeg command
if err := cmd.Start(); err != nil {
err = fmt.Errorf("error at ffmpeg command start: %w", err)
err = fmt.Errorf("error starting FFmpeg command with arguments %v: %w. Check that the input files are accessible and not corrupted. If the issue persists, contact the developer.", cmd.Args, err)
return err
}

parseProgress(index, total, progress, stdout, duration)

if err := cmd.Wait(); err != nil {
err = fmt.Errorf("error at ffmpeg command wait: %w", err)
err = fmt.Errorf("FFmpeg encountered an error while processing file %q with arguments %v: %w. Check the input files for issues or consider contacting the developer for further assistance.", newFileName, cmd.Args, err)
return err
}

Expand All @@ -133,11 +126,11 @@ func getChannelAmount(file string) (int, error) {
cmd := exec.Command(ffprobe, "-v", "error", "-select_streams", "a:0", "-count_packets", "-show_entries", "stream=channels", "-of", "csv=p=0", file)
out, err := cmd.Output()
if err != nil {
return 0, err
return 0, fmt.Errorf("failed to determine channel amount for file %q: %w. The file might be corrupted or unsupported.", file, err)
}
channels, err := strconv.Atoi(strings.TrimSuffix(strings.TrimSpace(string(out)), ","))
if err != nil {
return 0, err
return 0, fmt.Errorf("invalid channel information retrieved for file %q: %w. Please ensure the file is a valid audio file and consider reporting this issue if it persists.", file, err)
}
return channels, nil
}
Expand All @@ -148,7 +141,7 @@ func getDuration(filename string) (float64, error) {
cmd := exec.Command(ffprobe, "-v", "error", "-show_entries", "format=duration", "-of", "default=noprint_wrappers=1:nokey=1", filename)
out, err := cmd.Output()
if err != nil {
return 0, err
return 0, fmt.Errorf("failed to determine duration for file %q: %w. The file might be corrupted or unsupported. If issues persist, consider contacting the developer.", filename, err)
}
return strconv.ParseFloat(strings.TrimSpace(string(out)), 64)
}
Expand Down Expand Up @@ -186,7 +179,7 @@ func getChannelArguments(channels int, volume float64) ([]string, error) {
case 12:
return get7_1_4Arguments(volume), nil
}
return nil, fmt.Errorf("Currently only stereo, 5.1, 7.1.2 and 7.1.4 Soundscapes are supported")
return nil, fmt.Errorf("unsupported soundscape format with %d channels. Currently only stereo (2 channels), 5.1 (6 channels), 7.1.2 (10 channels), and 7.1.4 (12 channels) are supported. Please convert your files or contact the developer for assistance.", channels)
}

func getCoverArtArguments(file1 string, file2 string) []string {
Expand Down
25 changes: 21 additions & 4 deletions internal/ui/windows.go
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ func showFolderSelection(win fyne.Window, callback func(string)) {

dialog.ShowFolderOpen(func(uri fyne.ListableURI, err error) {
if err != nil {
dialog.ShowError(err, win)
showErrorDialog(win, fmt.Errorf("Failed to open folder selection dialog: %w. If this issue persists, please contact the developer.", err))
return
}
if uri == nil {
Expand Down Expand Up @@ -183,14 +183,12 @@ func CreateMainContent(app fyne.App, window fyne.Window) fyne.CanvasObject {
startButton.OnTapped = func() {
startButton.Disable()
progressBar.Show()
// Run CombineFiles synchronously on the main goroutine
err := logic.CombineFiles(folder1, folder2, folderOutput, progressBar, volumeSlider.Value, func(msg string) {
// Safe to call directly because we're on the main goroutine
statusLabel.SetText(msg)
})
progressBar.Hide()
if err != nil {
dialog.ShowError(err, window)
showErrorDialog(window, fmt.Errorf("An error occurred while combining the audio files: %w. Check that the input files are valid and supported. If you continue to encounter this issue, consider seeking help from the developer and providing the details above.", err))
statusLabel.SetText("Error during combination")
} else {
dialog.ShowInformation("Success", "Audio files combined successfully", window)
Expand Down Expand Up @@ -250,3 +248,22 @@ func updateStartButton(label1, label2, folderOutputLabel *widget.Label, button *
button.Disable()
}
}

func showErrorDialog(win fyne.Window, err error) {
if err == nil {
return
}

errorStr := err.Error()
copyButton := widget.NewButton("Copy Error", func() {
win.Clipboard().SetContent(errorStr)
})

errorLabel := widget.NewLabel(errorStr)
errorLabel.Wrapping = fyne.TextWrapWord

content := container.NewVBox(errorLabel, copyButton)
d := dialog.NewCustom("Error", "Close", content, win)
d.Resize(fyne.NewSize(700, 500))
d.Show()
}
32 changes: 25 additions & 7 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,11 @@ package main

import (
"context"
"fmt"
"net/url"
"strconv"
"strings"

"github.com/dpolakovics/soundscape-sync/internal/ui"

"fyne.io/fyne/v2"
Expand All @@ -12,9 +16,6 @@ import (
"fyne.io/fyne/v2/widget"

"github.com/google/go-github/v39/github"
"fmt"
"strings"
"strconv"
)

const (
Expand All @@ -40,7 +41,7 @@ func checkForUpdates(a fyne.App, w fyne.Window) {
client := github.NewClient(nil)
release, _, err := client.Repositories.GetLatestRelease(context.Background(), owner, repo)
if err != nil {
dialog.ShowError(err, w)
showErrorDialog(w, fmt.Errorf("Failed to check for the latest release: %w. Please ensure you have an internet connection, and if the issue persists, reach out to the developer.", err))
return
}

Expand All @@ -61,7 +62,6 @@ func checkForUpdates(a fyne.App, w fyne.Window) {
}

func isNewerVersion(oldVer, newVer string) bool {
// Strip leading 'v'
oldVer = strings.TrimPrefix(oldVer, "v")
newVer = strings.TrimPrefix(newVer, "v")

Expand All @@ -78,6 +78,24 @@ func isNewerVersion(oldVer, newVer string) bool {
}
}

// If all matched so far, then a longer new version means it's newer
return len(newParts) > len(oldParts)
}
}

func showErrorDialog(win fyne.Window, err error) {
if err == nil {
return
}

errorStr := err.Error()
copyButton := widget.NewButton("Copy Error", func() {
win.Clipboard().SetContent(errorStr)
})

errorLabel := widget.NewLabel(errorStr)
errorLabel.Wrapping = fyne.TextWrapWord

content := container.NewVBox(errorLabel, copyButton)
d := dialog.NewCustom("Error", "Close", content, win)
d.Resize(fyne.NewSize(700, 500))
d.Show()
}

0 comments on commit 9af6619

Please sign in to comment.