-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
f6f93c5
commit 9abbcad
Showing
9 changed files
with
2,270 additions
and
1,433 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,100 @@ | ||
"use client"; | ||
|
||
import { useSearchParams, usePathname, useRouter } from "next/navigation"; | ||
import { useState } from "react"; | ||
import { useDebouncedCallback } from "use-debounce"; | ||
|
||
export default function Search({ placeholder }: { placeholder: string }) { | ||
const searchParams = useSearchParams(); | ||
const pathname = usePathname(); | ||
const { replace } = useRouter(); | ||
//const [searchSuggs, setSearchSuggs] = useState([] as Array<{}>); | ||
const [searchFieldSuggs, setSearchFieldSuggs] = useState([] as Array<string>); | ||
|
||
const testArr = [ | ||
{ title: "1", description: "The number 1" }, | ||
{ title: "2", description: "The number 2" }, | ||
{ title: "3", description: "The number 3" }, | ||
{ title: "4", description: "The number 4" }, | ||
{ title: "5", description: "The number 5" } | ||
]; | ||
|
||
const handleSearch = useDebouncedCallback((search) => { | ||
const params = new URLSearchParams(searchParams); | ||
if (search) { | ||
params.set("q", search); | ||
|
||
const splitSearch = search.match(/\w+/g); //match on any word (\w+) with an optional trailing colon (:?) | ||
//set to array of keys that match entire search | ||
setSearchFieldSuggs(Object.keys(testArr[0]).filter((e) => e.toLowerCase().includes(splitSearch[splitSearch.length-1].toLowerCase()))); | ||
//set to array of objects where any value in the object matches the entire search | ||
//setSearchSuggs(testArr.filter((e) => { | ||
// return Object.values(e).filter((e2) => e2.toLowerCase().includes(search.toLowerCase())).length; | ||
//})); | ||
|
||
} else { | ||
params.delete("q"); | ||
|
||
setSearchFieldSuggs([]); | ||
//setSearchSuggs([]); | ||
} | ||
replace(`${pathname}?${params.toString()}`); | ||
}, 300); | ||
|
||
function suggClick(e: React.MouseEvent) { | ||
const params = new URLSearchParams(searchParams); | ||
|
||
//replace the last word with the clicked on suggestion | ||
let splitSearch = params.get("q")!.match(/\w+:?/g)!; //match on any word (\w+) with an optional trailing colon (:?). ! to assert existence since we know they both exist, otherwise you couldn't click on the div | ||
const lastLen = splitSearch[splitSearch.length-1].length; | ||
const newVal = params.get("q")!.trim().slice(0, -lastLen) + (e.target as HTMLElement).innerText + " "; | ||
params.set("q", newVal); //TS can't detect the type of e.target properly, so we assert it inline | ||
replace(`${pathname}?${params.toString()}`); | ||
|
||
const inp = document.getElementById("searchInput")! as HTMLInputElement; | ||
inp.focus(); | ||
inp.value = newVal; | ||
|
||
setSearchFieldSuggs([]); | ||
} | ||
|
||
return ( | ||
<div className="relative flex flex-1 flex-shrink-0 relative inline-block"> | ||
<label className="input input-bordered flex items-center gap-2 bg-neutral-content w-full"> | ||
<input | ||
id="searchInput" | ||
type="text" | ||
className="grow" | ||
placeholder={placeholder} | ||
onChange={(e) => { | ||
handleSearch(e.target.value); | ||
}} | ||
defaultValue={searchParams.get("q")?.toString()} | ||
/> | ||
<svg | ||
xmlns="http://www.w3.org/2000/svg" | ||
viewBox="0 0 16 16" | ||
fill="currentColor" | ||
className="h-4 w-4 opacity-70" | ||
> | ||
<path | ||
fillRule="evenodd" | ||
d="M9.965 11.026a5 5 0 1 1 1.06-1.06l2.755 2.754a.75.75 0 1 1-1.06 1.06l-2.755-2.754ZM10.5 7a3.5 3.5 0 1 1-7 0 3.5 3.5 0 0 1 7 0Z" | ||
clipRule="evenodd" | ||
/> | ||
</svg> | ||
</label> | ||
{/*{(searchFieldSuggs.length > 0 || searchSuggs.length > 0) &&*/} | ||
{searchFieldSuggs.length > 0 && | ||
<div className="absolute top-full inset-x-0 z-[10000] bg-neutral-content px-3 py-3 rounded-lg mt-1 flex flex-col"> | ||
{searchFieldSuggs.map((s, i) => ( | ||
<div key={i} onClick={suggClick} className="cursor-pointer hover:bg-neutral active:bg-neutral px-3 py-1 rounded-lg">{s}:</div> | ||
))} | ||
{/*{searchSuggs.map((s, i) => ( | ||
<div key={i} className="cursor-pointer hover:bg-neutral active:bg-neutral px-3 py-1 rounded-lg">{s.title}</div> | ||
))}*/} | ||
</div> | ||
} | ||
</div> | ||
); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,42 +1,19 @@ | ||
import { authMiddleware } from "@clerk/nextjs"; | ||
import { clerkMiddleware, createRouteMatcher } from "@clerk/nextjs/server"; | ||
|
||
export default authMiddleware({ | ||
publicRoutes: (request) => { | ||
return !(request.nextUrl.pathname.startsWith("/admin") || request.nextUrl.pathname.startsWith("/api/admin") | ||
|| request.nextUrl.pathname.startsWith("/tourmaline") || request.nextUrl.pathname.startsWith("/api/tourmaline")) | ||
}, | ||
}); | ||
const isProtectedRoute = createRouteMatcher(["/admin(.*)", "/api/admin(.*)", "/tourmaline(.*)", "/api/tourmaline(.*)"]); | ||
|
||
export const config = { | ||
matcher: ["/((?!.+\\.[\\w]+$|_next).*)", "/", "/(api|trpc)(.*)"], | ||
}; | ||
export default clerkMiddleware( | ||
(auth, req) => { | ||
if (isProtectedRoute(req)) auth().protect() | ||
}, | ||
//{ debug: true } | ||
); | ||
|
||
// import { authMiddleware, redirectToSignIn } from "@clerk/nextjs"; | ||
// import { NextResponse } from "next/server"; | ||
|
||
// export default authMiddleware({ | ||
// publicRoutes: (request) => { | ||
// return !(request.nextUrl.pathname.startsWith("/admin") || request.nextUrl.pathname.startsWith("/api/admin")); | ||
// }, | ||
// afterAuth(auth, req, evt) { | ||
// // Handle users who aren't authenticated | ||
// if (!auth.userId && !auth.isPublicRoute) { | ||
// return redirectToSignIn({ returnBackUrl: req.url }); | ||
// } | ||
// // Redirect logged in users to organization selection page if they are not active in an organization | ||
// if ( | ||
// auth.userId && | ||
// !auth.orgId && | ||
// req.nextUrl.pathname !== "/org-selection" | ||
// ) { | ||
// const orgSelection = new URL("/org-selection", req.url); | ||
// return NextResponse.redirect(orgSelection); | ||
// } | ||
// // If the user is logged in and trying to access a protected route, allow them to access route | ||
// if (auth.userId && !auth.isPublicRoute) { | ||
// return NextResponse.next(); | ||
// } | ||
// // Allow users visiting public routes to access them | ||
// return NextResponse.next(); | ||
// }, | ||
// }); | ||
export const config = { | ||
matcher: [ | ||
// Skip Next.js internals and all static files, unless found in search params | ||
"/((?!_next|[^?]*\\.(?:html?|css|js(?!on)|jpe?g|webp|png|gif|svg|ttf|woff2?|ico|csv|docx?|xlsx?|zip|webmanifest)).*)", | ||
// Always run for API routes | ||
"/(api|trpc)(.*)", | ||
], | ||
} |
Oops, something went wrong.