Coder Social home page Coder Social logo

mrusme / neonmodem Goto Github PK

View Code? Open in Web Editor NEW
499.0 9.0 22.0 2.36 MB

Neon Modem Overdrive

Home Page: https://neonmodem.com

License: GNU General Public License v3.0

Makefile 0.19% Go 99.81%
api api-client bbs bulletin-board bulletin-board-system bulletinboard cli command-line command-line-tool discourse

neonmodem's Introduction

Neon Modem Overdrive

Chat on Matrix

Neon Modem Overdrive

Neon Modem Overdrive is a BBS-style command line client that supports Discourse, Lemmy, Lobsters and Hacker News as backends, and seamlessly integrates all of them into a streamlined TUI. And yes, you heard that right, I really did call it Neon Modem Overdrive.

Neon Modem is built in Go, using Charm's Bubble Tea TUI framework, but implements an own window manager (or compositor if you want) that allows it to use a third dimension, on top of the two dimensional rendering that Bubble Tea offers today. With that it is possible to display dialogs on top of one another, in order to offer a smoother UI experience.

More info here!

Support

System Available List Forums List Posts List Replies Create Post Create Reply
Discourse ✔️ ✔️ ✔️ ✔️ ✔️ ✔️
Lemmy ✔️ ✔️ ✔️ ✔️ ✔️ ✔️
Lobsters ✔️ ✔️ ✔️ ✔️
Hacker News ✔️ ✔️ ✔️ ✔️
RSS+Disqus/Isso(?)
Superhighway84
NNTP

Installation

From Release

Download the latest release and unpack it:

$ tar -xzf ./neonmodem_*.tar.gz

The binary is called neonmodem. Feel free to move it to e.g. /usr/local/bin.

From Sauce

Clone this repository

Then cd into the cloned directory and run:

make

The binary is called neonmodem. Feel free to move it to e.g. /usr/local/bin.

For Arch Linux an AUR package is available here: https://aur.archlinux.org/packages/neonmodem

Install with your favorite AUR helper.

On NetBSD, a package is available from the official repositories. To install it, simply run pkgin install neonmodem.

Configuration

Before launching Neon Modem Overdrive it requires initial setup of the services (a.k.a. systems). Run neonmodem connect --help to find out more.

Connecting a service will add it to the configuration TOML.

Linux/Unix

~/.config/neonmodem.toml

MacOS

$HOME/Library/Application\ Support/neonmodem.toml

Systems

Discourse

For connecting to a Discourse instance you'll need to have an active account on that instance. Neon Modem will store the instance URL, username and a user key, but no password.

neonmodem connect --type discourse --url https://www.keebtalk.com

Lemmy

For connecting to a Lemmy instance you'll need to have an active account on that instance. Neon Modem will store the instance URL, username and password.

neonmodem connect --type lemmy --url https://lemmy.ml

Lobsters

For connecting to a Lobsters instance you won't need an account, as the integration is read-only. Neon Modem will store the instance URL.

neonmodem connect --type lobsters --url https://lobste.rs

Hacker News

For connecting to Hacker News you won't need an account, as the integration is read-only.

neonmodem connect --type hackernews

UI

The UI can be fully customized via the Theme section in the configuration file. To reset settings, all theme related configurations can simply be deleted from the configuration.

Run

After setup Neon Modem can be launched by calling neonmodem without any arguments. It will briefly display a splash screen, then switch to the posts list, which will aggregate the latest posts from all connected systems. A progress icon will be visible in the header while network requests are loading.

Usage

Neon Modem Overdrive

Navigation

In the posts list:

  • j: Scroll down
  • k: Scroll up
  • r/enter: Open selected post
  • n: Write new post in on the system/forum of the current selected post
  • C-e: Open system selector
  • C-t: Open forum selector
  • q/esc: Quit

In the post view dialog:

  • r: Reply to post
  • #r: Reply to specific comment # in post, e.g. 3r to reply to the reply #3
  • z: Load older replies (if available)
  • esc: Close dialog

In the new post / new reply dialog:

  • tab: Switch between elements (only in new post dialog)
  • C-s: Submit post/reply
  • esc: Close dialog

FAQ

  • Q: The post view is really slow when using a large terminal.
    A: Turning off image rendering will improve performance significantly on very large terminal windows and can be done by setting RenderImages = false in the configuration.
  • Q: Can I haz Reddit?
    A: I won't do the heavy lifting of integrating a proprietary platform with a $15 billion valuation that can't even be bothered to maintain a solid set of client API libraries. If you feel like, go ahead and PR!

neonmodem's People

Contributors

0323pin avatar breadmakesyoufat avatar dan-m8t avatar dependabot[bot] avatar dorii avatar flaviu-toader avatar greenfoo avatar monokrome avatar mrusme avatar tedwardd avatar tydavis avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

neonmodem's Issues

External editor

While the Bubble Tea textarea is great for quickly hacking in a response to a post, for more longform things it would be better to allow launching the external $EDITOR the way Superhighway84 has done it ever since.

The idea is to provide a shortcut for the new post/reply dialog window (e.g. ctrl+o) that would...

  • ... create a temporary text file under $TMP
  • launch $EDITOR with that temporary file in the foreground
  • Read in the temporary file on re-activation and write its contents in the textarea

Local caching

At some point it might make sense to implement a local cache of posts and replies to improve loading times over slow connections.

TODO

  • #11
  • Store posts/replies in local storage
  • Load posts/replies from local storage
  • Refresh cached data based on API cache-control/etag/etc.

loadSystems crashes with wrong Lemmy password

panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x80 pc=0x563d981d6ad1]

goroutine 1 [running]:
github.com/mrusme/neonmodem/cmd.loadSystems(0xc000456000)
github.com/mrusme/neonmodem/cmd/root.go:98 +0xf1
github.com/mrusme/neonmodem/cmd.glob..func1(0x563d98b4a1c0?, {0x563d981dbc8c?, 0x0?, 0x0?})
github.com/mrusme/neonmodem/cmd/root.go:115 +0xdc
github.com/spf13/cobra.(*Command).execute(0x563d98b4a1c0, {0xc000024240, 0x0, 0x0})
github.com/spf13/[email protected]/command.go:920 +0x847
github.com/spf13/cobra.(*Command).ExecuteC(0x563d98b4a1c0)
github.com/spf13/[email protected]/command.go:1044 +0x3bd
github.com/spf13/cobra.(*Command).Execute(...)
github.com/spf13/[email protected]/command.go:968
github.com/mrusme/neonmodem/cmd.Execute(0xc0000061a0?)
github.com/mrusme/neonmodem/cmd/root.go:127 +0x3e
main.main()
github.com/mrusme/neonmodem/neonmodem.go:13 +0x25

can find the file to try to figure out what its not working.. Any ideas?

Add proxy configuration

Neon Modem should support proxies, so that it could be connected to services running in Tor, I2P, etc.

Correctly handle incorrect system URLs

Hi, I'm a bit of a noob and I can't seem to get neonmodem working - neither by using the binary nor by building it myself. I'd appreciate any help!

OS: Pop!_OS 22.04 LTS
KERNEL: Linux pop-os 6.2.6-76060206-generic #202303130630~1685473338~22.04~995127e SMP PREEMPT_DYNAMIC Tue M x86_64 x86_64 x86_64 GNU/Linux

I've installed the latest stable Go to /usr/local/go after finding the upstream Go packages for my distro are too old.

The make command builds the binary successfully without error.

After building from Source:

~/Documents/dev/neonmodem$ ./neonmodem 
panic: Error(s) loading system(s)

goroutine 1 [running]:
github.com/mrusme/neonmodem/cmd.glob..func1(0x1781720?, {0xeae714?, 0x0?, 0x0?})
	/home/user/Documents/dev/neonmodem/cmd/root.go:128 +0x267
github.com/spf13/cobra.(*Command).execute(0x1781720, {0xc000098200, 0x0, 0x0})
	/home/user/go/pkg/mod/github.com/spf13/[email protected]/command.go:944 +0x847
github.com/spf13/cobra.(*Command).ExecuteC(0x1781720)
	/home/user/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068 +0x3bd
github.com/spf13/cobra.(*Command).Execute(...)
	/home/user/go/pkg/mod/github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute(0xc0000061a0?)
	/home/user/Documents/dev/neonmodem/cmd/root.go:141 +0x3e
main.main()
	/home/user/Documents/dev/neonmodem/neonmodem.go:13 +0x25

Attempting to use Binary:

~/bin$ neonmodem 
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x80 pc=0xd45616]

goroutine 1 [running]:
github.com/mrusme/neonmodem/cmd.loadSystems(0xc000454780)
	/home/runner/work/neonmodem/neonmodem/cmd/root.go:105 +0xb6
github.com/mrusme/neonmodem/cmd.glob..func1(0x1770140?, {0xe9628b?, 0x0?, 0x0?})
	/home/runner/work/neonmodem/neonmodem/cmd/root.go:122 +0xdc
github.com/spf13/cobra.(*Command).execute(0x1770140, {0xc000022230, 0x0, 0x0})
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944 +0x847
github.com/spf13/cobra.(*Command).ExecuteC(0x1770140)
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068 +0x3bd
github.com/spf13/cobra.(*Command).Execute(...)
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute(0xc0000061a0?)
	/home/runner/work/neonmodem/neonmodem/cmd/root.go:134 +0x3e
main.main()
	/home/runner/work/neonmodem/neonmodem/neonmodem.go:13 +0x25

Allow `n` in post view

Allow to press n in post view to create a new post in the current post's system/forum.

Make sure directories exist

neonmodem just exits loudly if $HOME/.config (for connect) or $HOME/.cache (always) do not exist.
I think it should create the directories if it needs them.

Connecting new Discourse systems results in 500 Internal Server Errors

Hi, thanks for making a this tool - love the design and UI! I am trying to connect different Discourse systems but every single one is giving an

Oops
The software powering this discussion forum encountered an unexpected problem. We apologize for the inconvenience.

response. I've tried with 3 different Discourse implementations, such as

neonmodem connect --type discourse --url https://community.openstreetmap.org
neonmodem connect --type discourse --url https://discourse.nixos.org
neonmodem connect --type discourse --url https://discourse.pollination.cloud

This definitely seems like an upstream problem, because several other implementations , such as

all have the same problem. But, I found this Observable notebook that does work, oddly enough. It's using node-forge for the PKI; not sure if that's relevant.

Again, this definitely seems like a Discourse problem, but I just wanted to flag it here in case something obvious stands out.

sixel support?

love this app, it's amazing! thought I'd drop a suggustion with images to use sixel? it's growing in support and works really well I've found with other terminal applications.

[Discourse] IPFS works, Caddy does not. Why?

Hello!

First off: I am so down with this synthwave branding, I love it! :D

Now, after getting the bin, I configured three sources:

  • discuss.ipfs.tech (Discourse)
  • caddy.community (Discourse)
  • drachennetz.com (Lemmy)

The Lemmy instance doesnt work either - but that is already in #23 .

The IPFS community works flawlessly - but the Caddy one, doe snot:

{"level":"error","ts":1686839701.429568,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: json: cannot unmarshal bool into Go struct field CategoryModel.category_list.categories.sort_ascending of type string\n","stacktrace":"github.com/mrusme/neonmodem/aggregator.(*Aggregator).ListPosts\n\t/home/runner/work/neonmodem/neonmodem/aggregator/aggregator.go:77\ngithub.com/mrusme/neonmodem/ui/views/posts.(*Model).refresh.func1\n\t/home/runner/work/neonmodem/neonmodem/ui/views/posts/posts.go:206\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/g║                                                                                                                                                                                                    ║                                                                 {"level":"error","ts":1686839701.430567,"caller":"posts/posts.go:209","msg":"[<nil> <nil> json: cannot unmarshal bool into Go struct ║   q quit • ? more                                                                                                                                                                                  ║ui/views/posts/posts.go:209\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/go/pkg/mod/github.com/charmbracelet/[email protected]/tea.go:247"}

The output was quite butchered in the view, so here is a screenshot:

image

Got any ideas for this?

Thanks and kind regards!

Integrate keyring

Right now this app saves user credentials in clear text in the toml config. Needless to say this is not safe. I'm not familiar with the go package ecosystem so I don't know what to recommend but I'm certain something like keyring for python exists for handling secrets in go.

Typing "q" while replying closes the reply prompt

After pressing "r" to reply, if I type anything with the letter "q" in it, it closes the reply prompt. (lemmy)

My system:
Kernel: Linux 5.19.0-46-generic
Distro: KDE Neon 5.27 x86_64
Terminal : konsole
Shell: Bash 5.1.16

400 Bad Request: missing_totp_token

Morning my good devs,

I have just downloaded the latest Mac arm64 build and connected it to my lemmy instance (https://lemmy.horwood.cloud/), but on starting neonmodem I get an error.

panic: Error(s) loading system(s)

goroutine 1 [running]:
github.com/mrusme/neonmodem/cmd.glob..func1(0x101edd0c0?, {0x1014b7db4?, 0x1?, 0x1?})
	/home/runner/work/neonmodem/neonmodem/cmd/root.go:128 +0x1ec
github.com/spf13/cobra.(*Command).execute(0x101edd0c0, {0x1400001e050, 0x1, 0x1})
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944 +0x5b0
github.com/spf13/cobra.(*Command).ExecuteC(0x101edd0c0)
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068 +0x35c
github.com/spf13/cobra.(*Command).Execute(...)
	/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute(0x1018206e0?)
	/home/runner/work/neonmodem/neonmodem/cmd/root.go:141 +0x58
main.main()
	/home/runner/work/neonmodem/neonmodem/neonmodem.go:13 +0x24

running with debug is the same, but a quick look in the logs show this is a login issue.

{"level":"error","ts":1688973078.467069,"caller":"cmd/root.go:97","msg":"error loading system: 400 Bad Request: missing_totp_token","stacktrace":"github.com/mrusme/neonmodem/cmd.loadSystems\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:97\ngithub.com/mrusme/neonmodem/cmd.glob..func1\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:123\ngithub.com/spf13/cobra.(*Command).execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:141\nmain.main\n\t/home/runner/work/neonmodem/neonmodem/neonmodem.go:13\nruntime.main\n\t/opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250"}
{"level":"error","ts":1688973078.467602,"caller":"cmd/root.go:126","msg":"400 Bad Request: missing_totp_token","stacktrace":"github.com/mrusme/neonmodem/cmd.glob..func1\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:126\ngithub.com/spf13/cobra.(*Command).execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:141\nmain.main\n\t/home/runner/work/neonmodem/neonmodem/neonmodem.go:13\nruntime.main\n\t/opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250"}
{"level":"error","ts":1688973129.346163,"caller":"cmd/root.go:97","msg":"error loading system: 400 Bad Request: missing_totp_token","stacktrace":"github.com/mrusme/neonmodem/cmd.loadSystems\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:97\ngithub.com/mrusme/neonmodem/cmd.glob..func1\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:123\ngithub.com/spf13/cobra.(*Command).execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:141\nmain.main\n\t/home/runner/work/neonmodem/neonmodem/neonmodem.go:13\nruntime.main\n\t/opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250"}
{"level":"error","ts":1688973129.346896,"caller":"cmd/root.go:126","msg":"400 Bad Request: missing_totp_token","stacktrace":"github.com/mrusme/neonmodem/cmd.glob..func1\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:126\ngithub.com/spf13/cobra.(*Command).execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\t/home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\t/home/runner/work/neonmodem/neonmodem/cmd/root.go:141\nmain.main\n\t/home/runner/work/neonmodem/neonmodem/neonmodem.go:13\nruntime.main\n\t/opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250"}
2023-07-10T08:12:36.739+0100    DEBUG   cmd/root.go:93  loading system of type lemmy ...
2023-07-10T08:12:37.224+0100    ERROR   cmd/root.go:97  error loading system: 400 Bad Request: missing_totp_token
github.com/mrusme/neonmodem/cmd.loadSystems
    /home/runner/work/neonmodem/neonmodem/cmd/root.go:97
github.com/mrusme/neonmodem/cmd.glob..func1
    /home/runner/work/neonmodem/neonmodem/cmd/root.go:123
github.com/spf13/cobra.(*Command).execute
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944
github.com/spf13/cobra.(*Command).ExecuteC
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068
github.com/spf13/cobra.(*Command).Execute
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute
    /home/runner/work/neonmodem/neonmodem/cmd/root.go:141
main.main
    /home/runner/work/neonmodem/neonmodem/neonmodem.go:13
runtime.main
    /opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250
2023-07-10T08:12:37.224+0100    ERROR   cmd/root.go:126 400 Bad Request: missing_totp_token
github.com/mrusme/neonmodem/cmd.glob..func1
    /home/runner/work/neonmodem/neonmodem/cmd/root.go:126
github.com/spf13/cobra.(*Command).execute
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:944
github.com/spf13/cobra.(*Command).ExecuteC
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:1068
github.com/spf13/cobra.(*Command).Execute
    /home/runner/go/pkg/mod/github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute
    /home/runner/work/neonmodem/neonmodem/cmd/root.go:141
main.main
    /home/runner/work/neonmodem/neonmodem/neonmodem.go:13
runtime.main
    /opt/hostedtoolcache/go/1.19.10/x64/src/runtime/proc.go:250

light mode

The colors by default seem to be for a white-on-black terminal - on a black-on-white one, the headers for entries are basically invisible.
The default generated config has light/dark mode settings, but I didn't see anything in README.md nor neonmodem --help to select light mode.
So is light mode already available? Please document it.
Thanks!

Add attachment upload

Systems should offer attachment uploads for new posts and replies, so that e.g. images will be uploaded and embedded/linked seamlessly.

TODO

  • [Discourse] Implement Uploads API
  • [*] Implement pouplar file upload service API (ImgUr? Better something OSS/self-hosted?)
  • Build (or use?) UI for file picking and integrate into new post/reply dialog window

[Discourse] ERROR json: cannot unmarshal object into Go struct field CategoryModel.category_list.categories.subcategory_list.uploaded_logo of type string

Steps to reproduce:

  1. Connect a Discourse system (in my case, discourse.nixos.org )
  2. Attempt to view posts
  3. "No items found" displays on UI; error log gives
2024-02-17T15:10:04.768-0600    DEBUG   ui/ui.go:328    generating UI viewcache
2024-02-17T15:10:05.809-0600    DEBUG   api/client.go:55        [DEBUG] %s %s[GET https://discourse.nixos.org/categories.json?include_subcategories=true]
2024-02-17T15:10:05.998-0600    ERROR   ui/ui.go:147    json: cannot unmarshal object into Go struct field CategoryModel.category_list.categories.subcategory_list.uploaded_logo of type string
github.com/mrusme/neonmodem/ui.Model.Update
        github.com/mrusme/neonmodem/ui/ui.go:147
github.com/charmbracelet/bubbletea.(*Program).eventLoop
        github.com/charmbracelet/[email protected]/tea.go:373
github.com/charmbracelet/bubbletea.(*Program).Run
        github.com/charmbracelet/[email protected]/tea.go:503
github.com/charmbracelet/bubbletea.(*Program).Start
        github.com/charmbracelet/[email protected]/tea.go:548
github.com/mrusme/neonmodem/cmd.init.func1
        github.com/mrusme/neonmodem/cmd/root.go:132
github.com/spf13/cobra.(*Command).execute
        github.com/spf13/[email protected]/command.go:944
github.com/spf13/cobra.(*Command).ExecuteC
        github.com/spf13/[email protected]/command.go:1068
github.com/spf13/cobra.(*Command).Execute
        github.com/spf13/[email protected]/command.go:992
github.com/mrusme/neonmodem/cmd.Execute
        github.com/mrusme/neonmodem/cmd/root.go:141
main.main
        github.com/mrusme/neonmodem/neonmodem.go:13
runtime.main
        runtime/proc.go:271

Unable to render composite windows

Terminal: Kitty version 0.26.5

It works fine in tmux, but when I run neonmodem without tmux, the pop-up windows get really messed up.

I installed it by cloning the repo, then cd into the repo and run make. Then moved the binary to /usr/local/bin. I'm only using the hackernews backend.

Kitty:
kitty-screenshot

Tmux + Kitty:
tmxu-screenshot

Lightweight local storage

It makes sense to have a local storage for all sorts of data (state, cache, etc). Ideally it should be something super lightweight (lighter than sqlite3) that's at laest a K/V store.

Add `print` feature

Allow to print a whole post (including replies), e.g. to a text file or even to a device (e.g. /dev/lp).

[Lemmy][Bug] Cannot unmarshal string into Go struct field

Configuring Neon Modem to connect to https://lemmy.sdf.org results in a blank feed. The following error logs are found in ~/.cache/neonmodem.log

{"level":"error","ts":1686705601.7717443,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: json: cannot unmarshal string into Go struct field PostView.posts.subscribed of type bool\n","stacktrace":"github.com/mrusme/neonmodem/aggregator.(*Aggregator).ListPosts\n\t/home/runner/work/neonmodem/neonmodem/aggregator/aggregator.go:77\ngithub.com/mrusme/neonmodem/ui/views/posts.(*Model).refresh.func1\n\t/home/runner/work/neonmodem/neonmodem/ui/views/posts/posts.go:206\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/go/pkg/mod/github.com/charmbracelet/[email protected]/tea.go:247"}
{"level":"error","ts":1686705601.7717974,"caller":"posts/posts.go:209","msg":"[json: cannot unmarshal string into Go struct field PostView.posts.subscribed of type bool]","stacktrace":"github.com/mrusme/neonmodem/ui/views/posts.(*Model).refresh.func1\n\t/home/runner/work/neonmodem/neonmodem/ui/views/posts/posts.go:209\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/go/pkg/mod/github.com/charmbracelet/[email protected]/tea.go:247"}
{"level":"error","ts":1686705602.1112926,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: json: cannot unmarshal string into Go struct field PostView.posts.subscribed of type bool\n","stacktrace":"github.com/mrusme/neonmodem/aggregator.(*Aggregator).ListPosts\n\t/home/runner/work/neonmodem/neonmodem/aggregator/aggregator.go:77\ngithub.com/mrusme/neonmodem/ui/views/posts.(*Model).refresh.func1\n\t/home/runner/work/neonmodem/neonmodem/ui/views/posts/posts.go:206\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/go/pkg/mod/github.com/charmbracelet/[email protected]/tea.go:247"}
{"level":"error","ts":1686705602.1114051,"caller":"posts/posts.go:209","msg":"[json: cannot unmarshal string into Go struct field PostView.posts.subscribed of type bool]","stacktrace":"github.com/mrusme/neonmodem/ui/views/posts.(*Model).refresh.func1\n\t/home/runner/work/neonmodem/neonmodem/ui/views/posts/posts.go:209\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\t/home/runner/go/pkg/mod/github.com/charmbracelet/[email protected]/tea.go:247"}

Typing 'n' character while entering filter text opens the new post dialog

While entering the text for a filter, e.g. if I wanted to look for posts with new in the title, as soon as I type the n character, the dialog for creating a new post opens.

The filter searching is case-insensitive, so this issue can be worked around by typing capital N instead of n, and entry of the filter text can continue.

Lemmy errors

Hello, very cool program thank you!
I saw it on the list of lemmy programs and was looking for a TUI or similar and saw this project and was fast to check if arch AUR had it, and it does, the issue is that after I run neonmodem connect .... and enter my credentials I open neonmodem and nothing happens.. in the logs Isee this:

{"level":"error","ts":1713144564.9067852,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: parsing time \"2024-04-15T01:27:55.951923Z\": extra text: \"Z\"\n","stacktrace":"github.com/mrusme/neonmod
em/aggregator.(*Aggregator).ListPosts\n\tgithub.com/mrusme/neonmodem/aggregator/aggregator.go:77\ngithub.com/mrusme/neonmodem/ui/views/posts.Model.Update.(*Model).refresh.func7\n\tgithub.com/mrusme/neonmodem/ui/
views/posts/posts.go:206\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\tgithub.com/charmbracelet/[email protected]/tea.go:268"}
{"level":"error","ts":1713144564.9068627,"caller":"posts/posts.go:209","msg":"[parsing time \"2024-04-15T01:27:55.951923Z\": extra text: \"Z\"]","stacktrace":"github.com/mrusme/neonmodem/ui/views/posts.Model.Upd
ate.(*Model).refresh.func7\n\tgithub.com/mrusme/neonmodem/ui/views/posts/posts.go:209\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\tgithub.com/charmbracelet/[email protected]/tea.go:26
8"}
{"level":"error","ts":1713144569.161709,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: parsing time \"2024-04-15T01:27:55.951923Z\": extra text: \"Z\"\n","stacktrace":"github.com/mrusme/neonmode
m/aggregator.(*Aggregator).ListPosts\n\tgithub.com/mrusme/neonmodem/aggregator/aggregator.go:77\ngithub.com/mrusme/neonmodem/ui/views/posts.Model.Update.(*Model).refresh.func7\n\tgithub.com/mrusme/neonmodem/ui/v
iews/posts/posts.go:206\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\tgithub.com/charmbracelet/[email protected]/tea.go:268"}
{"level":"error","ts":1713144569.1617947,"caller":"posts/posts.go:209","msg":"[parsing time \"2024-04-15T01:27:55.951923Z\": extra text: \"Z\"]","stacktrace":"github.com/mrusme/neonmodem/ui/views/posts.Model.Upd
ate.(*Model).refresh.func7\n\tgithub.com/mrusme/neonmodem/ui/views/posts/posts.go:209\ngithub.com/charmbracelet/bubbletea.(*Program).handleCommands.func1.1\n\tgithub.com/charmbracelet/[email protected]/tea.go:26
8"}
{"level":"error","ts":1713144678.7184458,"caller":"cmd/root.go:97","msg":"error loading system: 400 Bad Request: unknown","stacktrace":"github.com/mrusme/neonmodem/cmd.loadSystems\n\tgithub.com/mrusme/neonmodem/
cmd/root.go:97\ngithub.com/mrusme/neonmodem/cmd.init.func1\n\tgithub.com/mrusme/neonmodem/cmd/root.go:123\ngithub.com/spf13/cobra.(*Command).execute\n\tgithub.com/spf13/[email protected]/command.go:944\ngithub.com/sp
f13/cobra.(*Command).ExecuteC\n\tgithub.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\tgithub.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\
n\tgithub.com/mrusme/neonmodem/cmd/root.go:141\nmain.main\n\tgithub.com/mrusme/neonmodem/neonmodem.go:13\nruntime.main\n\truntime/proc.go:271"}
{"level":"error","ts":1713144678.7185192,"caller":"cmd/root.go:126","msg":"400 Bad Request: unknown","stacktrace":"github.com/mrusme/neonmodem/cmd.init.func1\n\tgithub.com/mrusme/neonmodem/cmd/root.go:126\ngithu
b.com/spf13/cobra.(*Command).execute\n\tgithub.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\tgithub.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command
).Execute\n\tgithub.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\tgithub.com/mrusme/neonmodem/cmd/root.go:141\nmain.main\n\tgithub.com/mrusme/neonmodem/neonmodem.go:13\nruntim
e.main\n\truntime/proc.go:271"}
{"level":"error","ts":1713144682.5802321,"caller":"cmd/root.go:97","msg":"error loading system: 400 Bad Request: unknown","stacktrace":"github.com/mrusme/neonmodem/cmd.loadSystems\n\tgithub.com/mrusme/neonmodem/
cmd/root.go:97\ngithub.com/mrusme/neonmodem/cmd.init.func1\n\tgithub.com/mrusme/neonmodem/cmd/root.go:123\ngithub.com/spf13/cobra.(*Command).execute\n\tgithub.com/spf13/[email protected]/command.go:944\ngithub.com/sp
f13/cobra.(*Command).ExecuteC\n\tgithub.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command).Execute\n\tgithub.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\
n\tgithub.com/mrusme/neonmodem/cmd/root.go:141\nmain.main\n\tgithub.com/mrusme/neonmodem/neonmodem.go:13\nruntime.main\n\truntime/proc.go:271"}
{"level":"error","ts":1713144682.5803134,"caller":"cmd/root.go:126","msg":"400 Bad Request: unknown","stacktrace":"github.com/mrusme/neonmodem/cmd.init.func1\n\tgithub.com/mrusme/neonmodem/cmd/root.go:126\ngithu
b.com/spf13/cobra.(*Command).execute\n\tgithub.com/spf13/[email protected]/command.go:944\ngithub.com/spf13/cobra.(*Command).ExecuteC\n\tgithub.com/spf13/[email protected]/command.go:1068\ngithub.com/spf13/cobra.(*Command
).Execute\n\tgithub.com/spf13/[email protected]/command.go:992\ngithub.com/mrusme/neonmodem/cmd.Execute\n\tgithub.com/mrusme/neonmodem/cmd/root.go:141\nmain.main\n\tgithub.com/mrusme/neonmodem/neonmodem.go:13\nruntim
e.main\n\truntime/proc.go:271"}
{"level":"error","ts":1713144809.1971514,"caller":"aggregator/aggregator.go:77","msg":"aggregator error: parsing time \"2024-04-15T01:29:54.112344Z\": extra text: \"Z\"\n","stacktrace":"github.com/mrusme/neonmod

I am running

  • Arch GNU/Linux
  • sway/wayland
  • foot terminal
    Other than this, I have no more information... sorry.
    Very eager to run this and try it.

Content blacklist

It should be possible to blacklist terms/forums/users. The blacklist should allow using e.g. RegEx .*twitter.*, or a script language (Lua?), or an external command to decied whether a post should be displayed or not. This way users can remove topics they're not interested in from either source.

[Lobsers] Implement reply/new post

It should be possible to connect to Lobsters systems with a user, to create new posts and comment on existing ones.

TODO

  • Figure out how the authentication/posting on Lobsters looks like
  • Implement into API client

[Discourse] "Infinite scroll" for post replies

The Discourse system needs to have an "infinite scroll" feature that automatically loads the next chunk of replies when viewport is close to the edge of the currently loaded replies. Unlike regular "infinite scroll" that loads later content below, this feature should go the other way, load the latest 10 replies and only when the user presses up/k the viewport should load the previous chunk of replies above the already loaded ones. In most cases users are probably more interested in the latest replies rather than historic ones.

Lemmy ListPosts results limited to 50

Lemmy post results are limited to 50 which results in a lot of empty communities (forums) when you have many subscriptions.
Probably need to split the go request in system/lemmy/lemmy.go func ListPosts into multiple requests, bumping the limit number directly will not succeed, but not experienced enough to do this myself.

[Hacker News] Implement reply/new post

It should be possible to connect to the Hacker News system with a user, to create new posts and comment on existing ones.

TODO

  • Figure out how the authentication/posting on Lobsters looks like
  • Implement into API client

[Enhancement] Allow alternate feed sorting

Right now neonmodem sorts by "new". This is fine, and probably necessary when viewing multiple systems at once, but it would be nice if we could detect (or hard code) the available sorting options and allow the use of them when viewing a specific system.

[Hackernews][Bug] Unable to add Hackernews in HEAD

$ ./neonmodem connect --type hackernews
panic: interface conversion: interface {} is nil, not string
[...]

system/hackernews/hackernews.goL#106 does not work as intended. I've spent some time trying to identify the issue but unfortunately my knowledge of go interfaces is limited so I was unable to determine what the actual values of sys.config were or where those values were coming from. It behaves as though it's not reading in what is expected and is empty which causes the type assertion to fail.

To confirm this, I applied the following changes to system/hackernews/hackernews.go which confirms that sys.config["proxy"] is indeed nil.

diff --git a/system/hackernews/hackernews.go b/system/hackernews/hackernews.go
index cf7068e..d80a4d3 100644
--- a/system/hackernews/hackernews.go
+++ b/system/hackernews/hackernews.go
@@ -103,7 +103,13 @@ func (sys *System) Load() error {
        var httpTransport *http.Transport = http.DefaultTransport.(*http.Transport).
                Clone()

-       proxy := sys.config["proxy"].(string)
+       var proxy string
+
+       if sys.config["proxy"] != nil {
+               proxy = sys.config["proxy"].(string)
+       } else {
+               proxy = ""
+       }
        if proxy != "" {
                proxyURL, err := url.Parse(proxy)
                if err != nil {

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.