Search for user

This commit is contained in:
2025-10-17 15:21:04 +02:00
parent 0f3be28b47
commit c784b80773
2 changed files with 61 additions and 29 deletions
+18 -19
View File
@@ -71,33 +71,32 @@ export async function POST(req: NextRequest) {
*/ */
export async function GET(req: NextRequest) { export async function GET(req: NextRequest) {
const url = new URL(req.url); const url = new URL(req.url);
const query_id = url.searchParams.get("id"); const id = url.searchParams.get("id");
const username = url.searchParams.get("username");
const token = req.cookies.get("token")?.value; const token = req.cookies.get("token")?.value;
if (!query_id && !token) if (!token && !id && !username)
return NextResponse.json( return NextResponse.json(
{ message: "Query arg should be token or id" }, { message: "Query arg should be token or id or username" },
{ status: StatusCodes.BAD_REQUEST } { status: StatusCodes.BAD_REQUEST }
); );
let user_id = query_id; const { data: profile, error } = id
if (!user_id && token) { ? await supabase
const {
data: { user },
} = await supabase.auth.getUser(token);
user_id = user?.id ?? null;
}
if (!user_id)
return NextResponse.json(
{ message: "Invalid token" },
{ status: StatusCodes.BAD_REQUEST }
);
const { data: profile, error } = await supabase
.from("profiles") .from("profiles")
.select("id, username, display_name, avatar_url, node_address") .select("id, username, display_name, avatar_url, node_address")
.eq("id", user_id) .eq("id", id)
.maybeSingle()
: username
? await supabase
.from("profiles")
.select("id, username, display_name, avatar_url, node_address")
.eq("username", username)
.maybeSingle()
: await supabase
.from("profiles")
.select("id, username, display_name, avatar_url, node_address")
.eq("id", (await supabase.auth.getUser(token)).data.user?.id)
.maybeSingle(); .maybeSingle();
if (error) if (error)
+37 -4
View File
@@ -37,6 +37,7 @@ import { get, Response } from "@/lib/request";
import { cn } from "@/lib/utils"; import { cn } from "@/lib/utils";
import App from "@/types/app"; import App from "@/types/app";
import { ProfileSettings } from "@/types/settings"; import { ProfileSettings } from "@/types/settings";
import axios from "axios";
export default function AppSidebar({ export default function AppSidebar({
children, children,
@@ -53,6 +54,7 @@ export default function AppSidebar({
}>) { }>) {
const [servers, setServers] = useState<[string, string][]>([]); const [servers, setServers] = useState<[string, string][]>([]);
const [newServer, setNewServer] = useState({ name: "", ip: "" }); const [newServer, setNewServer] = useState({ name: "", ip: "" });
const [query, setQuery] = useState("");
const router = useRouter(); const router = useRouter();
const dms = Array.from( const dms = Array.from(
@@ -63,6 +65,15 @@ export default function AppSidebar({
) )
); );
const filteredDms = dms.filter((id) => {
const user = getUser(id, app.profiles, app.setProfiles);
const name = user?.display_name || "";
return (
name.toLowerCase().includes(query.toLowerCase()) ||
id.toLowerCase().includes(query.toLowerCase())
);
});
useEffect(() => { useEffect(() => {
const s = Cookies.get("servers")?.split(","); const s = Cookies.get("servers")?.split(",");
if (s) setServers(s.map((x) => x.trim().split("@") as [string, string])); if (s) setServers(s.map((x) => x.trim().split("@") as [string, string]));
@@ -213,12 +224,16 @@ export default function AppSidebar({
<h2>{server.name}</h2> <h2>{server.name}</h2>
</div> </div>
) : ( ) : (
<div className="p-3 border-b flex items-center gap-2"> <div className="p-3 border-b flex items-center">
<Search className="h-4 w-4 text-muted-foreground" /> <div className="relative w-full">
<Input <Input
placeholder="Find or start a conversation" placeholder="Find or start a conversation"
className="h-8" className="pr-8 h-8"
value={query}
onChange={(e) => setQuery(e.target.value)}
/> />
<Search className="absolute right-2 top-1/2 -translate-y-1/2 h-4 w-4 text-muted-foreground" />
</div>
</div> </div>
)} )}
<ScrollArea className="flex-1"> <ScrollArea className="flex-1">
@@ -231,7 +246,7 @@ export default function AppSidebar({
</> </>
) : ( ) : (
<> <>
{dms.map((id) => ( {filteredDms.map((id) => (
<DMItem <DMItem
name={ name={
getUser(id, app.profiles, app.setProfiles) getUser(id, app.profiles, app.setProfiles)
@@ -247,6 +262,24 @@ export default function AppSidebar({
app={app} app={app}
/> />
))} ))}
{filteredDms.length === 0 && query.trim() !== "" ? (
<div className="px-3 py-2">
<Button
variant="ghost"
className="w-full justify-start gap-2 text-sm"
onClick={async () => {
const response = await axios.get("/api/profile", {
params: { username: query },
});
const user = response.data as UserProfile;
router.push(`/chat/${user.id}`);
}}
>
<Plus className="h-4 w-4" />
Start new DM with “{query}”
</Button>
</div>
) : null}
</> </>
)} )}
</div> </div>