Skip to content

Added Feat #332 Search project by name#340

Open
OfficialSubham wants to merge 1 commit intoapsinghdev:mainfrom
OfficialSubham:feat/project-search-by-name
Open

Added Feat #332 Search project by name#340
OfficialSubham wants to merge 1 commit intoapsinghdev:mainfrom
OfficialSubham:feat/project-search-by-name

Conversation

@OfficialSubham
Copy link

@OfficialSubham OfficialSubham commented Feb 14, 2026

Implemented search project by name

-UI
Added an input field in find project side bar at the top
there user can type the name of the repo they want to find

-API
Added repoName in zod validation of filterPropsSchema
added repoName in FilterProps
sending repo name to the query string.

Summary by CodeRabbit

New Features

  • Repository Name Filter: Users can now filter GitHub projects by repository name through a new input field in the filters section. This enhancement integrates seamlessly with existing filter options such as technology stack and popularity, enabling more precise and efficient project discovery.

@vercel
Copy link

vercel bot commented Feb 14, 2026

@OfficialSubham is attempting to deploy a commit to the AJEET PRATAP SINGH's projects Team on Vercel.

A member of the Team first needs to authorize it.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 14, 2026

📝 Walkthrough

Walkthrough

This pull request extends filtering capabilities by introducing a new optional repoName filter. The change propagates through the application stack: from shared type definitions through frontend UI components and utilities, to the backend API schema and service layer, enabling GitHub project filtering by repository name.

Changes

Cohort / File(s) Summary
Type Definitions
packages/shared/types/filter.ts, apps/web/src/types/filter.ts, apps/api/src/routers/projects.ts
Added optional repoName?: string property to filter type definitions across the shared types, web UI types, and API router schema, establishing the new filter field contract.
Backend Service
apps/api/src/services/project.service.ts
Implemented repository name filtering logic in GitHub search query construction, conditionally appending <repoName> in:name to query parameters when the filter is provided.
Frontend UI & Utilities
apps/web/src/components/ui/FiltersContainer.tsx, apps/web/src/utils/converter.ts
Added repository name input field to the Filters accordion and wired it through the filter store; implemented conversion logic to map the UI filter to the API input format.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~15 minutes

Poem

🐰 A filter by name, so neat and true,
Repo fields added through and through,
From schema to service, UI to sight,
Repository searching shines so bright! ✨

🚥 Pre-merge checks | ✅ 3 | ❌ 1
❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately describes the main change: adding a feature to search/filter projects by repository name, which is reflected across all modified files (UI input field, API filtering logic, and type definitions).
Merge Conflict Detection ✅ Passed ✅ No merge conflicts detected when merging into main

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Tip

Issue Planner is now in beta. Read the docs and try it out! Share your feedback on Discord.


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
Contributor

@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: 4

🤖 Fix all issues with AI agents
In `@apps/api/src/routers/projects.ts`:
- Line 24: The repoName zod schema currently allows arbitrary strings which are
later interpolated into the GitHub search template (`${trimmedRepoName}
in:name`) and can be abused to inject search qualifiers; update the schema for
repoName in routers/projects.ts to add length limits (e.g., min 1, max 100) and
a regex that only permits valid GitHub repo name characters (alphanumerics,
hyphens, underscores, dots) and disallows colons/spaces/qualifiers, and then
trim/normalize the value before passing it to the search in project.service.ts
(referencing the trimmedRepoName usage) so only validated/sanitized names reach
the GitHub query.

In `@apps/api/src/services/project.service.ts`:
- Around line 50-53: The repoName from filters is interpolated directly into the
GitHub search string (see filters.repoName and queryParts.push), so either
enforce/validate the allowed repo-name characters upstream in the router schema
or add a guard here: trim filters.repoName, validate it against an
allowed-repo-name regex (e.g. only letters, numbers, hyphen, underscore, dot),
reject or throw if it contains invalid characters, and use the
validated/sanitized value (e.g. sanitizedRepoName) when calling
queryParts.push(`${sanitizedRepoName} in:name`) to prevent injection via GitHub
search qualifiers.

In `@apps/web/src/components/ui/FiltersContainer.tsx`:
- Around line 83-92: The input in FiltersContainer is currently uncontrolled and
lacks accessibility and dark-theme styling; bind the input's value to the
filters' repoName (read from the store or props), keep the existing onChange
handler calling updateFilters({repoName: e.target.value}), add an appropriate
aria-label (e.g., aria-label="Repository name"), and replace the hard/absent
colors with design-token Tailwind classes (e.g., bg-surface-primary,
text-text-primary, placeholder:text-text-secondary) so the field clears when
resetFilters() updates repoName and matches dark theme; update the input element
in FiltersContainer accordingly.

In `@apps/web/src/utils/converter.ts`:
- Line 108: Update the inline example comment in converter.ts where it shows "//
reponame: "name"" to use the correct camelCase field name "repoName"; locate the
comment near the converter utilities (e.g., around functions that map or format
repo objects) and change "reponame" to "repoName" so the example matches the
actual field used in the code.
🧹 Nitpick comments (1)
apps/web/src/types/filter.ts (1)

50-57: Naming inconsistency in UserInputFilterProps.

Other keys in this type use user-facing display names ("Tech stack", "Popularity", etc.) while repoName uses camelCase. This works because the converter handles it as a direct pass-through rather than a lookup, but the mixed convention may confuse future contributors.

Consider using a consistent pattern — either rename to a display-style key (e.g., "Repository name") and update the converter accordingly, or document why repoName deviates.

.optional(),
pushed: z.string().optional(),
created: z.string().optional(),
repoName: z.string().optional()
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Consider adding length validation and sanitization to repoName.

The repoName string is passed directly into the GitHub search query (see project.service.ts Line 52: `${trimmedRepoName} in:name`). A user could inject GitHub search qualifiers (e.g., "stars:>1000 is:private") to manipulate search results beyond the intended name filter.

Proposed fix
-  repoName: z.string().optional()
+  repoName: z.string().max(256).regex(/^[a-zA-Z0-9._-]*$/).optional()

The regex restricts input to valid GitHub repository name characters, preventing injection of search qualifiers like stars:, is:, etc.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
repoName: z.string().optional()
repoName: z.string().max(256).regex(/^[a-zA-Z0-9._-]*$/).optional()
🤖 Prompt for AI Agents
In `@apps/api/src/routers/projects.ts` at line 24, The repoName zod schema
currently allows arbitrary strings which are later interpolated into the GitHub
search template (`${trimmedRepoName} in:name`) and can be abused to inject
search qualifiers; update the schema for repoName in routers/projects.ts to add
length limits (e.g., min 1, max 100) and a regex that only permits valid GitHub
repo name characters (alphanumerics, hyphens, underscores, dots) and disallows
colons/spaces/qualifiers, and then trim/normalize the value before passing it to
the search in project.service.ts (referencing the trimmedRepoName usage) so only
validated/sanitized names reach the GitHub query.

Comment on lines +50 to +53
if(filters.repoName) {
const trimmedRepoName = filters.repoName.trim();
queryParts.push(`${trimmedRepoName} in:name`)
}
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

User-supplied repoName is interpolated directly into the GitHub search query.

This is the injection point for the concern raised in the router's schema validation comment. If input sanitization is added at the schema level (as suggested in apps/api/src/routers/projects.ts), this code is safe. Otherwise, a malicious user could craft repoName values containing GitHub search qualifiers to manipulate results.

Ensure the upstream schema validation restricts repoName to valid repository name characters.

🤖 Prompt for AI Agents
In `@apps/api/src/services/project.service.ts` around lines 50 - 53, The repoName
from filters is interpolated directly into the GitHub search string (see
filters.repoName and queryParts.push), so either enforce/validate the allowed
repo-name characters upstream in the router schema or add a guard here: trim
filters.repoName, validate it against an allowed-repo-name regex (e.g. only
letters, numbers, hyphen, underscore, dot), reject or throw if it contains
invalid characters, and use the validated/sanitized value (e.g.
sanitizedRepoName) when calling queryParts.push(`${sanitizedRepoName} in:name`)
to prevent injection via GitHub search qualifiers.

Comment on lines +83 to +92
<div className="w-full px-6 flex justify-center h-10">
<input
type="text"
placeholder="Enter repository name"
className="w-full rounded-md outline-none focus:outline-2 focus:outline-ox-purple px-2"
onChange={(e) => {
updateFilters({repoName: e.target.value})
}}
/>
</div>
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Uncontrolled input won't clear on reset, lacks accessibility and dark-theme styling.

Several issues with this input:

  1. Uncontrolled component: No value prop bound to state, so when resetFilters() runs after search (Line 52), the input text remains stale. Per coding guidelines, prefer controlled components.
  2. Missing aria-label: Required by coding guidelines for accessibility on interactive elements.
  3. Missing dark-theme colors: No bg-* or text-* classes — the input will render with browser defaults (white background, black text), which clashes with the dark panel (bg-[#0c0c0d]).
Proposed fix

You'll need to wire the input value to a state variable. One approach is to read repoName from the store filters:

-            <div className="w-full px-6 flex justify-center h-10">
-              <input 
-                type="text" 
-                placeholder="Enter repository name"
-                className="w-full rounded-md outline-none focus:outline-2 focus:outline-ox-purple px-2"
-                onChange={(e) => {
-                  updateFilters({repoName: e.target.value})
-                }}
-              />
-            </div>
+            <div className="w-full px-6 flex justify-center h-10">
+              <input 
+                type="text" 
+                placeholder="Enter repository name"
+                aria-label="Search by repository name"
+                value={(filters as Record<string, string>).repoName ?? ""}
+                className="w-full rounded-md bg-[`#141418`] text-white border border-[`#28282c`] outline-none focus:outline-2 focus:outline-ox-purple px-2 placeholder:text-zinc-500"
+                onChange={(e) => {
+                  updateFilters({repoName: e.target.value})
+                }}
+              />
+            </div>

As per coding guidelines: "Prefer controlled components over uncontrolled", "Include proper aria labels for accessibility", and "NEVER use hardcoded hex values directly in components; ALWAYS reference colors from the design token system using Tailwind classes" — consider using semantic color tokens (e.g., bg-surface-primary, text-text-primary) if they exist in your design system instead of the hex values I used above.

🤖 Prompt for AI Agents
In `@apps/web/src/components/ui/FiltersContainer.tsx` around lines 83 - 92, The
input in FiltersContainer is currently uncontrolled and lacks accessibility and
dark-theme styling; bind the input's value to the filters' repoName (read from
the store or props), keep the existing onChange handler calling
updateFilters({repoName: e.target.value}), add an appropriate aria-label (e.g.,
aria-label="Repository name"), and replace the hard/absent colors with
design-token Tailwind classes (e.g., bg-surface-primary, text-text-primary,
placeholder:text-text-secondary) so the field clears when resetFilters() updates
repoName and matches dark theme; update the input element in FiltersContainer
accordingly.

// forks: { min: "50", max: "1000" },
// pushed: ">=2024-12-08",
// created: ">=2024-12-12",
// reponame: "name"
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Typo in comment: reponame should be repoName.

The comment example uses lowercase reponame but the actual field is repoName (camelCase). This could mislead developers referencing the example.

-//   reponame: "name"
+//   repoName: "name"
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
// reponame: "name"
// repoName: "name"
🤖 Prompt for AI Agents
In `@apps/web/src/utils/converter.ts` at line 108, Update the inline example
comment in converter.ts where it shows "//   reponame: "name"" to use the
correct camelCase field name "repoName"; locate the comment near the converter
utilities (e.g., around functions that map or format repo objects) and change
"reponame" to "repoName" so the example matches the actual field used in the
code.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant