diff --git a/api/applications.ts b/api/applications.ts index d787a1fb..9b802684 100644 --- a/api/applications.ts +++ b/api/applications.ts @@ -5,10 +5,7 @@ const supabaseServiceRole = process.env.SUPABASE_SERVICE_ROLE || ""; const supabase = createClient(supabaseUrl, supabaseServiceRole); -export async function getMyApplications( - req: Request, - userId: string -) { +export async function getMyApplications(req: Request, userId: string) { const url = new URL(req.url); const page = parseInt(url.searchParams.get("page") || "1"); const limit = parseInt(url.searchParams.get("limit") || "10"); @@ -25,7 +22,7 @@ export async function getMyApplications( if (!creator) { return new Response( JSON.stringify({ error: "Creator profile not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -43,7 +40,7 @@ export async function getMyApplications( updated_at, aethex_opportunities(id, title, arm_affiliation, job_type, posted_by_id, aethex_creators!aethex_opportunities_posted_by_id_fkey(username, avatar_url)) `, - { count: "exact" } + { count: "exact" }, ) .eq("creator_id", creator.id); @@ -73,20 +70,20 @@ export async function getMyApplications( { status: 200, headers: { "Content-Type": "application/json" }, - } + }, ); } catch (error) { console.error("Error fetching applications:", error); return new Response( JSON.stringify({ error: "Failed to fetch applications" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } export async function getApplicationsForOpportunity( opportunityId: string, - userId: string + userId: string, ) { try { // Verify user owns this opportunity @@ -97,10 +94,10 @@ export async function getApplicationsForOpportunity( .single(); if (!opportunity) { - return new Response( - JSON.stringify({ error: "Opportunity not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Opportunity not found" }), { + status: 404, + headers: { "Content-Type": "application/json" }, + }); } const { data: creator } = await supabase @@ -110,10 +107,10 @@ export async function getApplicationsForOpportunity( .single(); if (creator?.id !== opportunity.posted_by_id) { - return new Response( - JSON.stringify({ error: "Unauthorized" }), - { status: 403, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Unauthorized" }), { + status: 403, + headers: { "Content-Type": "application/json" }, + }); } const { data, error } = await supabase @@ -126,7 +123,7 @@ export async function getApplicationsForOpportunity( cover_letter, applied_at, aethex_creators(username, avatar_url, bio, skills) - ` + `, ) .eq("opportunity_id", opportunityId) .order("applied_at", { ascending: false }); @@ -141,15 +138,12 @@ export async function getApplicationsForOpportunity( console.error("Error fetching opportunity applications:", error); return new Response( JSON.stringify({ error: "Failed to fetch applications" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } -export async function submitApplication( - req: Request, - userId: string -) { +export async function submitApplication(req: Request, userId: string) { try { const body = await req.json(); const { opportunity_id, cover_letter } = body; @@ -164,7 +158,7 @@ export async function submitApplication( if (!creator) { return new Response( JSON.stringify({ error: "Creator profile not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -179,7 +173,7 @@ export async function submitApplication( if (!opportunity) { return new Response( JSON.stringify({ error: "Opportunity not found or closed" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -193,8 +187,10 @@ export async function submitApplication( if (existing) { return new Response( - JSON.stringify({ error: "You have already applied to this opportunity" }), - { status: 400, headers: { "Content-Type": "application/json" } } + JSON.stringify({ + error: "You have already applied to this opportunity", + }), + { status: 400, headers: { "Content-Type": "application/json" } }, ); } @@ -219,7 +215,7 @@ export async function submitApplication( console.error("Error submitting application:", error); return new Response( JSON.stringify({ error: "Failed to submit application" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } @@ -227,7 +223,7 @@ export async function submitApplication( export async function updateApplicationStatus( req: Request, applicationId: string, - userId: string + userId: string, ) { try { const body = await req.json(); @@ -241,16 +237,16 @@ export async function updateApplicationStatus( id, opportunity_id, aethex_opportunities(posted_by_id) - ` + `, ) .eq("id", applicationId) .single(); if (!application) { - return new Response( - JSON.stringify({ error: "Application not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Application not found" }), { + status: 404, + headers: { "Content-Type": "application/json" }, + }); } const { data: creator } = await supabase @@ -260,10 +256,10 @@ export async function updateApplicationStatus( .single(); if (creator?.id !== application.aethex_opportunities.posted_by_id) { - return new Response( - JSON.stringify({ error: "Unauthorized" }), - { status: 403, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Unauthorized" }), { + status: 403, + headers: { "Content-Type": "application/json" }, + }); } const { data, error } = await supabase @@ -287,14 +283,14 @@ export async function updateApplicationStatus( console.error("Error updating application:", error); return new Response( JSON.stringify({ error: "Failed to update application" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } export async function withdrawApplication( applicationId: string, - userId: string + userId: string, ) { try { // Verify user owns this application @@ -305,10 +301,10 @@ export async function withdrawApplication( .single(); if (!application) { - return new Response( - JSON.stringify({ error: "Application not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Application not found" }), { + status: 404, + headers: { "Content-Type": "application/json" }, + }); } const { data: creator } = await supabase @@ -318,10 +314,10 @@ export async function withdrawApplication( .single(); if (creator?.id !== application.creator_id) { - return new Response( - JSON.stringify({ error: "Unauthorized" }), - { status: 403, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Unauthorized" }), { + status: 403, + headers: { "Content-Type": "application/json" }, + }); } const { error } = await supabase @@ -339,7 +335,7 @@ export async function withdrawApplication( console.error("Error withdrawing application:", error); return new Response( JSON.stringify({ error: "Failed to withdraw application" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } diff --git a/api/creators.ts b/api/creators.ts index e907c8b5..8f17d70c 100644 --- a/api/creators.ts +++ b/api/creators.ts @@ -28,7 +28,7 @@ export async function getCreators(req: Request) { created_at, aethex_projects(count) `, - { count: "exact" } + { count: "exact" }, ) .eq("is_discoverable", true) .order("created_at", { ascending: false }); @@ -38,9 +38,7 @@ export async function getCreators(req: Request) { } if (search) { - query = query.or( - `username.ilike.%${search}%,bio.ilike.%${search}%` - ); + query = query.or(`username.ilike.%${search}%,bio.ilike.%${search}%`); } const start = (page - 1) * limit; @@ -63,14 +61,14 @@ export async function getCreators(req: Request) { { status: 200, headers: { "Content-Type": "application/json" }, - } + }, ); } catch (error) { console.error("Error fetching creators:", error); - return new Response( - JSON.stringify({ error: "Failed to fetch creators" }), - { status: 500, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Failed to fetch creators" }), { + status: 500, + headers: { "Content-Type": "application/json" }, + }); } } @@ -92,7 +90,7 @@ export async function getCreatorByUsername(username: string) { updated_at, aethex_projects(id, title, description, url, image_url, tags, is_featured), aethex_skill_endorsements(skill, count) - ` + `, ) .eq("username", username) .eq("is_discoverable", true) @@ -117,10 +115,7 @@ export async function getCreatorByUsername(username: string) { } } -export async function createCreatorProfile( - req: Request, - userId: string -) { +export async function createCreatorProfile(req: Request, userId: string) { try { const body = await req.json(); const { @@ -158,15 +153,12 @@ export async function createCreatorProfile( console.error("Error creating creator profile:", error); return new Response( JSON.stringify({ error: "Failed to create creator profile" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } -export async function updateCreatorProfile( - req: Request, - userId: string -) { +export async function updateCreatorProfile(req: Request, userId: string) { try { const body = await req.json(); const { @@ -209,15 +201,12 @@ export async function updateCreatorProfile( console.error("Error updating creator profile:", error); return new Response( JSON.stringify({ error: "Failed to update creator profile" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } -export async function addProjectToCreator( - req: Request, - creatorId: string -) { +export async function addProjectToCreator(req: Request, creatorId: string) { try { const body = await req.json(); const { title, description, url, image_url, tags, is_featured } = body; @@ -244,17 +233,17 @@ export async function addProjectToCreator( }); } catch (error) { console.error("Error adding project:", error); - return new Response( - JSON.stringify({ error: "Failed to add project" }), - { status: 500, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Failed to add project" }), { + status: 500, + headers: { "Content-Type": "application/json" }, + }); } } export async function endorseSkill( req: Request, creatorId: string, - endorsedByUserId: string + endorsedByUserId: string, ) { try { const body = await req.json(); @@ -270,7 +259,7 @@ export async function endorseSkill( if (!endorsingCreator) { return new Response( JSON.stringify({ error: "Endorsing user not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -292,9 +281,9 @@ export async function endorseSkill( }); } catch (error) { console.error("Error endorsing skill:", error); - return new Response( - JSON.stringify({ error: "Failed to endorse skill" }), - { status: 500, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Failed to endorse skill" }), { + status: 500, + headers: { "Content-Type": "application/json" }, + }); } } diff --git a/api/devconnect-links.ts b/api/devconnect-links.ts index de09539f..d3192384 100644 --- a/api/devconnect-links.ts +++ b/api/devconnect-links.ts @@ -5,10 +5,7 @@ const supabaseServiceRole = process.env.SUPABASE_SERVICE_ROLE || ""; const supabase = createClient(supabaseUrl, supabaseServiceRole); -export async function linkDevConnectAccount( - req: Request, - userId: string -) { +export async function linkDevConnectAccount(req: Request, userId: string) { try { const body = await req.json(); const { devconnect_username, devconnect_profile_url } = body; @@ -16,7 +13,7 @@ export async function linkDevConnectAccount( if (!devconnect_username) { return new Response( JSON.stringify({ error: "DevConnect username is required" }), - { status: 400, headers: { "Content-Type": "application/json" } } + { status: 400, headers: { "Content-Type": "application/json" } }, ); } @@ -29,8 +26,10 @@ export async function linkDevConnectAccount( if (!creator) { return new Response( - JSON.stringify({ error: "Creator profile not found. Create profile first." }), - { status: 404, headers: { "Content-Type": "application/json" } } + JSON.stringify({ + error: "Creator profile not found. Create profile first.", + }), + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -50,7 +49,9 @@ export async function linkDevConnectAccount( .from("aethex_devconnect_links") .update({ devconnect_username, - devconnect_profile_url: devconnect_profile_url || `https://devconnect.com/${devconnect_username}`, + devconnect_profile_url: + devconnect_profile_url || + `https://devconnect.com/${devconnect_username}`, }) .eq("aethex_creator_id", creator.id) .select() @@ -66,7 +67,9 @@ export async function linkDevConnectAccount( .insert({ aethex_creator_id: creator.id, devconnect_username, - devconnect_profile_url: devconnect_profile_url || `https://devconnect.com/${devconnect_username}`, + devconnect_profile_url: + devconnect_profile_url || + `https://devconnect.com/${devconnect_username}`, }) .select() .single(); @@ -89,7 +92,7 @@ export async function linkDevConnectAccount( console.error("Error linking DevConnect account:", error); return new Response( JSON.stringify({ error: "Failed to link DevConnect account" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } @@ -106,7 +109,7 @@ export async function getDevConnectLink(userId: string) { if (!creator) { return new Response( JSON.stringify({ error: "Creator profile not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -128,7 +131,7 @@ export async function getDevConnectLink(userId: string) { console.error("Error fetching DevConnect link:", error); return new Response( JSON.stringify({ error: "Failed to fetch DevConnect link" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } @@ -145,7 +148,7 @@ export async function unlinkDevConnectAccount(userId: string) { if (!creator) { return new Response( JSON.stringify({ error: "Creator profile not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -170,15 +173,12 @@ export async function unlinkDevConnectAccount(userId: string) { console.error("Error unlinking DevConnect account:", error); return new Response( JSON.stringify({ error: "Failed to unlink DevConnect account" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } -export async function verifyDevConnectLink( - req: Request, - userId: string -) { +export async function verifyDevConnectLink(req: Request, userId: string) { try { const body = await req.json(); const { verification_code } = body; @@ -193,7 +193,7 @@ export async function verifyDevConnectLink( if (!creator) { return new Response( JSON.stringify({ error: "Creator profile not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -216,7 +216,7 @@ export async function verifyDevConnectLink( console.error("Error verifying DevConnect link:", error); return new Response( JSON.stringify({ error: "Failed to verify DevConnect link" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } diff --git a/api/opportunities.ts b/api/opportunities.ts index 82361804..a5bcf75d 100644 --- a/api/opportunities.ts +++ b/api/opportunities.ts @@ -34,7 +34,7 @@ export async function getOpportunities(req: Request) { created_at, aethex_applications(count) `, - { count: "exact" } + { count: "exact" }, ) .eq("status", "open"); @@ -43,9 +43,7 @@ export async function getOpportunities(req: Request) { } if (search) { - query = query.or( - `title.ilike.%${search}%,description.ilike.%${search}%` - ); + query = query.or(`title.ilike.%${search}%,description.ilike.%${search}%`); } if (jobType) { @@ -80,13 +78,13 @@ export async function getOpportunities(req: Request) { { status: 200, headers: { "Content-Type": "application/json" }, - } + }, ); } catch (error) { console.error("Error fetching opportunities:", error); return new Response( JSON.stringify({ error: "Failed to fetch opportunities" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } @@ -111,7 +109,7 @@ export async function getOpportunityById(opportunityId: string) { created_at, updated_at, aethex_applications(count) - ` + `, ) .eq("id", opportunityId) .eq("status", "open") @@ -126,10 +124,7 @@ export async function getOpportunityById(opportunityId: string) { } } -export async function createOpportunity( - req: Request, - userId: string -) { +export async function createOpportunity(req: Request, userId: string) { try { const body = await req.json(); const { @@ -151,8 +146,10 @@ export async function createOpportunity( if (!creator) { return new Response( - JSON.stringify({ error: "Creator profile not found. Create profile first." }), - { status: 404, headers: { "Content-Type": "application/json" } } + JSON.stringify({ + error: "Creator profile not found. Create profile first.", + }), + { status: 404, headers: { "Content-Type": "application/json" } }, ); } @@ -182,7 +179,7 @@ export async function createOpportunity( console.error("Error creating opportunity:", error); return new Response( JSON.stringify({ error: "Failed to create opportunity" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } @@ -190,7 +187,7 @@ export async function createOpportunity( export async function updateOpportunity( req: Request, opportunityId: string, - userId: string + userId: string, ) { try { const body = await req.json(); @@ -212,10 +209,10 @@ export async function updateOpportunity( .single(); if (!opportunity) { - return new Response( - JSON.stringify({ error: "Opportunity not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Opportunity not found" }), { + status: 404, + headers: { "Content-Type": "application/json" }, + }); } const { data: creator } = await supabase @@ -225,10 +222,10 @@ export async function updateOpportunity( .single(); if (creator?.id !== opportunity.posted_by_id) { - return new Response( - JSON.stringify({ error: "Unauthorized" }), - { status: 403, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Unauthorized" }), { + status: 403, + headers: { "Content-Type": "application/json" }, + }); } const { data, error } = await supabase @@ -257,15 +254,12 @@ export async function updateOpportunity( console.error("Error updating opportunity:", error); return new Response( JSON.stringify({ error: "Failed to update opportunity" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } -export async function closeOpportunity( - opportunityId: string, - userId: string -) { +export async function closeOpportunity(opportunityId: string, userId: string) { try { // Verify user owns this opportunity const { data: opportunity } = await supabase @@ -275,10 +269,10 @@ export async function closeOpportunity( .single(); if (!opportunity) { - return new Response( - JSON.stringify({ error: "Opportunity not found" }), - { status: 404, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Opportunity not found" }), { + status: 404, + headers: { "Content-Type": "application/json" }, + }); } const { data: creator } = await supabase @@ -288,10 +282,10 @@ export async function closeOpportunity( .single(); if (creator?.id !== opportunity.posted_by_id) { - return new Response( - JSON.stringify({ error: "Unauthorized" }), - { status: 403, headers: { "Content-Type": "application/json" } } - ); + return new Response(JSON.stringify({ error: "Unauthorized" }), { + status: 403, + headers: { "Content-Type": "application/json" }, + }); } const { data, error } = await supabase @@ -314,7 +308,7 @@ export async function closeOpportunity( console.error("Error closing opportunity:", error); return new Response( JSON.stringify({ error: "Failed to close opportunity" }), - { status: 500, headers: { "Content-Type": "application/json" } } + { status: 500, headers: { "Content-Type": "application/json" } }, ); } } diff --git a/client/App.tsx b/client/App.tsx index ae382dcf..756f812f 100644 --- a/client/App.tsx +++ b/client/App.tsx @@ -144,7 +144,10 @@ const App = () => ( /> } /> } /> - } /> + } + /> } /> ( {/* Creator Network routes */} } /> - } /> + } + /> } /> - } /> + } + /> {/* Service routes */} } /> diff --git a/client/api/applications.ts b/client/api/applications.ts index 111990c1..030e363d 100644 --- a/client/api/applications.ts +++ b/client/api/applications.ts @@ -63,7 +63,7 @@ export async function getMyApplications(filters?: { export async function getApplicationsForOpportunity(opportunityId: string) { const response = await fetch( - `${API_BASE}/api/opportunities/${opportunityId}/applications` + `${API_BASE}/api/opportunities/${opportunityId}/applications`, ); if (!response.ok) throw new Error("Failed to fetch applications"); const data = await response.json(); @@ -88,20 +88,28 @@ export async function updateApplicationStatus( data: { status: "reviewing" | "accepted" | "rejected"; response_message?: string; - } + }, ): Promise { - const response = await fetch(`${API_BASE}/api/applications/${applicationId}/status`, { - method: "PUT", - headers: { "Content-Type": "application/json" }, - body: JSON.stringify(data), - }); + const response = await fetch( + `${API_BASE}/api/applications/${applicationId}/status`, + { + method: "PUT", + headers: { "Content-Type": "application/json" }, + body: JSON.stringify(data), + }, + ); if (!response.ok) throw new Error("Failed to update application"); return response.json(); } -export async function withdrawApplication(applicationId: string): Promise { - const response = await fetch(`${API_BASE}/api/applications/${applicationId}`, { - method: "DELETE", - }); +export async function withdrawApplication( + applicationId: string, +): Promise { + const response = await fetch( + `${API_BASE}/api/applications/${applicationId}`, + { + method: "DELETE", + }, + ); if (!response.ok) throw new Error("Failed to withdraw application"); } diff --git a/client/api/creators.ts b/client/api/creators.ts index eb4a4583..e82050c3 100644 --- a/client/api/creators.ts +++ b/client/api/creators.ts @@ -130,35 +130,50 @@ export async function addProject(data: { return response.json(); } -export async function updateProject(projectId: string, data: { - title?: string; - description?: string; - url?: string; - image_url?: string; - tags?: string[]; - is_featured?: boolean; -}): Promise { - const response = await fetch(`${API_BASE}/api/creators/me/projects/${projectId}`, { - method: "PUT", - headers: { "Content-Type": "application/json" }, - body: JSON.stringify(data), - }); +export async function updateProject( + projectId: string, + data: { + title?: string; + description?: string; + url?: string; + image_url?: string; + tags?: string[]; + is_featured?: boolean; + }, +): Promise { + const response = await fetch( + `${API_BASE}/api/creators/me/projects/${projectId}`, + { + method: "PUT", + headers: { "Content-Type": "application/json" }, + body: JSON.stringify(data), + }, + ); if (!response.ok) throw new Error("Failed to update project"); return response.json(); } export async function deleteProject(projectId: string): Promise { - const response = await fetch(`${API_BASE}/api/creators/me/projects/${projectId}`, { - method: "DELETE", - }); + const response = await fetch( + `${API_BASE}/api/creators/me/projects/${projectId}`, + { + method: "DELETE", + }, + ); if (!response.ok) throw new Error("Failed to delete project"); } -export async function endorseSkill(creatorId: string, skill: string): Promise { - const response = await fetch(`${API_BASE}/api/creators/${creatorId}/endorse`, { - method: "POST", - headers: { "Content-Type": "application/json" }, - body: JSON.stringify({ skill }), - }); +export async function endorseSkill( + creatorId: string, + skill: string, +): Promise { + const response = await fetch( + `${API_BASE}/api/creators/${creatorId}/endorse`, + { + method: "POST", + headers: { "Content-Type": "application/json" }, + body: JSON.stringify({ skill }), + }, + ); if (!response.ok) throw new Error("Failed to endorse skill"); } diff --git a/client/api/devconnect-links.ts b/client/api/devconnect-links.ts index 13004cce..73821688 100644 --- a/client/api/devconnect-links.ts +++ b/client/api/devconnect-links.ts @@ -36,7 +36,9 @@ export async function unlinkDevConnectAccount(): Promise { if (!response.ok) throw new Error("Failed to unlink DevConnect account"); } -export async function verifyDevConnectLink(verificationCode: string): Promise { +export async function verifyDevConnectLink( + verificationCode: string, +): Promise { const response = await fetch(`${API_BASE}/api/devconnect/link/verify`, { method: "POST", headers: { "Content-Type": "application/json" }, diff --git a/client/api/opportunities.ts b/client/api/opportunities.ts index e60446d2..bce837bb 100644 --- a/client/api/opportunities.ts +++ b/client/api/opportunities.ts @@ -57,7 +57,8 @@ export async function getOpportunities(filters?: { if (filters?.arm) params.append("arm", filters.arm); if (filters?.search) params.append("search", filters.search); if (filters?.jobType) params.append("jobType", filters.jobType); - if (filters?.experienceLevel) params.append("experienceLevel", filters.experienceLevel); + if (filters?.experienceLevel) + params.append("experienceLevel", filters.experienceLevel); if (filters?.sort) params.append("sort", filters.sort); if (filters?.page) params.append("page", String(filters.page)); if (filters?.limit) params.append("limit", String(filters.limit)); @@ -73,7 +74,9 @@ export async function getOpportunityById(id: string): Promise { return response.json(); } -export async function createOpportunity(data: CreateOpportunityData): Promise { +export async function createOpportunity( + data: CreateOpportunityData, +): Promise { const response = await fetch(`${API_BASE}/api/opportunities`, { method: "POST", headers: { "Content-Type": "application/json" }, @@ -85,7 +88,7 @@ export async function createOpportunity(data: CreateOpportunityData): Promise + data: Partial, ): Promise { const response = await fetch(`${API_BASE}/api/opportunities/${id}`, { method: "PUT", @@ -104,7 +107,9 @@ export async function closeOpportunity(id: string): Promise { } export async function getApplicationsForOpportunity(opportunityId: string) { - const response = await fetch(`${API_BASE}/api/opportunities/${opportunityId}/applications`); + const response = await fetch( + `${API_BASE}/api/opportunities/${opportunityId}/applications`, + ); if (!response.ok) throw new Error("Failed to fetch applications"); return response.json(); } diff --git a/client/components/creator-network/ArmBadge.tsx b/client/components/creator-network/ArmBadge.tsx index 46869b5f..8bbd943a 100644 --- a/client/components/creator-network/ArmBadge.tsx +++ b/client/components/creator-network/ArmBadge.tsx @@ -35,7 +35,8 @@ export interface ArmBadgeProps { export function ArmBadge({ arm, size = "md" }: ArmBadgeProps) { const colors = ARM_COLORS[arm.toLowerCase()] || ARM_COLORS.labs; - const sizeClass = size === "sm" ? "text-xs" : size === "lg" ? "text-base" : "text-sm"; + const sizeClass = + size === "sm" ? "text-xs" : size === "lg" ? "text-base" : "text-sm"; return ( diff --git a/client/components/creator-network/CreatorCard.tsx b/client/components/creator-network/CreatorCard.tsx index 1871d1ee..52aaab52 100644 --- a/client/components/creator-network/CreatorCard.tsx +++ b/client/components/creator-network/CreatorCard.tsx @@ -19,7 +19,9 @@ export function CreatorCard({ creator }: CreatorCardProps) {
- {creator.username.charAt(0).toUpperCase()} + + {creator.username.charAt(0).toUpperCase()} + {creator.devconnect_linked && (
diff --git a/client/components/creator-network/DevConnectLinkModal.tsx b/client/components/creator-network/DevConnectLinkModal.tsx index 70d0f60c..8f74923a 100644 --- a/client/components/creator-network/DevConnectLinkModal.tsx +++ b/client/components/creator-network/DevConnectLinkModal.tsx @@ -47,8 +47,10 @@ export function DevConnectLinkModal({ onSuccess?.(); } catch (error) { toast( - error instanceof Error ? error.message : "Failed to link DevConnect account", - "error" + error instanceof Error + ? error.message + : "Failed to link DevConnect account", + "error", ); } finally { setIsLoading(false); @@ -61,7 +63,8 @@ export function DevConnectLinkModal({ Link Your DevConnect Account - Enter your DevConnect username to link your profile. This allows you to showcase your presence on both platforms. + Enter your DevConnect username to link your profile. This allows you + to showcase your presence on both platforms. @@ -79,7 +82,8 @@ export function DevConnectLinkModal({ />

- Your username will be used to create a link to your DevConnect profile + Your username will be used to create a link to your DevConnect + profile

diff --git a/client/components/creator-network/OpportunityCard.tsx b/client/components/creator-network/OpportunityCard.tsx index 67c232ca..2263b7de 100644 --- a/client/components/creator-network/OpportunityCard.tsx +++ b/client/components/creator-network/OpportunityCard.tsx @@ -29,7 +29,8 @@ export function OpportunityCard({ opportunity }: OpportunityCardProps) { const formatSalary = (min?: number, max?: number) => { if (!min && !max) return "Not specified"; - if (min && max) return `$${min.toLocaleString()} - $${max.toLocaleString()}`; + if (min && max) + return `$${min.toLocaleString()} - $${max.toLocaleString()}`; if (min) return `$${min.toLocaleString()}+`; if (max) return `Up to $${max.toLocaleString()}`; }; @@ -41,11 +42,15 @@ export function OpportunityCard({ opportunity }: OpportunityCardProps) {
- {poster.username.charAt(0).toUpperCase()} + + {poster.username.charAt(0).toUpperCase()} +

Posted by

-

@{poster.username}

+

+ @{poster.username} +

@@ -86,7 +91,9 @@ export function OpportunityCard({ opportunity }: OpportunityCardProps) {
{opportunity.aethex_applications.count}{" "} - {opportunity.aethex_applications.count === 1 ? "applicant" : "applicants"} + {opportunity.aethex_applications.count === 1 + ? "applicant" + : "applicants"}
)}
diff --git a/client/components/onboarding/CreatorProfile.tsx b/client/components/onboarding/CreatorProfile.tsx index ea769c05..ae5fb3ba 100644 --- a/client/components/onboarding/CreatorProfile.tsx +++ b/client/components/onboarding/CreatorProfile.tsx @@ -15,10 +15,34 @@ interface CreatorProfileProps { } const AVAILABLE_ARMS = [ - { id: "labs", name: "Labs", description: "R&D & Innovation", color: "from-yellow-500 to-orange-500", icon: Zap }, - { id: "gameforge", name: "GameForge", description: "Game Development", color: "from-green-500 to-emerald-500", icon: Code }, - { id: "corp", name: "Corp", description: "Enterprise Consulting", color: "from-blue-500 to-cyan-500", icon: Users }, - { id: "foundation", name: "Foundation", description: "Education & Open Source", color: "from-red-500 to-pink-500", icon: Users }, + { + id: "labs", + name: "Labs", + description: "R&D & Innovation", + color: "from-yellow-500 to-orange-500", + icon: Zap, + }, + { + id: "gameforge", + name: "GameForge", + description: "Game Development", + color: "from-green-500 to-emerald-500", + icon: Code, + }, + { + id: "corp", + name: "Corp", + description: "Enterprise Consulting", + color: "from-blue-500 to-cyan-500", + icon: Users, + }, + { + id: "foundation", + name: "Foundation", + description: "Education & Open Source", + color: "from-red-500 to-pink-500", + icon: Users, + }, ]; const SKILL_SUGGESTIONS = [ @@ -48,7 +72,11 @@ export default function CreatorProfile({ totalSteps, }: CreatorProfileProps) { const [inputValue, setInputValue] = useState(""); - const creatorData = data.creatorProfile || { bio: "", skills: [], primaryArm: "" }; + const creatorData = data.creatorProfile || { + bio: "", + skills: [], + primaryArm: "", + }; const canProceed = useMemo(() => { return creatorData.primaryArm && creatorData.skills.length > 0; @@ -138,7 +166,9 @@ export default function CreatorProfile({
{arm.name}
-
{arm.description}
+
+ {arm.description} +
@@ -150,7 +180,10 @@ export default function CreatorProfile({ {/* Skills Selection */}
{/* Skills Input */} @@ -221,11 +254,7 @@ export default function CreatorProfile({ {/* Navigation */}
-
- Enterprise consulting and business solutions + + Enterprise consulting and business solutions +
-

Active Clients

-

34

-

Enterprise accounts

+

+ Active Clients +

+

+ 34 +

+

+ Enterprise accounts +

-

ARR

-

$4.2M

-

Annual recurring

+

+ ARR +

+

+ $4.2M +

+

+ Annual recurring +

-

Retention Rate

-

94%

-

12-month

+

+ Retention Rate +

+

+ 94% +

+

+ 12-month +

-

Consulting Team

-

16

-

Senior consultants

+

+ Consulting Team +

+

+ 16 +

+

+ Senior consultants +

@@ -1260,51 +1339,93 @@ export default function Admin() {
- Foundation - Education & Community + + Foundation - Education & Community +
- Educational impact and talent pipeline effectiveness + + Educational impact and talent pipeline effectiveness +
-

Student Metrics

+

+ Student Metrics +

-

Course Completion

-

87.5%

-

↑ +12% YoY

+

+ Course Completion +

+

+ 87.5% +

+

+ ↑ +12% YoY +

-

Active Learners

-

342

-

↑ +28 new

+

+ Active Learners +

+

+ 342 +

+

+ ↑ +28 new +

-

Placement Rate

-

42%

-

54 hired

+

+ Placement Rate +

+

+ 42% +

+

+ 54 hired +

-

Open Source Impact

+

+ Open Source Impact +

-

GitHub Forks

-

2.3K

+

+ GitHub Forks +

+

+ 2.3K +

-

PRs

-

184

+

+ PRs +

+

+ 184 +

-

External Usage

-

452

+

+ External Usage +

+

+ 452 +

-

Contributors

-

67

+

+ Contributors +

+

+ 67 +

@@ -1320,29 +1441,55 @@ export default function Admin() { Nexus - Talent Marketplace
- Creator network and opportunity matching metrics + + Creator network and opportunity matching metrics +
-

Active Creators

-

1,240

-

↑ +180 this month

+

+ Active Creators +

+

+ 1,240 +

+

+ ↑ +180 this month +

-

Open Opportunities

-

342

-

Across all arms

+

+ Open Opportunities +

+

+ 342 +

+

+ Across all arms +

-

Successful Matches

-

87

-

This quarter

+

+ Successful Matches +

+

+ 87 +

+

+ This quarter +

-

Match Success Rate

-

68%

-

Application to hire

+

+ Match Success Rate +

+

+ 68% +

+

+ Application to hire +

diff --git a/client/pages/Corp.tsx b/client/pages/Corp.tsx index 345c5397..664e26c5 100644 --- a/client/pages/Corp.tsx +++ b/client/pages/Corp.tsx @@ -137,7 +137,11 @@ export default function Corp() { The Profit Engine

- AeThex Corp delivers high-margin enterprise consulting and specialized software development. We leverage proprietary technologies from Labs to create cutting-edge solutions while generating stable, benchmarkable revenue that funds our ambitious R&D roadmap. + AeThex Corp delivers high-margin enterprise consulting and + specialized software development. We leverage proprietary + technologies from Labs to create cutting-edge solutions while + generating stable, benchmarkable revenue that funds our + ambitious R&D roadmap.

@@ -160,7 +164,9 @@ export default function Corp() { {/* Creator Network CTAs */}
-

Explore our creator community:

+

+ Explore our creator community: +

@@ -125,7 +138,9 @@ export default function Labs() { {/* Creator Network CTAs */}
-

Explore our creator community:

+

+ Explore our creator community: +

@@ -173,7 +188,8 @@ export default function Nexus() { Multi-Arm Marketplace

- Access talent and opportunities from all AeThex arms in one place + Access talent and opportunities from all AeThex arms in one + place

@@ -205,7 +221,8 @@ export default function Nexus() { Ready to Connect?

- Join the Nexus today and find your next opportunity or team member + Join the Nexus today and find your next opportunity or team + member

diff --git a/client/pages/corp/CorpContactUs.tsx b/client/pages/corp/CorpContactUs.tsx index 6a90bc13..66ff1ac5 100644 --- a/client/pages/corp/CorpContactUs.tsx +++ b/client/pages/corp/CorpContactUs.tsx @@ -53,7 +53,7 @@ export default function CorpContactUs() { const handleInputChange = ( e: React.ChangeEvent< HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement - > + >, ) => { const { name, value } = e.target; setFormData((prev) => ({ ...prev, [name]: value })); @@ -91,7 +91,9 @@ export default function CorpContactUs() { Get In Touch

- Have questions about our services? Want to schedule a consultation? Contact our enterprise team and we'll get back to you quickly. + Have questions about our services? Want to schedule a + consultation? Contact our enterprise team and we'll get back to + you quickly.

@@ -272,9 +274,9 @@ export default function CorpContactUs() { Expected Response Time

- We typically respond to inquiries within 24 business hours. - For urgent matters, please call our direct line during - business hours (9AM-6PM EST, Monday-Friday). + We typically respond to inquiries within 24 business + hours. For urgent matters, please call our direct line + during business hours (9AM-6PM EST, Monday-Friday).

diff --git a/client/pages/corp/CorpScheduleConsultation.tsx b/client/pages/corp/CorpScheduleConsultation.tsx index c3a9aeaa..066cef48 100644 --- a/client/pages/corp/CorpScheduleConsultation.tsx +++ b/client/pages/corp/CorpScheduleConsultation.tsx @@ -15,7 +15,8 @@ export default function CorpScheduleConsultation() { id: "custom-dev", name: "Custom Software Development", duration: "60 min", - description: "Discuss your project requirements and our development approach", + description: + "Discuss your project requirements and our development approach", details: [ "Project scope assessment", "Technology stack recommendations", @@ -116,7 +117,9 @@ export default function CorpScheduleConsultation() { Schedule Your Consultation

- Get expert guidance from our enterprise solutions team. Choose a service, pick your time, and let's discuss how we can help transform your business. + Get expert guidance from our enterprise solutions team. Choose a + service, pick your time, and let's discuss how we can help + transform your business.

@@ -247,7 +250,9 @@ export default function CorpScheduleConsultation() { What to Expect

- Our consultants will assess your needs, provide expert recommendations, and create a customized solution proposal tailored to your business goals. + Our consultants will assess your needs, provide expert + recommendations, and create a customized solution proposal + tailored to your business goals.

- {Array.from({ length: totalPages }, (_, i) => i + 1).map( - (p) => ( - - ) - )} + {Array.from( + { length: totalPages }, + (_, i) => i + 1, + ).map((p) => ( + + ))}
diff --git a/client/pages/devlink/DevLinkProfiles.tsx b/client/pages/devlink/DevLinkProfiles.tsx index b5a0f2c0..6ef78665 100644 --- a/client/pages/devlink/DevLinkProfiles.tsx +++ b/client/pages/devlink/DevLinkProfiles.tsx @@ -84,7 +84,8 @@ export default function DevLinkProfiles() { Developer Directory

- Find and connect with talented Roblox developers, browse portfolios, and discover collaboration opportunities. + Find and connect with talented Roblox developers, browse + portfolios, and discover collaboration opportunities.

@@ -115,7 +116,10 @@ export default function DevLinkProfiles() {
- {dev.name.split(" ").map(n => n[0]).join("")} + {dev.name + .split(" ") + .map((n) => n[0]) + .join("")}
{dev.available && ( @@ -144,7 +148,9 @@ export default function DevLinkProfiles() {
- {dev.portfolio} + + {dev.portfolio} + {dev.rating} @@ -172,9 +178,7 @@ export default function DevLinkProfiles() {

Showcase your work and connect with other developers.

- diff --git a/client/pages/foundation/FoundationContribute.tsx b/client/pages/foundation/FoundationContribute.tsx index c5f725a7..a7696505 100644 --- a/client/pages/foundation/FoundationContribute.tsx +++ b/client/pages/foundation/FoundationContribute.tsx @@ -84,7 +84,8 @@ export default function FoundationContribute() { }, { name: "Developer CLI", - description: "Command-line tools for streamlined game development workflow", + description: + "Command-line tools for streamlined game development workflow", stars: "1.2K", language: "Go", issues: "15 open", @@ -92,8 +93,7 @@ export default function FoundationContribute() { }, { name: "Multiplayer Framework", - description: - "Drop-in networking layer for real-time multiplayer games", + description: "Drop-in networking layer for real-time multiplayer games", stars: "980", language: "TypeScript", issues: "10 open", @@ -155,7 +155,9 @@ export default function FoundationContribute() { Ways to Contribute

- Join our community and help us build amazing open-source projects. There are many ways to contribute, regardless of your skill level. + Join our community and help us build amazing open-source + projects. There are many ways to contribute, regardless of your + skill level.

diff --git a/client/pages/foundation/FoundationGetInvolved.tsx b/client/pages/foundation/FoundationGetInvolved.tsx index 332811f1..9111a874 100644 --- a/client/pages/foundation/FoundationGetInvolved.tsx +++ b/client/pages/foundation/FoundationGetInvolved.tsx @@ -173,7 +173,8 @@ export default function FoundationGetInvolved() { Get Involved

- Join our thriving community of developers. Whether you're just starting or a seasoned pro, there's a place for you here. + Join our thriving community of developers. Whether you're just + starting or a seasoned pro, there's a place for you here.

diff --git a/client/pages/foundation/FoundationLearnMore.tsx b/client/pages/foundation/FoundationLearnMore.tsx index 7608f227..bdba317d 100644 --- a/client/pages/foundation/FoundationLearnMore.tsx +++ b/client/pages/foundation/FoundationLearnMore.tsx @@ -25,12 +25,7 @@ export default function FoundationLearnMore() { "Complete introduction to game development concepts and best practices", lessons: "50", duration: "20 hours", - topics: [ - "Game loops", - "Physics", - "Input handling", - "Asset management", - ], + topics: ["Game loops", "Physics", "Input handling", "Asset management"], free: true, }, { @@ -59,12 +54,7 @@ export default function FoundationLearnMore() { "Learn scalable architectural patterns used in professional game development", modules: "8", projects: "4", - topics: [ - "MVC pattern", - "ECS systems", - "Networking", - "State management", - ], + topics: ["MVC pattern", "ECS systems", "Networking", "State management"], free: true, }, { @@ -174,7 +164,9 @@ export default function FoundationLearnMore() { Free Learning Resources

- Learn game development from the ground up with our free, comprehensive educational resources. Everything you need to become an expert developer. + Learn game development from the ground up with our free, + comprehensive educational resources. Everything you need to + become an expert developer.

@@ -426,8 +418,8 @@ export default function FoundationLearnMore() { Start Your Learning Journey

- Choose a learning path and begin mastering game development today. - Everything is completely free and open to the community. + Choose a learning path and begin mastering game development + today. Everything is completely free and open to the community.

- {Array.from({ length: totalPages }, (_, i) => i + 1).map( - (p) => ( - - ) - )} + {Array.from( + { length: totalPages }, + (_, i) => i + 1, + ).map((p) => ( + + ))}