Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,4 @@ dist/
out/
# App
site/
bup.yaml
4 changes: 3 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ Remembers your `destination` directory and uses the current directory as `source

Supports directory excludes stored in the config file with the saved destination.

[![View Documentation](https://img.shields.io/badge/view_documentation-blue?style=for-the-badge&logo=googledocs&logoColor=white)](https://smashedr.github.io/bup/)
[![VHS Tape](https://raw.githubusercontent.com/smashedr/repo-images/refs/heads/master/bup/bup.gif)](https://smashedr.github.io/bup/)

## Install

Expand Down Expand Up @@ -73,6 +73,8 @@ docker run --rm ghcr.io/smashedr/bup:latest
go install github.com/smashedr/bup@latest
```

[![View Documentation](https://img.shields.io/badge/view_documentation-blue?style=for-the-badge&logo=googledocs&logoColor=white)](https://smashedr.github.io/bup/)

## Usage

- Specify `source` and `destination`
Expand Down
9 changes: 9 additions & 0 deletions Taskfile.yml
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,15 @@ tasks:
wget https://github.com/Bill-Stewart/PathMgr/releases/download/v2.0.0/PathMgr-2.0.0.zip -O dist/pathmgr.zip
unzip dist/pathmgr.zip -d dist/PathMgr

vhs:
desc: Create VHS Tape
summary: Requires a bup.yaml with a valid backup destination
cmds:
- rm -rf "$HOME/backup/bup"
- cp -f assets/bup.tape bup.tape
- vhs bup.tape
- defer: rm -f bup.tape

test:
if: test ! -d dist/PathMgr
#preconditions:
Expand Down
43 changes: 43 additions & 0 deletions assets/bup.tape
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
Output dist/bup.gif
Output dist/bup.mp4
Output dist/bup.webm

Require bup

Set Theme "Catppuccin Frappe"
Set MarginFill "#6B50FF"
Set Margin 10
Set WindowBar Colorful
Set BorderRadius 10
Set Padding 30
Set Width 1200
Set Height 900
Set FontSize 26

Type "bup backup ."
Sleep 0.5s
Enter
Wait /Proceed\?/
Sleep 2s
Type "y"
Sleep 1s
Enter
Wait
Sleep 3s

Type "bup list"
Sleep 0.5s
Enter
Wait
Screenshot dist/bup.png
Sleep 2s

Type "bup l bup"
Sleep 0.5s
Enter
Wait
Sleep 2s

Type "clear"
Sleep 0.3s
Enter
60 changes: 43 additions & 17 deletions cmd/backup.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,16 +47,7 @@ var backupCmd = &cobra.Command{
fmt.Printf("Excludes: %s\n", excludes)

if destination == "" {
fmt.Print("Enter Destination Path: ")
var response string
_, _ = fmt.Scanln(&response)
//fmt.Printf("response: \"%s\"\n", response)
responseInfo, err := os.Stat(response)
if err != nil || !responseInfo.IsDir() {
fmt.Printf("Error: inalid destination: %s\n", response)
return
}
destination = response
destination = promptForDestination()
}

sourceInfo, err := os.Stat(source)
Expand Down Expand Up @@ -122,10 +113,12 @@ var backupCmd = &cobra.Command{

// Create timestamp filename
timestamp := time.Now().Format("06-01-02-15-04-05") // YY-MM-DD-HH-MM-SS
zipFilename := filepath.Join(fullDestPath, timestamp+".zip")
fmt.Printf("zipFilename: %s\n", zipFilename)
zipFileName := timestamp + ".zip"
fmt.Printf("zipFileName: %s\n", zipFileName)
zipFilePath := filepath.Join(fullDestPath, zipFileName)
fmt.Printf("zipFilePath: %s\n", zipFilePath)

if err := archive.CreateZipArchive(excludes, sourcePath, zipFilename); err != nil {
if err := archive.CreateZipArchive(excludes, sourcePath, zipFilePath); err != nil {
fmt.Printf("Error creating archive: %v\n", err)
os.Exit(1)
}
Expand All @@ -134,23 +127,56 @@ var backupCmd = &cobra.Command{
fmt.Printf("copyToClipboard: %v\n", copyToClipboard)
if copyToClipboard {
if err := clipboard.Init(); err != nil {
fmt.Printf("%v\n", err)
//fmt.Printf("%v\n", err)
fmt.Printf("Clipboard not available.\n")
} else {
clipboard.Write(clipboard.FmtText, []byte(zipFilename))
clipboard.Write(clipboard.FmtText, []byte(zipFilePath))
}
}

fileInfo, err := os.Stat(zipFilename)
fileInfo, err := os.Stat(zipFilePath)
if err != nil {
fmt.Printf("Error getting archive info: %v", err)
} else {
fmt.Printf("Archive Size: %s\n", formatBytes(fileInfo.Size()))
}

fmt.Printf("Success!\n")
fmt.Printf("Archive File: %s\nSuccess!\n", zipFilePath)
},
}

func promptForDestination() string {
for {
fmt.Print("Enter Destination Path: ")

var input string
_, _ = fmt.Scanln(&input)

// Expand ~ to home directory
if strings.HasPrefix(input, "~") {
home, err := os.UserHomeDir()
if err != nil {
fmt.Println("Error: unable to resolve home directory")
continue
}

if input == "~" {
input = home
} else if strings.HasPrefix(input, "~/") {
input = filepath.Join(home, input[2:])
}
}

info, err := os.Stat(input)
if err != nil || !info.IsDir() {
fmt.Printf("Error: invalid destination: %s\n", input)
continue
}

return input
}
}

func formatBytes(bytes int64) string {
const unit = 1024
if bytes < unit {
Expand Down