aboutsummaryrefslogtreecommitdiff
path: root/cmd
diff options
context:
space:
mode:
authorXe Iaso <me@xeiaso.net>2024-05-09 12:55:15 -0400
committerXe Iaso <me@xeiaso.net>2024-05-09 12:57:45 -0400
commit3a943a2986151aefc61923cef5b2c84edb266279 (patch)
tree22a80d65982d60e32cd0c30e0d34572b3e62144c /cmd
parentd53a5ffc052469c11c5312edb51bc8590eb7d21f (diff)
downloadx-3a943a2986151aefc61923cef5b2c84edb266279.tar.xz
x-3a943a2986151aefc61923cef5b2c84edb266279.zip
cmd/sapientwindex: clean up for general usage
Signed-off-by: Xe Iaso <me@xeiaso.net>
Diffstat (limited to 'cmd')
-rw-r--r--cmd/sapientwindex/README.md92
-rw-r--r--cmd/sapientwindex/main.go34
-rw-r--r--cmd/sapientwindex/manifest.yaml15
-rw-r--r--cmd/sapientwindex/yeetfile.js15
4 files changed, 132 insertions, 24 deletions
diff --git a/cmd/sapientwindex/README.md b/cmd/sapientwindex/README.md
new file mode 100644
index 0000000..dd6a3b7
--- /dev/null
+++ b/cmd/sapientwindex/README.md
@@ -0,0 +1,92 @@
+# sapientwindex
+
+sapientwindex is a Reddit -> Discord bot. It will monitor a subreddit
+(or group of subreddits) and then post any new posts to a given
+channel by webhook.
+
+<details>
+ <summary>If you know what "Kubernetes" means and you have your own cluster</summary>
+
+If you have a Kubernetes cluster, create a generic secret called
+`sapientwindex` in the default namespace with the following fields:
+
+* `DISCORD_WEBHOOK_URL`: The webhook URL to use for Discord
+* `REDDIT_USERNAME`: Your reddit username
+* `SUBREDDITS`: The subreddits you want to scrape, separated by commas
+
+Run `kubectl apply -f manifest.yaml` and you should be good.
+
+Updating the service is done by restarting the deployment:
+
+```
+kubectl rollout restart deployments/sapientwindex
+```
+
+Change the namespace of the manifest if running this in a separate
+namespace is desired.
+
+</details>
+
+## Prerequisites for self-hosting
+
+In order to host this yourself, you need the following things:
+
+* A linux system that is on 24/7 to run this on (WSL on a gaming tower
+ is fine)
+* An x86-64 CPU (any computer sold in the last decade is fine)
+* A discord webhook for the channel in question
+* A reddit account for attributing the bot to yourself
+* A list of subreddits to monitor
+
+1. Install [Docker
+ Desktop](https://docs.docker.com/desktop/install/windows-install/)
+1. Run the following command to start the sapientwindex service:
+ ```
+ docker run --name sapientwindex -e DISCORD_WEBHOOK_URL=<paste webhook here> -e REDDIT_USERNAME=<your reddit username> -e SUBREDDITS=<list,of,subreddits> -dit ghcr.io/xe/x/sapientwindex:latest
+ ```
+1. Run the following command to verify that the bot has started:
+ ```
+ docker logs sapientwindex
+ ```
+ If you see a message like this:
+ ```
+ {"time":"2024-05-09T16:39:08.546206894Z","level":"INFO","source":{"function":"main.main","file":"within.website/x/cmd/sapientwindex/main.go","line":28},"msg":"starting up","subreddit":"tulpas","scan_duration":"30s"}
+ ```
+ then everything is good to go.
+
+### Updating the bot
+
+To update the bot, run these commands:
+
+1. Pull the latest version of the sapientwindex container:
+ ```
+ docker pull ghcr.io/xe/x/sapientwindex:latest
+ ```
+1. Delete the old version of your sapientwindex container:
+ ```
+ docker rm -f sapientwindex
+ ```
+1. Run the start command again:
+ ```
+ docker run --name sapientwindex -e DISCORD_WEBHOOK_URL=<paste webhook here> -e REDDIT_USERNAME=<your reddit username> -e SUBREDDITS=<list,of,subreddits> -dit ghcr.io/xe/x/sapientwindex:latest
+ ```
+
+Updates to the bot will be done very infrequently.
+
+## Hosted option
+
+For a nominal fee, I can host a copy of this bot for you on my
+homelab. Please [contact me](sapientwindexsales@xeserv.us) to arrange
+terms for this hosted option.
+
+## Support
+
+Support is done by [GitHub issues](https://github.com/Xe/x/issues) on
+a best-effort basis, with priority to [people subscribed to me on
+Patreon](https://patreon.com/cadey). If you deploy this bot in your
+community, a subscription would be greatly appreciated.
+
+Support can also be done by email at `sapientwindex@xeserv.us`. Again,
+priority support will be given to [my
+patrons](https://patreon.com/cadey) with all other support being done
+on a best-effort basis.
diff --git a/cmd/sapientwindex/main.go b/cmd/sapientwindex/main.go
index ced3658..4c947b5 100644
--- a/cmd/sapientwindex/main.go
+++ b/cmd/sapientwindex/main.go
@@ -6,35 +6,54 @@ import (
"log"
"log/slog"
"net/http"
+ "os"
"strings"
"time"
"github.com/Marcel-ICMC/graw"
"github.com/Marcel-ICMC/graw/reddit"
"within.website/x/internal"
+ "within.website/x/internal/yeet"
"within.website/x/web/discordwebhook"
)
var (
- discordWebhookURL = flag.String("discord-webhook-url", "", "discord webhook url")
- redditUserAgent = flag.String("reddit-user-agent", "graw:windex:0.0.1 by /u/shadowh511", "reddit user agent")
- subreddit = flag.String("subreddit", "tulpas", "subreddit to post to")
+ discordWebhookURL = flag.String("discord-webhook-url", "", "The Discord webhook url sapientwindex will post to")
+ redditUsername = flag.String("reddit-username", "", "Your reddit username")
+ subreddits = flag.String("subreddits", "", "subreddits to scan (separate multiple by commas)")
scanDuration = flag.Duration("scan-duration", 30*time.Second, "scan frequency")
)
func main() {
internal.HandleStartup()
- slog.Info("starting up", "subreddit", *subreddit, "scan_duration", (*scanDuration).String())
+ if *discordWebhookURL == "" {
+ slog.Error("you must set the discord webhook URL to use this bot")
+ os.Exit(2)
+ }
+
+ if *redditUsername == "" {
+ slog.Error("you must set your reddit username to use this bot")
+ os.Exit(2)
+ }
+
+ if *subreddits == "" {
+ slog.Error("you must set the subreddit list to use this bot")
+ os.Exit(2)
+ }
+
+ redditUserAgent := fmt.Sprintf("graw:within.website/x/cmd/sapientwindex:%s by /u/%s", yeet.DateTag, *redditUsername)
+
+ slog.Info("starting up", "subreddits", *subreddits, "scan_duration", (*scanDuration).String())
- handle, err := reddit.NewScript(*redditUserAgent, *scanDuration)
+ handle, err := reddit.NewScript(redditUserAgent, *scanDuration)
if err != nil {
log.Fatal(err)
}
announce := &announcer{}
scriptCfg := graw.Config{
- Subreddits: []string{*subreddit},
+ Subreddits: strings.Split(*subreddits, ","),
Logger: slog.NewLogLogger(slog.Default().Handler(), slog.LevelInfo),
}
@@ -47,6 +66,7 @@ func main() {
wait()
stop()
+ slog.Info("connection lost, sleeping and retrying")
time.Sleep(5 * time.Second)
}
}
@@ -73,7 +93,7 @@ func (a announcer) Post(post *reddit.Post) error {
wh := discordwebhook.Webhook{
Username: post.Author,
Content: fmt.Sprintf("## %s\n> %s\n<https://reddit.com%s>", post.Title, addMemeArrow(post.SelfText), post.Permalink),
- AvatarURL: fmt.Sprintf("https://cdn.xeiaso.net/avatar/%s", internal.Hash(post.Author, *redditUserAgent)),
+ AvatarURL: fmt.Sprintf("https://cdn.xeiaso.net/avatar/%s", internal.Hash(post.Author, *redditUsername)),
AllowedMentions: map[string][]string{
"parse": {},
},
diff --git a/cmd/sapientwindex/manifest.yaml b/cmd/sapientwindex/manifest.yaml
index 3308ae8..b5cc412 100644
--- a/cmd/sapientwindex/manifest.yaml
+++ b/cmd/sapientwindex/manifest.yaml
@@ -17,12 +17,23 @@ spec:
labels:
app.kubernetes.io/name: sapientwindex
spec:
- containers:
+ containers:
- name: bot
image: ghcr.io/xe/x/sapientwindex:latest
+ imagePullPolicy: "Always"
env:
+ - name: REDDIT_USERNAME
+ valueFrom:
+ secretKeyRef:
+ name: sapientwindex
+ key: REDDIT_USERNAME
+ - name: SUBREDDITS
+ valueFrom:
+ secretKeyRef:
+ name: sapientwindex
+ key: SUBREDDITS
- name: DISCORD_WEBHOOK_URL
valueFrom:
secretKeyRef:
name: sapientwindex
- key: DISCORD_WEBHOOK_URL \ No newline at end of file
+ key: DISCORD_WEBHOOK_URL
diff --git a/cmd/sapientwindex/yeetfile.js b/cmd/sapientwindex/yeetfile.js
index 4d6b49a..aed9798 100644
--- a/cmd/sapientwindex/yeetfile.js
+++ b/cmd/sapientwindex/yeetfile.js
@@ -1,19 +1,4 @@
nix.build(".#docker.sapientwindex");
docker.load("./result");
-const image = `ghcr.io/xe/x/sapientwindex:${yeet.datetag}`;
-docker.tag("ghcr.io/xe/x/sapientwindex", image);
docker.push(`ghcr.io/xe/x/sapientwindex`);
-docker.push(image);
yeet.run("kubectl", "apply", "-f=manifest.yaml");
-yeet.run("kubectl", "patch", "deployment", "sapientwindex", "--subresource='spec'", "--type='merge'", "-p", JSON.stringify({
- spec: {
- templates: {
- spec: {
- containers: [{
- name: "bot",
- image
- }]
- }
- }
- }
-}));