Skip to content

feat: Add Java Search Suggestions project#37

Merged
gitsofaryan merged 2 commits intogitsofaryan:mainfrom
ashwini2k6:feat/java-search-suggestions
Oct 27, 2025
Merged

feat: Add Java Search Suggestions project#37
gitsofaryan merged 2 commits intogitsofaryan:mainfrom
ashwini2k6:feat/java-search-suggestions

Conversation

@ashwini2k6
Copy link
Contributor

@ashwini2k6 ashwini2k6 commented Oct 26, 2025

This PR adds a "Search Suggestions System" project, written in Java.

Project Details:

  • Folder: Search suggestion system
  • Logic: SearchSuggestions.java (Implements a Trie data structure)
  • Data: dictionary.txt (A sample dictionary file)
  • Docs: README.md (Includes compile/run instructions)

This project is a clean implementation that demonstrates the practical application of a Trie (Prefix tree). Words in dictionary.txt can be extended as per user's requirements.

Summary by CodeRabbit

  • New Features

    • Interactive command-line search suggestion system that loads a dictionary and provides real-time word suggestions by prefix.
  • Documentation

    • Added a README with setup, usage instructions, and example sessions.
  • Chores

    • Added .gitignore to exclude build, IDE, editor, and OS-generated files.
  • Assets

    • Included a sample dictionary file with common terms for suggestion testing.

@coderabbitai
Copy link

coderabbitai bot commented Oct 26, 2025

Walkthrough

Adds a new Java Trie-based prefix search suggestions implementation with CLI, sample dictionary, README, and a project .gitignore.

Changes

Cohort / File(s) Summary
Configuration
\.gitignore``
Adds a new .gitignore with patterns to ignore Java artifacts (*.class, *.jar, *.war, *.ear), build directories (target/, build/, out/, bin/), editor/IDE files (.idea/, .vscode/, *.iml, *.iws, *.ipr), temp/editor files (*.swp, *~), and OS files (.DS_Store, Thumbs.db).
Search Suggestion System
**Search suggestion system/**
\Search suggestion system/SearchSuggestions.java`, `Search suggestion system/README.md`, `Search suggestion system/dictionary.txt``
Adds a Trie-based Java implementation SearchSuggestions.java with insert, getSuggestions, recursive word collection, dictionary loader, and main CLI loop; includes README.md documenting usage and internals; adds a plain dictionary.txt with 22 words.

Sequence Diagram

sequenceDiagram
    participant User
    participant Main as main()
    participant Trie as SearchSuggestions
    participant File as dictionary.txt

    Main->>File: loadDictionary(filename)
    File-->>Main: lines (words)
    loop for each word
        Main->>Trie: insert(word)
    end
    Note over Trie: Trie built from dictionary
    Main->>User: prompt for prefix
    User->>Main: prefix input
    Main->>Trie: getSuggestions(prefix)
    Note over Trie: traverse to prefix node\ncollect descendant words
    Trie-->>Main: suggestions list
    Main->>User: display suggestions
    alt user continues
        loop until 'q' or empty
            User->>Main: next prefix
            Main->>Trie: getSuggestions(prefix)
            Trie-->>Main: suggestions list
            Main->>User: display suggestions
        end
    end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • Review Trie traversal and recursion in findAllWords for correctness and stack safety.
  • Verify dictionary loading, file handling, and error messages in loadDictionary.
  • Check CLI input handling and resource cleanup in main.

Poem

🐰 In a burrow of bytes I hopped with glee,
I planted words in a branching tree,
Type a prefix, watch ideas unfurl —
Suggestions hop out, one by one they twirl! ✨

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 16.67% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The title "feat: Add Java Search Suggestions project" directly and accurately describes the main objective of the pull request. The PR adds a complete new project consisting of a SearchSuggestions.java file implementing a Trie-based search system, supporting documentation in README.md, a sample dictionary.txt file, and a .gitignore configuration. The title is concise, uses clear language, follows conventional commit format, and is specific enough that a reviewer scanning the repository history would immediately understand the primary change being introduced.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

📜 Recent review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 6c24d60 and 3683a6f.

📒 Files selected for processing (4)
  • .gitignore (1 hunks)
  • Search suggestion system/README.md (1 hunks)
  • Search suggestion system/SearchSuggestions.java (1 hunks)
  • Search suggestion system/dictionary.txt (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (3)
  • .gitignore
  • Search suggestion system/SearchSuggestions.java
  • Search suggestion system/README.md
🧰 Additional context used
🪛 LanguageTool
Search suggestion system/dictionary.txt

[uncategorized] ~1-~1: Did you mean the proper noun “Apple” (= technology company)?
Context: apple app application apply apricot banana ba...

(APPLE_PRODUCTS)

🔇 Additional comments (1)
Search suggestion system/dictionary.txt (1)

1-22: Well-structured sample dictionary for Trie demonstrations.

The dictionary contains appropriate test data with good prefix variety (app*, ba*, pro*, java*, etc.) suitable for demonstrating Trie-based search suggestions. The lowercase format and one-word-per-line structure are correct for a dictionary data file.

Note: The static analysis suggestion to capitalize "apple" is a false positive—lowercase entries are intentional and correct in a dictionary file used by search systems.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (5)
.gitignore (1)

1-14: Consider adding additional common patterns.

The .gitignore covers essential Java artifacts and IDE files. Consider optionally adding these common patterns for a more comprehensive setup:

 # Java
 *.class
 *.log
 *.jar
 *.war
 *.ear
+
+# Build directories
+target/
+build/
+out/
+bin/
+
+# Editor temporary files
+*.swp
+*~
+
 # IDE files
 .idea/
 .vscode/
 *.iml
 *.iws
 *.ipr
+
 # Other
 .DS_Store
+Thumbs.db
Search suggestion system/README.md (1)

59-64: Consider adjusting list indentation.

The markdown linter suggests using 0-space indentation instead of 2 spaces for the unordered list items. While this is a stylistic preference, standardizing on 0-space indentation improves consistency with common markdown conventions.

Apply this diff:

-  * `TrieNode`: A private inner class holds a `Map<Character, TrieNode>` for its children and a `boolean` to mark the end of a word.
-  * `insert(String word)`: Iterates through each character of the word, creating new nodes in the Trie as needed.
-  * `getSuggestions(String prefix)`:
-    1.  Traverses the Trie to the node corresponding to the last character of the prefix.
-    2.  If the prefix path doesn't exist, it returns an empty list.
-    3.  If it does, it calls a recursive helper `findAllWords()` to explore all child paths from that node and collect all complete words.
+* `TrieNode`: A private inner class holds a `Map<Character, TrieNode>` for its children and a `boolean` to mark the end of a word.
+* `insert(String word)`: Iterates through each character of the word, creating new nodes in the Trie as needed.
+* `getSuggestions(String prefix)`:
+  1.  Traverses the Trie to the node corresponding to the last character of the prefix.
+  2.  If the prefix path doesn't exist, it returns an empty list.
+  3.  If it does, it calls a recursive helper `findAllWords()` to explore all child paths from that node and collect all complete words.
Search suggestion system/SearchSuggestions.java (3)

25-31: Add input validation for robustness.

The insert method doesn't validate the input parameter. If a null or empty word is passed, it could lead to unexpected behavior or exceptions.

Apply this diff to add input validation:

 public void insert(String word) {
+    if (word == null || word.isEmpty()) {
+        return; // or throw IllegalArgumentException
+    }
     TrieNode node = root;
     for (char c : word.toLowerCase().toCharArray()) {
         node = node.children.computeIfAbsent(c, k -> new TrieNode());
     }
     node.isEndOfWord = true;
 }

33-47: Add input validation for robustness.

Similar to the insert method, getSuggestions doesn't validate the input parameter. If null is passed, it will throw a NullPointerException at line 34.

Apply this diff to add input validation:

 public List<String> getSuggestions(String prefix) {
+    if (prefix == null) {
+        return Collections.emptyList();
+    }
     String lowerPrefix = prefix.toLowerCase();
     TrieNode node = root;

100-123: Consider using try-with-resources for Scanner.

The Scanner is properly closed at line 122, but using try-with-resources would be more robust and ensure cleanup even if an exception occurs.

Apply this diff:

-        Scanner scanner = new Scanner(System.in);
-
-        while (true) {
+        try (Scanner scanner = new Scanner(System.in)) {
+            while (true) {
+                System.out.print("\nEnter prefix to search (or 'q' to quit): ");
+                String prefix = scanner.nextLine();
+
+                if (prefix.equalsIgnoreCase("q") || prefix.isEmpty()) {
+                    break;
+                }
+
+                List<String> suggestions = trie.getSuggestions(prefix);
+
+                if (suggestions.isEmpty()) {
+                    System.out.println("No suggestions found for '" + prefix + "'.");
+                } else {
+                    System.out.println("Suggestions for '" + prefix + "':");
+                    for (String suggestion : suggestions) {
+                        System.out.println(" -> " + suggestion);
+                    }
+                }
+            }
-            System.out.print("\nEnter prefix to search (or 'q' to quit): ");
-            String prefix = scanner.nextLine();
-
-            if (prefix.equalsIgnoreCase("q") || prefix.isEmpty()) {
-                break;
-            }
-
-            List<String> suggestions = trie.getSuggestions(prefix);
-
-            if (suggestions.isEmpty()) {
-                System.out.println("No suggestions found for '" + prefix + "'.");
-            } else {
-                System.out.println("Suggestions for '" + prefix + "':");
-                for (String suggestion : suggestions) {
-                    System.out.println(" -> " + suggestion);
-                }
-            }
+            System.out.println("Goodbye!");
         }
-
-        scanner.close();
-        System.out.println("Goodbye!");
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between dc8755d and 6c24d60.

📒 Files selected for processing (4)
  • .gitignore (1 hunks)
  • Search suggestion system/README.md (1 hunks)
  • Search suggestion system/SearchSuggestions.java (1 hunks)
  • Search suggestion system/dictionary.txt (1 hunks)
🧰 Additional context used
🪛 LanguageTool
Search suggestion system/dictionary.txt

[uncategorized] ~1-~1: Did you mean the proper noun “Apple” (= technology company)?
Context: apple app application apply apricot banana ba...

(APPLE_PRODUCTS)

🪛 markdownlint-cli2 (0.18.1)
Search suggestion system/README.md

35-35: Fenced code blocks should have a language specified

(MD040, fenced-code-language)


59-59: Unordered list indentation
Expected: 0; Actual: 2

(MD007, ul-indent)


60-60: Unordered list indentation
Expected: 0; Actual: 2

(MD007, ul-indent)


61-61: Unordered list indentation
Expected: 0; Actual: 2

(MD007, ul-indent)

🔇 Additional comments (6)
Search suggestion system/dictionary.txt (1)

1-23: LGTM!

The dictionary file contains a good set of sample words for testing the search suggestion system. The words are properly formatted (one per line, lowercase) and cover various prefixes for meaningful testing.

Search suggestion system/SearchSuggestions.java (5)

14-17: LGTM!

The TrieNode inner class is well-designed with appropriate use of HashMap for children and a boolean flag for word endings. The private visibility provides good encapsulation.


21-23: LGTM!

The constructor properly initializes the root node. The root field being final is a good practice.


49-59: LGTM!

The recursive DFS traversal with backtracking is correctly implemented. The use of StringBuilder for efficient string building and proper backtracking with setLength demonstrates good understanding of the algorithm.

Note: Since HashMap doesn't guarantee iteration order, suggestions will not be returned in any particular order (e.g., not alphabetically sorted). This is acceptable for the current use case, but could be enhanced by sorting if needed.


64-81: LGTM!

The loadDictionary method demonstrates good practices:

  • Try-with-resources for automatic resource management
  • Proper exception handling with specific catches
  • Trimming and validation of input lines
  • Appropriate error messages to stderr

86-91: Document the working directory requirement clearly.

The comments explain that the program must be run from within the project directory, which is a reasonable constraint for this demonstration project. The README provides clear instructions for this.

Comment on lines 35 to 55
```
Loading dictionary from 'dictionary.txt'...
Successfully loaded 10 words.

Enter prefix to search (or 'q' to quit): pro
Suggestions for 'pro':
-> profile
-> program
-> project
-> python

Enter prefix to search (or 'q' to quit): app
Suggestions for 'app':
-> app
-> apple
-> apply
-> application

Enter prefix to search (or 'q' to quit): q
Goodbye!
```
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Incorrect example output.

Line 44 shows "python" as a suggestion for the prefix "pro", but "python" doesn't start with "pro". Based on the dictionary.txt file, the correct suggestions should only include: profile, program, and project.

Apply this diff to fix the example:

 Enter prefix to search (or 'q' to quit): pro
 Suggestions for 'pro':
  -> profile
  -> program
  -> project
- -> python

Additionally, consider specifying the language for the output block to address the markdown linter warning:

-```
+```text
 Loading dictionary from 'dictionary.txt'...
🧰 Tools
🪛 markdownlint-cli2 (0.18.1)

35-35: Fenced code blocks should have a language specified

(MD040, fenced-code-language)

🤖 Prompt for AI Agents
In Search suggestion system/README.md around lines 35 to 55, the example output
is wrong and the code block lacks a language: remove " -> python" from the
suggestions for prefix "pro" so the list shows only "profile", "program", and
"project", and change the opening fenced code block from ``` to ```text to
satisfy the markdown linter; keep the rest of the example output identical.

@ashwini2k6 ashwini2k6 closed this Oct 26, 2025
@ashwini2k6 ashwini2k6 reopened this Oct 26, 2025
@ashwini2k6
Copy link
Contributor Author

Hi @gitsofaryan, kindly review it!!

@gitsofaryan gitsofaryan merged commit 194390c into gitsofaryan:main Oct 27, 2025
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants