[HN Gopher] Show HN: Shelgon: A Framework for Building Interacti...
       ___________________________________________________________________
        
       Show HN: Shelgon: A Framework for Building Interactive REPL Shells
       in Rust
        
       I've been working on Shelgon, a framework that lets you build your
       own custom REPL shells and interactive CLI applications in Rust.
       You can use Shelgon to:  - Create a custom shell with only a few
       lines of code - Build interactive debugging tools with persistent
       state between commands - Develop domain-specific language
       interpreters with shell-like interfaces - Add REPL capabilities to
       existing applications  Getting started is straightforward -
       implement a single trait that handles your command execution logic,
       and Shelgon takes care of the terminal UI, input handling, and
       async runtime integration.  For example, a simple echo shell takes
       less than 50 lines of code, including a full implementation of
       command history, cursor movement, and tab completion.  Repository:
       https://github.com/nishantjoshi00/shelgon
        
       Author : cat-whisperer
       Score  : 119 points
       Date   : 2025-03-06 19:32 UTC (1 days ago)
        
 (HTM) web link (github.com)
 (TXT) w3m dump (github.com)
        
       | hkalbasi wrote:
       | How it compares to other libraries in this space, e.g. reedline
       | or rustyline?
        
         | cat-whisperer wrote:
         | Wow! rustyline has intensive support for a lot of the actions
         | and things the user can do. Though I wanted to provide a more
         | restrictive yet powerful abstraction that's my I chose a trait
         | based approach. It provides the exact control needed on certain
         | aspects of the shell while providing ample control because of
         | the shared state. Initially, I was planning to make the
         | functions async, but I rather choose to pass the async runtime
         | instead. It solves for 2 cool use-cases; 1 we can call block_on
         | and manage an async task in the flow, or 2 queue in the action
         | and consider pooling it when needed.
        
       | cmrdporcupine wrote:
       | Neat. I'll check it out.
       | 
       | One suggestions: the README advertises lovely TUIs. Show us a
       | screenshot, or screencast, so we can see what you mean!
        
         | tmpfs wrote:
         | Yes, a screenshot would be good to get a visual on this.
         | 
         | I have done a simple shell using Rustyline and Clap and this
         | could be something I might be interested in but it's hard to
         | say without a visual idea, asccinema would be perfect!
        
           | cat-whisperer wrote:
           | asccinema is a killer idea! but I am still chasing my perfect
           | shell . If you end up implementing an insane looking shell
           | with this, contributions are always open.
        
       | bfLives wrote:
       | Looks really interesting. I like the approach of writing pure
       | functions that return descriptions of IO tasks to perform. A
       | couple of questions:
       | 
       | 1. Why async?
       | 
       | 2. Why couple to anyhow instead of using an associated error
       | type?
        
         | cmrdporcupine wrote:
         | +1 for #1. In general, I would recommend providing non-async
         | alternative APIs, with the async runtime as an _option_ rather
         | than assumed default. Not all of us drink the kool-aid there.
         | And no, I don 't mean just providing a "sync" API that uses
         | "block_on" behind the scenes but still uses tokio...
         | 
         | Also, for async don't mandate tokio, use the "agnostic" crate
         | to abstract it so people can use alternative runtimes.
         | 
         | And yes, don't use anyhow in a library like this. Anyhow is for
         | your internal code, not public libraries/crates. Define a set
         | of error enums, or use thiserror for it if you have to.
        
           | cat-whisperer wrote:
           | Yup, I am planning to use thiserror and error-stack for this
           | in the future updates. But, anyhow provides an insanely easy
           | interface for the person using this library, and keeps their
           | mind off the error handling and rather in managing the domain
           | stuff.
        
           | dhon_ wrote:
           | Could you elaborate on why using block_on wouldn't be an
           | acceptable solution for users that want a blocking API?
        
             | cmrdporcupine wrote:
             | Why would I want to add tokio as a dependency if I don't
             | use it?
        
               | dhon_ wrote:
               | Yes you're right. I'd assumed that tokio was used
               | internally in the UI but from a cursory read it doesn't
               | seem to be the case.
        
               | cat-whisperer wrote:
               | I was thinking of making it a opt-in feature, but I saw
               | most of the usecases that I might have, might need
               | concurrency and a runtime.
        
             | cat-whisperer wrote:
             | it definitely would be, that was my intention. By passing
             | in a runtime you can either block or schedule. Giving you
             | control on what you want to be concurrent and what you
             | don't.
        
       | ilikegreen wrote:
       | Please don't mind my possibly simplistic question -- but is this
       | something that would bring Rust development closer to a Lisp
       | environment? Seems like an interesting project.
        
         | fredrikholm wrote:
         | This is more in line with building a REPL for your own
         | language.
         | 
         | Lisp environments are just that; environments. That is to say
         | that there is a runtime that holds your code in memory, which
         | then enables a REPL to replace parts of the code in memory
         | while the program is running.
         | 
         | This implies an interpreted language (that might or might not
         | also be compiled further at runtime), which Rust is not. It
         | also heavily implies a garbage collector, which Rust doesn't
         | have. Lastly, type guarantees in these languages tend to be
         | less strong as the system almost by definition is already very
         | dynamic.
        
       | jiaaro wrote:
       | Cool project! But, I wonder how long can a project like this use
       | a Pokemon as their namesake and mascot before you hear from
       | nintendo's lawyers?
        
         | dartos wrote:
         | Right up until they start charging
        
         | gertlex wrote:
         | I wonder if they could get away with an extra L and using ascii
         | art of the pokemon...
        
           | cat-whisperer wrote:
           | ascii art for the win
        
       | serial_dev wrote:
       | Interesting stuff!
       | 
       | Video or gif would be nice! It's like a UI library need at least
       | a screenshot, this thing needs a video demo of sorts.
       | 
       | Q: why write that the docs is by LLM? In my opinion if it's
       | correct, and it makes sense, I don't care even if an alien gave
       | it to you.
        
         | cat-whisperer wrote:
         | giving credit where credit is due.
        
       | faizshah wrote:
       | This is awesome, there's a really nice one in python called
       | prompt toolkit that has some a nice api as well: https://python-
       | prompt-toolkit.readthedocs.io/en/master/
        
       ___________________________________________________________________
       (page generated 2025-03-07 23:02 UTC)