Menu
Coddy logo textTech

Admin CLI Interface

Part of the Object Oriented Programming section of Coddy's GO journey — lesson 103 of 107.

challenge icon

Challenge

Easy

Let's build a command-line interface for our Library Management System using the Command Pattern! You'll create a CLI that processes admin commands like adding books, registering users, and managing borrowing operations—all through a clean, extensible architecture.

You'll organize your code across six files:

  • book.go: Your Book struct with JSON tags for ID, Title, Author, ISBN, and Available. Include the NewBook constructor.
  • user.go: Your User struct with JSON tags for ID, Name, Email, and BorrowedBooks. Include the NewUser constructor.
  • library.go: Your Library struct with maps for books and users, along with AddBook, AddUser, Borrow, and Return methods from previous lessons.
  • commands.go: This is where the Command Pattern comes to life! Define a Command interface with an Execute method that takes a *Library and []string args, returning a string result. Then implement these command structs:
    • AddBookCommand — expects 4 args: id, title, author, isbn. Adds the book and returns Book added: [title]
    • AddUserCommand — expects 3 args: id, name, email. Adds the user and returns User added: [name]
    • BorrowCommand — expects 2 args: userID, bookID. Returns Borrowed: [bookID] on success, or Error: [message] on failure
    • ReturnCommand — expects 2 args: userID, bookID. Returns Returned: [bookID] on success, or Error: [message] on failure
    • ListBooksCommand — takes no args. Returns each book's ID and title on separate lines in format [id]: [title], or No books if empty (list books sorted by ID)

    If a command receives insufficient arguments, return Error: insufficient arguments

  • cli.go: Create a CLI struct that holds a pointer to a Library and a map of command names to Command implementations. Build:
    • NewCLI constructor that initializes the CLI with a library and registers all commands: addbook, adduser, borrow, return, listbooks
    • Run method that takes an input string, parses it using strings.Fields, looks up the command, and executes it. Return No command provided for empty input, or Unknown command: [name] for unrecognized commands
  • main.go: Create a library and CLI, then process commands from input. Read the number of commands, then read each command string on a separate line. For each command, call Run and print the result.

The following inputs will be provided:

  • Number of commands
  • Each command as a complete string on its own line

For example, given:

6
addbook B001 Go-Programming Alan-Donovan 978-0134190440
addbook B002 Clean-Code Robert-Martin 978-0132350884
adduser U001 Alice alice@test.com
borrow U001 B001
listbooks
borrow U001 B001

Your output should be:

Book added: Go-Programming
Book added: Clean-Code
User added: Alice
Borrowed: B001
B001: Go-Programming
B002: Clean-Code
Error: book not available

And given:

4
listbooks
addbook B100 Design-Patterns Gang-of-Four 978-0201633610
listbooks
invalidcmd test

Your output should be:

No books
Book added: Design-Patterns
B100: Design-Patterns
Unknown command: invalidcmd

And given:

5
adduser U001 Bob bob@email.com
borrow U001 B001
addbook B001 Golang-Guide John-Smith 123-456
borrow U001 B001
return U001 B001

Your output should be:

User added: Bob
Error: book not found
Book added: Golang-Guide
Borrowed: B001
Returned: B001

Notice how the CLI doesn't need to know the details of each operation—it simply looks up the command and delegates execution. This makes adding new commands as simple as creating a new struct that implements the Command interface and registering it in the CLI!

Try it yourself

package main

import (
	"bufio"
	"fmt"
	"os"
)

func main() {
	// Read the number of commands
	var n int
	fmt.Scanln(&n)

	// Create a scanner to read full lines
	scanner := bufio.NewScanner(os.Stdin)

	// TODO: Create a new Library

	// TODO: Create a new CLI with the library

	// TODO: Process each command
	// For each of the n commands:
	// - Read the command line using scanner.Scan() and scanner.Text()
	// - Run the command through the CLI
	// - Print the result

	_ = scanner // Remove this line when you use scanner
}

All lessons in Object Oriented Programming