From 2ab278fc5da19208dceb9e6af9033205d255324a Mon Sep 17 00:00:00 2001 From: Shin'ya Minazuki Date: Mon, 29 Dec 2025 22:53:47 -0300 Subject: [PATCH] Initial message to the past Signed-off-by: Shin'ya Minazuki --- COPYING | 15 +++++++++ Makefile | 13 ++++++++ README.md | 17 ++++++++++ cmd/mikuru-login/main.go | 67 ++++++++++++++++++++++++++++++++++++++++ config.go | 22 +++++++++++++ go.mod | 17 ++++++++++ go.sum | 36 +++++++++++++++++++++ mikuru.1 | 17 ++++++++++ version.go | 14 +++++++++ 9 files changed, 218 insertions(+) create mode 100644 COPYING create mode 100644 Makefile create mode 100644 README.md create mode 100644 cmd/mikuru-login/main.go create mode 100644 config.go create mode 100644 go.mod create mode 100644 go.sum create mode 100644 mikuru.1 create mode 100644 version.go diff --git a/COPYING b/COPYING new file mode 100644 index 0000000..97ff0a9 --- /dev/null +++ b/COPYING @@ -0,0 +1,15 @@ +ISC License (ISCL) + +Copyright (C) 2025 Shin'ya Minazuki + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH +REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY +AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT, +INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM +LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE +OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR +PERFORMANCE OF THIS SOFTWARE. diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..20004d0 --- /dev/null +++ b/Makefile @@ -0,0 +1,13 @@ +GO = go +GOFLAGS = -v -ldflags "-w -X mikuru.Version=${VERSION} -X mikuru.Rev=${REVISION}" +REVISION = `git rev-list --all | wc -l` +VERSION = HEAD + +PROGRAMS = mikuru-login \ + mikuru-post \ + mikuru-timeline + +build: + ${GO} build ${GOFLAGS} ./cmd/${PROGRAMS} +clean: + rm -f ${PROGRAMS} diff --git a/README.md b/README.md new file mode 100644 index 0000000..746488c --- /dev/null +++ b/README.md @@ -0,0 +1,17 @@ +# Mikuru +[Yarn.social](https://yarn.social) client where each task (except for logout) is handled by a separate program. + +## Current status +* [X] Login +* [ ] Posting +* [ ] Timeline + +## License +[ISC](COPYING) + +## Requirements +* [Go](https://go.dev) (>=1.20) + +## Where did the name come from? +Huh? I couldn't possibly tell you about that! +Tee hee, it's classified information! diff --git a/cmd/mikuru-login/main.go b/cmd/mikuru-login/main.go new file mode 100644 index 0000000..2ca12f2 --- /dev/null +++ b/cmd/mikuru-login/main.go @@ -0,0 +1,67 @@ +package main + +import ( + "fmt" + "os" + "syscall" + + "golang.org/x/term" + "go.yarn.social/client" + "git.laidback.moe/shinyoukai/mikuru" +) + +var ( + username string + password string +) + +func init() { + xdg_config_home, err := os.UserConfigDir() + if err != nil { + fmt.Println("Unable to obtain user's configuration directory") + os.Exit(1) + } + configPath := xdg_config_home + "/mikuru.ini" + mikuru.Parse(configPath) +} + +func main() { + cli, err := client.NewClient(client.WithURI(mikuru.Config.Host)) + if err != nil { + fmt.Printf("%s", err) + fmt.Println("Error creating client") + os.Exit(1) + } + signin(cli) +} +func signin(cli *client.Client) { + fmt.Printf("Username: ") + fmt.Scanln(&username) + + if len(username) == 0 { + fmt.Println("No value. Bailing out") + os.Exit(1) + } + + fmt.Printf("Password: ") + data, err := term.ReadPassword(int(syscall.Stdin)) + if err != nil { + fmt.Printf("Unable to obtain password: %s\n", err) + os.Exit(1) + } + + password := string(data) + + res, err := cli.Login(username, password) + + if err != nil { + fmt.Println("Unable to login") + os.Exit(1) + } + + fmt.Println("Login successful") + fmt.Println("Place this token in your configuration file for later use") + fmt.Println("Do not share it with anyone, it's classified information") + fmt.Println("Trim surrounding braces before usage") + fmt.Printf("token = %v\n", res) +} diff --git a/config.go b/config.go new file mode 100644 index 0000000..8b7967d --- /dev/null +++ b/config.go @@ -0,0 +1,22 @@ +package mikuru + +import ( + "gopkg.in/ini.v1" +) + +var Config struct { + Host string + Token string +} + +func Parse(file string) error { + cfg, err := ini.Load(file) + if err != nil { + return err + } + + Config.Host = cfg.Section("mikuru").Key("host").String() + Config.Token = cfg.Section("mikuru").Key("token").String() + + return nil +} diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..fa72190 --- /dev/null +++ b/go.mod @@ -0,0 +1,17 @@ +module git.laidback.moe/shinyoukai/mikuru + +go 1.20 + +require ( + go.yarn.social/client v0.0.0-20250420114029-410ad71a453e + golang.org/x/term v0.38.0 + gopkg.in/ini.v1 v1.67.0 +) + +require ( + github.com/sirupsen/logrus v1.9.3 // indirect + github.com/stretchr/testify v1.11.1 // indirect + go.yarn.social/types v0.0.0-20250420113154-c5a6df6d2f22 // indirect + golang.org/x/sys v0.39.0 // indirect + gopkg.in/yaml.v2 v2.4.0 // indirect +) diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..f0bcce3 --- /dev/null +++ b/go.sum @@ -0,0 +1,36 @@ +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0= +github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk= +github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= +github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/rogpeppe/go-internal v1.8.0 h1:FCbCCtXNOY3UtUuHUYaghJg4y7Fd14rXifAYUAtL9R8= +github.com/rogpeppe/go-internal v1.8.0/go.mod h1:WmiCO8CzOY8rg0OYDC4/i/2WRWAB6poM+XZ2dLUbcbE= +github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ= +github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U= +github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U= +go.yarn.social/client v0.0.0-20250420114029-410ad71a453e h1:A4wok2/cSAbvWLjHhtCrW8dvv1XlgcGRj7H15150HhA= +go.yarn.social/client v0.0.0-20250420114029-410ad71a453e/go.mod h1:+VjffjmcZMHIudGsZlnbPnavk0oSK6xf4olzExiojhg= +go.yarn.social/types v0.0.0-20250420113154-c5a6df6d2f22 h1:M34aQ3AaRKE2t7JOLwoemJ65r0e8c1z4TwuHzogHvZE= +go.yarn.social/types v0.0.0-20250420113154-c5a6df6d2f22/go.mod h1:+xnDkQ0T0S8emxWIsvxlCAoyF8gBaj0q81hr/VrKc0c= +golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.39.0 h1:CvCKL8MeisomCi6qNZ+wbb0DN9E5AATixKsvNtMoMFk= +golang.org/x/sys v0.39.0/go.mod h1:OgkHotnGiDImocRcuBABYBEXf8A9a87e/uXjp9XT3ks= +golang.org/x/term v0.38.0 h1:PQ5pkm/rLO6HnxFR7N2lJHOZX6Kez5Y1gDSJla6jo7Q= +golang.org/x/term v0.38.0/go.mod h1:bSEAKrOT1W+VSu9TSCMtoGEOUcKxOKgl3LE5QEF/xVg= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= +gopkg.in/ini.v1 v1.67.0 h1:Dgnx+6+nfE+IfzjUEISNeydPJh9AXNNsWbGP9KzCsOA= +gopkg.in/ini.v1 v1.67.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k= +gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= +gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= +gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/mikuru.1 b/mikuru.1 new file mode 100644 index 0000000..ffabccd --- /dev/null +++ b/mikuru.1 @@ -0,0 +1,17 @@ +.Dd December 30, 2025 +.Dt MIKURU 1 +.Os +.Sh NAME +.Nm mikuru +.Nd A yarn-compatible twtxt client from the future +.Sh SYNOPSIS +.Nm +.Sh DESCRIPTION +This client has every single part of its functionality +handled by a separate program. +.Sh SEE ALSO +.Xr mikuru-login 1 +.Xr mikuru-post 1 +.Xr mikuru-timeline 1 +.Sh AUTHORS +.An Shin'ya Minazuki Aq Mt shinyoukai@laidback.moe diff --git a/version.go b/version.go new file mode 100644 index 0000000..8b8cb59 --- /dev/null +++ b/version.go @@ -0,0 +1,14 @@ +package mikuru + +import ( + "fmt" +) + +var ( + Revision = "0" + Version = "0" +) + +func PrintVersion() string { + return fmt.Sprintf("%s (%s)", Version, Revision) +}