From 5f271efcf8b8b86b386910b2137cea619e6b6c05 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Tue, 23 Sep 2025 13:59:55 +0100 Subject: [PATCH 01/15] Add cobra --- go.mod | 9 +++++++++ go.sum | 11 +++++++++++ 2 files changed, 20 insertions(+) create mode 100644 go.mod create mode 100644 go.sum diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..466a14f --- /dev/null +++ b/go.mod @@ -0,0 +1,9 @@ +module zet + +go 1.24.6 + +require ( + github.com/inconshreveable/mousetrap v1.1.0 // indirect + github.com/spf13/cobra v1.10.1 // indirect + github.com/spf13/pflag v1.0.10 // indirect +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..989827e --- /dev/null +++ b/go.sum @@ -0,0 +1,11 @@ +github.com/cpuguy83/go-md2man/v2 v2.0.6/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g= +github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= +github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= +github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= +github.com/spf13/cobra v1.10.1 h1:lJeBwCfmrnXthfAupyUTzJ/J4Nc1RsHC/mSRU2dll/s= +github.com/spf13/cobra v1.10.1/go.mod h1:7SmJGaTHFVBY0jW4NXGluQoLvhqFQM+6XSKD+P4XaB0= +github.com/spf13/pflag v1.0.9/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= +github.com/spf13/pflag v1.0.10 h1:4EBh2KAYBwaONj6b2Ye1GiHfwjqyROoF4RwYO+vPwFk= +github.com/spf13/pflag v1.0.10/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= From b80b56c2d58a17ecdea9db2f5aa9f5dbb4e99736 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Tue, 23 Sep 2025 14:04:51 +0100 Subject: [PATCH 02/15] Initialise a new Cobra app --- cmd/root.go | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++ main.go | 7 +++++++ 2 files changed, 58 insertions(+) create mode 100644 cmd/root.go create mode 100644 main.go diff --git a/cmd/root.go b/cmd/root.go new file mode 100644 index 0000000..2a6f443 --- /dev/null +++ b/cmd/root.go @@ -0,0 +1,51 @@ +/* +Copyright © 2025 NAME HERE + +*/ +package cmd + +import ( + "os" + + "github.com/spf13/cobra" +) + + + +// rootCmd represents the base command when called without any subcommands +var rootCmd = &cobra.Command{ + Use: "zet", + Short: "A brief description of your application", + Long: `A longer description that spans multiple lines and likely contains +examples and usage of using your application. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + // Uncomment the following line if your bare application + // has an action associated with it: + // Run: func(cmd *cobra.Command, args []string) { }, +} + +// Execute adds all child commands to the root command and sets flags appropriately. +// This is called by main.main(). It only needs to happen once to the rootCmd. +func Execute() { + err := rootCmd.Execute() + if err != nil { + os.Exit(1) + } +} + +func init() { + // Here you will define your flags and configuration settings. + // Cobra supports persistent flags, which, if defined here, + // will be global for your application. + + // rootCmd.PersistentFlags().StringVar(&cfgFile, "config", "", "config file (default is $HOME/.zet.yaml)") + + // Cobra also supports local flags, which will only run + // when this action is called directly. + rootCmd.Flags().BoolP("toggle", "t", false, "Help message for toggle") +} + + diff --git a/main.go b/main.go new file mode 100644 index 0000000..55d8744 --- /dev/null +++ b/main.go @@ -0,0 +1,7 @@ +package main + +import "zet/cmd" + +func main() { + cmd.Execute() +} From 12a0353a4ccf4a231496e8b7d069828b47d298a6 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Tue, 23 Sep 2025 14:06:22 +0100 Subject: [PATCH 03/15] Add Go dev shell --- .envrc | 1 + 1 file changed, 1 insertion(+) create mode 100644 .envrc diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..e89fbf9 --- /dev/null +++ b/.envrc @@ -0,0 +1 @@ +use flake "git+https://code.oliverdavies.uk/opdavies/dev-shells#go" From 9019f4579d354ec04a9d384d4e91fc2df303ea16 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Tue, 23 Sep 2025 23:56:47 +0100 Subject: [PATCH 04/15] Add `titles` command to show all IDs and titles Signed-off-by: Oliver Davies --- .gitignore | 1 + build | 9 ++ cmd/root.go | 2 + cmd/titles.go | 26 +++++ go.mod | 2 +- internal/lib/git.go | 12 +++ internal/lib/lib.go | 93 +++++++++++++++++ main.go | 2 +- watch | 5 + zet | 244 -------------------------------------------- 10 files changed, 150 insertions(+), 246 deletions(-) create mode 100644 .gitignore create mode 100755 build create mode 100644 cmd/titles.go create mode 100644 internal/lib/git.go create mode 100644 internal/lib/lib.go create mode 100755 watch delete mode 100755 zet diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..b4ceeaf --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +/zet diff --git a/build b/build new file mode 100755 index 0000000..af2e46b --- /dev/null +++ b/build @@ -0,0 +1,9 @@ +#!/usr/bin/env bash + +set -euo pipefail + +echo "Building..." + +go build -o zet main.go + +echo "Done." diff --git a/cmd/root.go b/cmd/root.go index 2a6f443..f086cd2 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -37,6 +37,8 @@ func Execute() { } func init() { + rootCmd.AddCommand(titlesCmd) + // Here you will define your flags and configuration settings. // Cobra supports persistent flags, which, if defined here, // will be global for your application. diff --git a/cmd/titles.go b/cmd/titles.go new file mode 100644 index 0000000..175ac02 --- /dev/null +++ b/cmd/titles.go @@ -0,0 +1,26 @@ +package cmd + +import ( + "github.com/spf13/cobra" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" +) + +var titlesCmd = &cobra.Command{ + Use: "titles", + Aliases: []string{"t"}, + Short: "A brief description of your command", + Long: `A longer description that spans multiple lines and likely contains examples +and usage of using your command. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + Run: func(cmd *cobra.Command, args []string) { + zetDir := "/home/opdavies/Documents/zet" + + zets := lib.GetAllZets(zetDir) + + lib.ParseZetList(zets) + }, +} diff --git a/go.mod b/go.mod index 466a14f..bcaf3a4 100644 --- a/go.mod +++ b/go.mod @@ -1,4 +1,4 @@ -module zet +module code.oliverdavies.uk/opdavies/cmd-zet go 1.24.6 diff --git a/internal/lib/git.go b/internal/lib/git.go new file mode 100644 index 0000000..eda5e53 --- /dev/null +++ b/internal/lib/git.go @@ -0,0 +1,12 @@ +package lib + +import "os/exec" + +func execGitCommand(dir string, parts ...string) (string, error) { + args := append([]string{"-C", dir}, parts...) + command := exec.Command("git", args...) + + output, err := command.CombinedOutput() + + return string(output), err +} diff --git a/internal/lib/lib.go b/internal/lib/lib.go new file mode 100644 index 0000000..a10699c --- /dev/null +++ b/internal/lib/lib.go @@ -0,0 +1,93 @@ +package lib + +import ( + "bufio" + "fmt" + "log" + "os" + "path" + "regexp" + "sort" + "strconv" + "strings" +) + +func GetAllZets(dir string) []int { + zets, err := execGitCommand(dir, "ls-files") + + if err != nil { + log.Println(err) + } + + re := regexp.MustCompile(`[0-9]+`) + matches := re.FindAllString(zets, -1) + + sort.Strings(matches) + + ids := make(map[int]struct{}) + for _, id := range matches { + num, err := strconv.Atoi(id) + + if err == nil { + ids[num] = struct{}{} + } + } + + var sorted []int + for num := range ids { + sorted = append(sorted, num) + } + + sort.Ints(sorted) + + return sorted +} + +func ParseZetList(ids []int) []string { + var lines []string + + green := "\033[32m" + reset := "\033[0m" + + for _, num := range ids { + line := fmt.Sprintf("%s%s%s %s", green, strconv.Itoa(num), reset, getTitle(num)) + + fmt.Println(line) + + lines = append(lines, line) + } + + return lines +} + +func getTitle(id int) string { + return getTitleFromFile(path.Join(strconv.Itoa(id), "index.adoc")) +} + +func getTitleFromFile(filePath string) string { + filePath = path.Join("/home/opdavies/Documents/zet", filePath) + + file, err := os.Open(filePath) + + if err != nil { + fmt.Println("Error opening file:", err) + + return "" + } + + defer file.Close() + + scanner := bufio.NewScanner(file) + + if scanner.Scan() { + text := scanner.Text() + + return strings.TrimPrefix(text, "= ") + } + + if err := scanner.Err(); err != nil { + fmt.Println("Error reading file:", err) + } + + return "" +} diff --git a/main.go b/main.go index 55d8744..7b82f30 100644 --- a/main.go +++ b/main.go @@ -1,6 +1,6 @@ package main -import "zet/cmd" +import "code.oliverdavies.uk/opdavies/cmd-zet/cmd" func main() { cmd.Execute() diff --git a/watch b/watch new file mode 100755 index 0000000..fc894da --- /dev/null +++ b/watch @@ -0,0 +1,5 @@ +#!/usr/bin/env bash + +set -euo pipefail + +onchange "**/*.go" "./build && echo "" && ./zet $*" diff --git a/zet b/zet deleted file mode 100755 index 19633c4..0000000 --- a/zet +++ /dev/null @@ -1,244 +0,0 @@ -#!/usr/bin/env bash - -set -o pipefail - -IFS= read -rd '' USAGE < "$ZID/index.adoc" - edit_file "$ZID/index.adoc" - on_save "$ZID" -} - -delete_zettel() { - [[ -d "$ZID" ]] && rm -fr "$ZID" - commit_zettel "$ZID" -} - -edit_file() { - "$EDITOR" "$1" -} - -edit_zet() { - edit_file "$1/index.adoc" - on_save "$1" -} - -generate_links() { - echo "$1" | while IFS= read -r line; do - id="${line%% *}" - title="${line#* }" - echo "* link:../${id}/index.adoc[${title}]" - done -} - -get_latest_zettel() { - find . -maxdepth 1 -type d -name '[0-9]*' -printf '%f\n' | sort -nr | head -n 1 -} - -get_title() { - get_title_from_file "$1/index.adoc" -} - -get_title_from_file() { - head -n 1 "$1" | sed -e 's/^[#=] //' -} - -main() { - case "$1" in - create | new | c | n) - shift 1 - cmd_create "$@" - ;; - - edit | e) - shift 1 - cmd_edit "$@" - ;; - - help | h) - show_usage - ;; - - id) - shift 1 - cmd_id "$@" - ;; - - latest) - ZID="$(get_latest_zettel)" - edit_zet "$ZID" - ;; - - links | l) - shift 1 - cmd_links "$@" - ;; - - view | v) - shift 1 - cmd_view "$@" - ;; - - *) - cmd_search "$@" - ;; - esac -} - -new_zid() { - EXISTING_ZETTELS=$(find . -maxdepth 1 -type d -regex './[0-9]+' | wc -l) - - echo $((EXISTING_ZETTELS + 1)) -} - -on_save() { - ZID="$1" - - if [[ -s "$ZID/index.adoc" ]]; then - TITLE=$(get_title "$ZID") - commit_zettel "$ZID" "$TITLE" - else - echo "Deleting empty zettel: $ZID" - delete_zettel "$ZID" - fi -} - -parse_zet_list() { - ZET_LIST=() - - while IFS= read -r ZID; do - TITLE=$(get_title "$ZID") - ZET_LIST+=("$ZID $TITLE") - done -} - -search_zettel() { - if [[ "$*" == "latest" ]] || [[ "$*" == "l" ]]; then - get_latest_zettel - return - fi - - QUERY="$*" - - grep_args=("--extended-regexp") - [[ "$QUERY" != "" ]] && grep_args+=("--word-regex") - - git grep -i --name-only "${grep_args[@]}" "$QUERY" | grep -o -E '[0-9]+' | sort -un -} - -select_zet() { - if [[ "${#ZET_LIST[@]}" == 0 ]]; then - echo "No zettels to select" - exit 1 - fi - - if [[ "${#ZET_LIST[@]}" == 1 ]]; then - SELECTED_ZET=$(awk '{ print $1 }' <<<"${ZET_LIST[0]}") - return - fi - - selector - - if [[ -z "$SELECTED_ZET" ]]; then - echo "No zet selected" - exit 1 - fi -} - -selector() { - ITEM=$(printf "%s\n" "${ZET_LIST[@]}" | fzf --prompt="Select a zet: ") - - SELECTED_ZET=$(awk '{ print $1 }' <<< "$ITEM") -} - -show_usage() { - echo "$USAGE" -} - -view_zettel() { - cat "$1/index.adoc" -} - -(cd "$ZET_DIR" && main "$@") From f9a05ab5d9c1b4baa18c492b431b65eabaf780d1 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 08:26:16 +0100 Subject: [PATCH 05/15] Remove the toggle flag Signed-off-by: Oliver Davies --- cmd/root.go | 4 ---- 1 file changed, 4 deletions(-) diff --git a/cmd/root.go b/cmd/root.go index f086cd2..b885b02 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -44,10 +44,6 @@ func init() { // will be global for your application. // rootCmd.PersistentFlags().StringVar(&cfgFile, "config", "", "config file (default is $HOME/.zet.yaml)") - - // Cobra also supports local flags, which will only run - // when this action is called directly. - rootCmd.Flags().BoolP("toggle", "t", false, "Help message for toggle") } From 0a6e2b075ccd717f8abc34e7ec2080dac77f090e Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 08:30:00 +0100 Subject: [PATCH 06/15] Add `view` command Signed-off-by: Oliver Davies --- cmd/root.go | 6 +---- cmd/view.go | 39 +++++++++++++++++++++++++++++++++ internal/lib/file.go | 22 +++++++++++++++++++ internal/lib/{lib.go => zet.go} | 6 +++++ 4 files changed, 68 insertions(+), 5 deletions(-) create mode 100644 cmd/view.go create mode 100644 internal/lib/file.go rename internal/lib/{lib.go => zet.go} (91%) diff --git a/cmd/root.go b/cmd/root.go index b885b02..54a606e 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -1,6 +1,5 @@ /* Copyright © 2025 NAME HERE - */ package cmd @@ -10,8 +9,6 @@ import ( "github.com/spf13/cobra" ) - - // rootCmd represents the base command when called without any subcommands var rootCmd = &cobra.Command{ Use: "zet", @@ -38,6 +35,7 @@ func Execute() { func init() { rootCmd.AddCommand(titlesCmd) + rootCmd.AddCommand(viewCmd) // Here you will define your flags and configuration settings. // Cobra supports persistent flags, which, if defined here, @@ -45,5 +43,3 @@ func init() { // rootCmd.PersistentFlags().StringVar(&cfgFile, "config", "", "config file (default is $HOME/.zet.yaml)") } - - diff --git a/cmd/view.go b/cmd/view.go new file mode 100644 index 0000000..4ece1d9 --- /dev/null +++ b/cmd/view.go @@ -0,0 +1,39 @@ +package cmd + +import ( + "fmt" + "os" + "strconv" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" + "github.com/spf13/cobra" + // "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" +) + +var viewCmd = &cobra.Command{ + Use: "view", + Aliases: []string{"v"}, + Short: "A brief description of your command", + Long: `A longer description that spans multiple lines and likely contains examples +and usage of using your command. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + Run: func(cmd *cobra.Command, args []string) { + if len(args) < 1 { + fmt.Println("Error: No id provided") + os.Exit(1) + } + + idInt, err := strconv.Atoi(args[0]) + + if err != nil { + os.Exit(1) + } + + zetDir := "/home/opdavies/Documents/zet" + + fmt.Println(lib.ViewZet(zetDir, idInt)) + }, +} diff --git a/internal/lib/file.go b/internal/lib/file.go new file mode 100644 index 0000000..254a95b --- /dev/null +++ b/internal/lib/file.go @@ -0,0 +1,22 @@ +package lib + +import ( + "fmt" + "os" +) + +func ViewFile(filePath string) string { + if _, err := os.Stat(filePath); os.IsNotExist(err) { + fmt.Printf("Error: The file for path '%s' was not found\n", filePath) + os.Exit(1) + } + + content, err := os.ReadFile(filePath) + + if err != nil { + fmt.Println("Error opening the file:", err) + os.Exit(1) + } + + return string(content) +} diff --git a/internal/lib/lib.go b/internal/lib/zet.go similarity index 91% rename from internal/lib/lib.go rename to internal/lib/zet.go index a10699c..2273ccb 100644 --- a/internal/lib/lib.go +++ b/internal/lib/zet.go @@ -60,6 +60,12 @@ func ParseZetList(ids []int) []string { return lines } +func ViewZet(zetDir string, id int) string { + zetPath := path.Join(zetDir, strconv.Itoa(id), "index.adoc") + + return ViewFile(zetPath) +} + func getTitle(id int) string { return getTitleFromFile(path.Join(strconv.Itoa(id), "index.adoc")) } From 97445ca2cdb30ada4fb2ba04f2f3aadde0c492c3 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 13:00:00 +0100 Subject: [PATCH 07/15] Add `find` command Signed-off-by: Oliver Davies --- cmd/find.go | 35 +++++++++++++++++++++++++++++++++++ cmd/root.go | 1 + internal/lib/zet.go | 33 +++++++++++++++++++++++++++++++++ 3 files changed, 69 insertions(+) create mode 100644 cmd/find.go diff --git a/cmd/find.go b/cmd/find.go new file mode 100644 index 0000000..0564bc7 --- /dev/null +++ b/cmd/find.go @@ -0,0 +1,35 @@ +package cmd + +import ( + "fmt" + "os" + + "github.com/spf13/cobra" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" +) + +var findCmd = &cobra.Command{ + Use: "find", + Aliases: []string{"f", "s", "search"}, + Short: "A brief description of your command", + Long: `A longer description that spans multiple lines and likely contains examples +and usage of using your command. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + Run: func(cmd *cobra.Command, args []string) { + zetDir := "/home/opdavies/Documents/zet" + + if len(args) < 1 { + fmt.Println("No query") + + os.Exit(1) + } + + zets := lib.SearchZets(zetDir, args[0]) + + lib.ParseZetList(zets) + }, +} diff --git a/cmd/root.go b/cmd/root.go index 54a606e..cd7c326 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -34,6 +34,7 @@ func Execute() { } func init() { + rootCmd.AddCommand(findCmd) rootCmd.AddCommand(titlesCmd) rootCmd.AddCommand(viewCmd) diff --git a/internal/lib/zet.go b/internal/lib/zet.go index 2273ccb..2de0c21 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -43,6 +43,39 @@ func GetAllZets(dir string) []int { return sorted } +func SearchZets(dir string, query string) []int { + zets, err := execGitCommand(dir, "grep", "-i", "--name-only", "--word-regex", query) + + if err != nil { + fmt.Printf("No matches found for %s.\n", query) + + os.Exit(1) + } + + re := regexp.MustCompile(`[0-9]+`) + matches := re.FindAllString(zets, -1) + + sort.Strings(matches) + + ids := make(map[int]struct{}) + for _, id := range matches { + num, err := strconv.Atoi(id) + + if err == nil { + ids[num] = struct{}{} + } + } + + var sorted []int + for num := range ids { + sorted = append(sorted, num) + } + + sort.Ints(sorted) + + return sorted +} + func ParseZetList(ids []int) []string { var lines []string From ba5f26056f3b22d2085c13710dc50da5754a90f1 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 18:39:03 +0100 Subject: [PATCH 08/15] Refactor Signed-off-by: Oliver Davies --- cmd/find.go | 4 +--- cmd/titles.go | 4 +--- cmd/view.go | 4 +--- internal/lib/config.go | 5 +++++ internal/lib/git.go | 4 ++-- internal/lib/zet.go | 14 +++++++------- 6 files changed, 17 insertions(+), 18 deletions(-) create mode 100644 internal/lib/config.go diff --git a/cmd/find.go b/cmd/find.go index 0564bc7..817b257 100644 --- a/cmd/find.go +++ b/cmd/find.go @@ -20,15 +20,13 @@ Cobra is a CLI library for Go that empowers applications. This application is a tool to generate the needed files to quickly create a Cobra application.`, Run: func(cmd *cobra.Command, args []string) { - zetDir := "/home/opdavies/Documents/zet" - if len(args) < 1 { fmt.Println("No query") os.Exit(1) } - zets := lib.SearchZets(zetDir, args[0]) + zets := lib.SearchZets(args[0]) lib.ParseZetList(zets) }, diff --git a/cmd/titles.go b/cmd/titles.go index 175ac02..048253b 100644 --- a/cmd/titles.go +++ b/cmd/titles.go @@ -17,9 +17,7 @@ Cobra is a CLI library for Go that empowers applications. This application is a tool to generate the needed files to quickly create a Cobra application.`, Run: func(cmd *cobra.Command, args []string) { - zetDir := "/home/opdavies/Documents/zet" - - zets := lib.GetAllZets(zetDir) + zets := lib.GetAllZets() lib.ParseZetList(zets) }, diff --git a/cmd/view.go b/cmd/view.go index 4ece1d9..d03d299 100644 --- a/cmd/view.go +++ b/cmd/view.go @@ -32,8 +32,6 @@ to quickly create a Cobra application.`, os.Exit(1) } - zetDir := "/home/opdavies/Documents/zet" - - fmt.Println(lib.ViewZet(zetDir, idInt)) + fmt.Println(lib.ViewZet(idInt)) }, } diff --git a/internal/lib/config.go b/internal/lib/config.go new file mode 100644 index 0000000..9d482ae --- /dev/null +++ b/internal/lib/config.go @@ -0,0 +1,5 @@ +package lib + +func GetZetDir() string { + return "/home/opdavies/Documents/zet" +} diff --git a/internal/lib/git.go b/internal/lib/git.go index eda5e53..30abd4a 100644 --- a/internal/lib/git.go +++ b/internal/lib/git.go @@ -2,8 +2,8 @@ package lib import "os/exec" -func execGitCommand(dir string, parts ...string) (string, error) { - args := append([]string{"-C", dir}, parts...) +func execGitCommand(parts ...string) (string, error) { + args := append([]string{"-C", GetZetDir()}, parts...) command := exec.Command("git", args...) output, err := command.CombinedOutput() diff --git a/internal/lib/zet.go b/internal/lib/zet.go index 2de0c21..4ca8c9d 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -12,8 +12,8 @@ import ( "strings" ) -func GetAllZets(dir string) []int { - zets, err := execGitCommand(dir, "ls-files") +func GetAllZets() []int { + zets, err := execGitCommand("ls-files") if err != nil { log.Println(err) @@ -43,8 +43,8 @@ func GetAllZets(dir string) []int { return sorted } -func SearchZets(dir string, query string) []int { - zets, err := execGitCommand(dir, "grep", "-i", "--name-only", "--word-regex", query) +func SearchZets(query string) []int { + zets, err := execGitCommand("grep", "-i", "--name-only", "--word-regex", query) if err != nil { fmt.Printf("No matches found for %s.\n", query) @@ -93,8 +93,8 @@ func ParseZetList(ids []int) []string { return lines } -func ViewZet(zetDir string, id int) string { - zetPath := path.Join(zetDir, strconv.Itoa(id), "index.adoc") +func ViewZet(id int) string { + zetPath := path.Join(GetZetDir(), strconv.Itoa(id), "index.adoc") return ViewFile(zetPath) } @@ -104,7 +104,7 @@ func getTitle(id int) string { } func getTitleFromFile(filePath string) string { - filePath = path.Join("/home/opdavies/Documents/zet", filePath) + filePath = path.Join(GetZetDir(), filePath) file, err := os.Open(filePath) From 1986b9deca11fa757c8b2678f68a4d4ad539e443 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 18:39:20 +0100 Subject: [PATCH 09/15] Remove copyright statement Signed-off-by: Oliver Davies --- cmd/root.go | 3 --- 1 file changed, 3 deletions(-) diff --git a/cmd/root.go b/cmd/root.go index cd7c326..d94759f 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -1,6 +1,3 @@ -/* -Copyright © 2025 NAME HERE -*/ package cmd import ( From 125aa05e0dc3ee9380317c04cbaa9006fd32a711 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 19:35:56 +0100 Subject: [PATCH 10/15] Add `edit` command to edit a zettel Signed-off-by: Oliver Davies --- cmd/edit.go | 36 ++++++++++++++++++++++++++++++++++++ cmd/root.go | 1 + internal/lib/file.go | 15 +++++++++++++++ internal/lib/run.go | 22 ++++++++++++++++++++++ internal/lib/zet.go | 6 ++++++ 5 files changed, 80 insertions(+) create mode 100644 cmd/edit.go create mode 100644 internal/lib/run.go diff --git a/cmd/edit.go b/cmd/edit.go new file mode 100644 index 0000000..ea5fba5 --- /dev/null +++ b/cmd/edit.go @@ -0,0 +1,36 @@ +package cmd + +import ( + "fmt" + "os" + "strconv" + + "github.com/spf13/cobra" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" +) + +var editCmd = &cobra.Command{ + Use: "edit", + Aliases: []string{"e"}, + Short: "A brief description of your command", + Long: `A longer description that spans multiple lines and likely contains examples +and usage of using your command. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + Run: func(cmd *cobra.Command, args []string) { + if len(args) < 1 { + fmt.Println("Error: No id provided") + os.Exit(1) + } + + idInt, err := strconv.Atoi(args[0]) + if err != nil { + os.Exit(1) + } + + lib.EditZet(idInt) + }, +} diff --git a/cmd/root.go b/cmd/root.go index d94759f..6b68650 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -31,6 +31,7 @@ func Execute() { } func init() { + rootCmd.AddCommand(editCmd) rootCmd.AddCommand(findCmd) rootCmd.AddCommand(titlesCmd) rootCmd.AddCommand(viewCmd) diff --git a/internal/lib/file.go b/internal/lib/file.go index 254a95b..77781e7 100644 --- a/internal/lib/file.go +++ b/internal/lib/file.go @@ -5,6 +5,21 @@ import ( "os" ) +func EditFile(filePath string) { + if _, err := os.Stat(filePath); os.IsNotExist(err) { + fmt.Printf("Error: The file for path '%s' was not found\n", filePath) + os.Exit(1) + } + + editor := os.Getenv("EDITOR") + + err := Exec(editor, filePath) + + if err != nil { + fmt.Println(err) + } +} + func ViewFile(filePath string) string { if _, err := os.Stat(filePath); os.IsNotExist(err) { fmt.Printf("Error: The file for path '%s' was not found\n", filePath) diff --git a/internal/lib/run.go b/internal/lib/run.go new file mode 100644 index 0000000..48318ff --- /dev/null +++ b/internal/lib/run.go @@ -0,0 +1,22 @@ +package lib + +import ( + "fmt" + "os" + "os/exec" +) + +func Exec(args ...string) error { + path, err := exec.LookPath(args[0]) + + if err != nil { + fmt.Println(err) + } + + cmd := exec.Command(path, args[1:]...) + cmd.Stderr = os.Stderr + cmd.Stdin = os.Stdin + cmd.Stdout = os.Stdout + + return cmd.Run() +} diff --git a/internal/lib/zet.go b/internal/lib/zet.go index 4ca8c9d..2e2f50d 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -12,6 +12,12 @@ import ( "strings" ) +func EditZet(id int) { + zetPath := path.Join(GetZetDir(), strconv.Itoa(id), "index.adoc") + + EditFile(zetPath) +} + func GetAllZets() []int { zets, err := execGitCommand("ls-files") From 2537b4db9e4c0efffc711d741f0c4497a63d7048 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Wed, 24 Sep 2025 19:41:32 +0100 Subject: [PATCH 11/15] Refactor Signed-off-by: Oliver Davies --- cmd/view.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cmd/view.go b/cmd/view.go index d03d299..a06846b 100644 --- a/cmd/view.go +++ b/cmd/view.go @@ -5,9 +5,9 @@ import ( "os" "strconv" - "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" "github.com/spf13/cobra" - // "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" ) var viewCmd = &cobra.Command{ From 59c4d132b242f089bbbd9530387a063a57def1f5 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Thu, 25 Sep 2025 23:30:22 +0100 Subject: [PATCH 12/15] Commit the zettel after saving Signed-off-by: Oliver Davies --- internal/lib/git.go | 25 ++++++++++++++++++++++++- internal/lib/zet.go | 8 ++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) diff --git a/internal/lib/git.go b/internal/lib/git.go index 30abd4a..4ffb8a2 100644 --- a/internal/lib/git.go +++ b/internal/lib/git.go @@ -1,6 +1,18 @@ package lib -import "os/exec" +import ( + "os" + "os/exec" + "strconv" +) + +func CommitZettel(id int, title string) { + idString := strconv.Itoa(id) + + runGitCommand("add", idString) + runGitCommand("commit", "-m", title) + runGitCommand("push") +} func execGitCommand(parts ...string) (string, error) { args := append([]string{"-C", GetZetDir()}, parts...) @@ -10,3 +22,14 @@ func execGitCommand(parts ...string) (string, error) { return string(output), err } + +func runGitCommand(parts ...string) { + args := append([]string{"-C", GetZetDir()}, parts...) + command := exec.Command("git", args...) + + command.Stderr = os.Stderr + command.Stdin = os.Stdin + command.Stdout = os.Stdout + + command.Run() +} diff --git a/internal/lib/zet.go b/internal/lib/zet.go index 2e2f50d..766240e 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -16,6 +16,8 @@ func EditZet(id int) { zetPath := path.Join(GetZetDir(), strconv.Itoa(id), "index.adoc") EditFile(zetPath) + + onSave(id) } func GetAllZets() []int { @@ -136,3 +138,9 @@ func getTitleFromFile(filePath string) string { return "" } + +func onSave(id int) { + title := getTitle(id) + + CommitZettel(id, title) +} From b2f7f7af7f05f877324947fc3db6a5e11a476cfc Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Fri, 26 Sep 2025 09:33:16 +0100 Subject: [PATCH 13/15] Create a new zettel with a given title Signed-off-by: Oliver Davies --- cmd/create.go | 32 ++++++++++++++++++++++++++++++++ cmd/root.go | 1 + internal/lib/zet.go | 45 +++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 78 insertions(+) create mode 100644 cmd/create.go diff --git a/cmd/create.go b/cmd/create.go new file mode 100644 index 0000000..0df2c13 --- /dev/null +++ b/cmd/create.go @@ -0,0 +1,32 @@ +package cmd + +import ( + "strings" + + "github.com/spf13/cobra" + + "code.oliverdavies.uk/opdavies/cmd-zet/internal/lib" +) + +var createCmd = &cobra.Command{ + Use: "create", + Aliases: []string{"e"}, + Short: "A brief description of your command", + Long: `A longer description that spans multiple lines and likely contains examples +and usage of using your command. For example: + +Cobra is a CLI library for Go that empowers applications. +This application is a tool to generate the needed files +to quickly create a Cobra application.`, + Run: func(cmd *cobra.Command, args []string) { + title := "" + if len(args) > 0 { + title = strings.Join(args, " ") + } + + lib.CreateZet(title) + + // TODO: Edit the file + // TODO: Commit the changes + }, +} diff --git a/cmd/root.go b/cmd/root.go index 6b68650..a3d98ad 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -31,6 +31,7 @@ func Execute() { } func init() { + rootCmd.AddCommand(createCmd) rootCmd.AddCommand(editCmd) rootCmd.AddCommand(findCmd) rootCmd.AddCommand(titlesCmd) diff --git a/internal/lib/zet.go b/internal/lib/zet.go index 766240e..b0e4f92 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -5,6 +5,7 @@ import ( "fmt" "log" "os" + "os/exec" "path" "regexp" "sort" @@ -12,6 +13,32 @@ import ( "strings" ) +func CreateZet(title string) { + zid := newZid() + + fmt.Println(title, zid) + + path := path.Join(GetZetDir(), strconv.Itoa(zid)) + + os.Mkdir(path, 0750) + + filePath := fmt.Sprintf("%s/index.adoc", path) + + file, err := os.Create(filePath) + + if err != nil { + log.Fatal(err) + } + + defer file.Close() + + _, err = fmt.Fprintf(file, "= %s", title) + + if err != nil { + log.Fatal(err) + } +} + func EditZet(id int) { zetPath := path.Join(GetZetDir(), strconv.Itoa(id), "index.adoc") @@ -139,6 +166,24 @@ func getTitleFromFile(filePath string) string { return "" } +func newZid() int { + cmd := exec.Command("ls", GetZetDir()) + output, _ := cmd.CombinedOutput() + + zets := strings.Split(string(output), "\n") + + var zetCount int + + for _, zet := range zets { + num, err := strconv.Atoi(zet) + if err == nil && num > zetCount { + zetCount = num + } + } + + return zetCount + 1 +} + func onSave(id int) { title := getTitle(id) From a344f7a91364d107f5de0f9358678d1224300584 Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Fri, 26 Sep 2025 12:17:37 +0100 Subject: [PATCH 14/15] Edit the new zettel and commit the changes Signed-off-by: Oliver Davies --- cmd/create.go | 4 +--- internal/lib/zet.go | 4 ++++ 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/cmd/create.go b/cmd/create.go index 0df2c13..c11824a 100644 --- a/cmd/create.go +++ b/cmd/create.go @@ -20,13 +20,11 @@ This application is a tool to generate the needed files to quickly create a Cobra application.`, Run: func(cmd *cobra.Command, args []string) { title := "" + if len(args) > 0 { title = strings.Join(args, " ") } lib.CreateZet(title) - - // TODO: Edit the file - // TODO: Commit the changes }, } diff --git a/internal/lib/zet.go b/internal/lib/zet.go index b0e4f92..2fdfeb8 100644 --- a/internal/lib/zet.go +++ b/internal/lib/zet.go @@ -37,6 +37,10 @@ func CreateZet(title string) { if err != nil { log.Fatal(err) } + + EditFile(filePath) + + onSave(zid) } func EditZet(id int) { From 06167c4b67bb6146819ff4bb0e4a1ecdde9882bf Mon Sep 17 00:00:00 2001 From: Oliver Davies Date: Fri, 26 Sep 2025 12:24:08 +0100 Subject: [PATCH 15/15] Fix create aliases --- cmd/create.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd/create.go b/cmd/create.go index c11824a..e5c2fcc 100644 --- a/cmd/create.go +++ b/cmd/create.go @@ -10,7 +10,7 @@ import ( var createCmd = &cobra.Command{ Use: "create", - Aliases: []string{"e"}, + Aliases: []string{"c", "n", "new"}, Short: "A brief description of your command", Long: `A longer description that spans multiple lines and likely contains examples and usage of using your command. For example: