GemReader/docs/api.md
2025-09-29 22:43:04 -05:00

5.3 KiB

API Documentation

This document provides detailed documentation for the GemReader application's internal APIs and code structure.

Package Structure

  • main (cmd/gemreader/main.go): Application entry point and command-line interface
  • config (internal/config/config.go): Configuration loading and management
  • tui (internal/tui/tui.go): Terminal user interface implementation

Main Package

main.go

Execute() function

func Execute()
  • Initializes and executes the Cobra command
  • Handles command execution errors
  • Exits the application with appropriate error code if execution fails

rootCmd variable

var rootCmd = &cobra.Command
  • Main Cobra command for the application
  • Uses format: gemreader [file]
  • Allows 0 or 1 arguments (the markdown file to view)
  • Handles file reading and TUI initialization
  • If no file is provided, attempts to use the default file from config

validateFilePath() function

func validateFilePath(inputPath string) (string, error)
  • Validates file paths to prevent directory traversal attacks
  • Cleans and resolves absolute paths
  • Ensures the resolved path is within the current working directory
  • Returns error if path traversal is detected

validateFile() function

func validateFile(filePath string) error
  • Performs security checks on files before loading
  • Validates file size (max 10MB)
  • Ensures file is a supported type (.md, .markdown, .txt, or no extension)

Config Package

config.go

Config struct

type Config struct {
    Title       string `mapstructure:"title"`
    DefaultFile string `mapstructure:"default_file"`
    ShowTOC     bool   `mapstructure:"show_toc"`
}
  • Stores application configuration
  • Supports Title, DefaultFile, and ShowTOC fields
  • Tagged for Viper configuration mapping

LoadConfig() function

func LoadConfig() (config Config, err error)
  • Loads configuration from config.toml file
  • Searches for config file in current directory
  • Supports TOML format
  • Returns Config struct and error if any
  • Uses Viper for configuration management
  • Returns defaults if config file doesn't exist

TUI Package

tui.go

model struct

type model struct {
    content         string
    rawLines        []string
    toc             []tocEntry
    selectedTocIndex int

    tocViewport     viewport.Model
    contentViewport viewport.Model

    activePane   pane
    helpVisible  bool
    config       config.Config
    windowWidth  int
    windowHeight int
}

The model struct contains all state information for the TUI:

  • content: Original markdown content as string
  • rawLines: Original content split by newlines for TOC generation
  • toc: Table of contents entries
  • selectedTocIndex: Index of currently selected TOC entry
  • tocViewport: Bubble Tea viewport for TOC pane
  • contentViewport: Bubble Tea viewport for content pane
  • activePane: Currently active pane (TOC or content)
  • helpVisible: Whether help text is visible
  • config: Application configuration
  • windowWidth, windowHeight: Terminal dimensions

pane type

type pane int

const (
    tocPane pane = iota
    contentPane
)
  • Represents the two panes in the UI
  • tocPane: Left pane showing table of contents
  • contentPane: Right pane showing markdown content

tocEntry struct

type tocEntry struct {
    level int
    text  string
    line  int
}
  • Represents a single entry in the table of contents
  • level: Header level (1 for #, 2 for ##, etc.)
  • text: Text content of the header
  • line: Line number in the original document

NewModel() function

func NewModel(content string, cfg config.Config) model
  • Creates a new TUI model with the given content and configuration
  • Splits content into lines for TOC generation
  • Generates table of contents from headers
  • Initializes viewport models
  • Sets up initial state with content pane as active

generateTOC() function

func generateTOC(lines []string) []tocEntry
  • Scans content lines for markdown headers
  • Creates tocEntry for each header found
  • Determines header level based on number of # characters
  • Returns list of all headers in document order

(m model) Init() method

func (m model) Init() tea.Cmd
  • Bubble Tea initialization method
  • Returns nil command (no initial command needed)

(m model) Update() method

func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd)
  • Bubble Tea update method for handling messages and user input
  • Handles window resize events and recalculates pane dimensions
  • Processes keyboard input for navigation
  • Switches between TOC and content panes with Tab key
  • Handles TOC navigation and jumping to selected entries
  • Updates both viewport models
  • Supports all navigation commands

(m model) View() method

func (m model) View() string
  • Bubble Tea view method for rendering the UI
  • Applies styles to active and inactive panes
  • Renders both TOC and content panes side by side
  • Shows help text at the bottom if visible
  • Returns string representation of current UI state

(m model) renderTOC() method

func (m model) renderTOC() string
  • Renders the table of contents view
  • Shows headers with proper indentation based on level
  • Highlights the currently selected entry with '>'
  • Shows "No table of contents found." if no headers exist