Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
f085a07
Implemented _index.tsx (home page) using temporary JSON data with fun…
tedthavisin Nov 1, 2025
b7395fe
Added pages for auth with no functionality as of now
pranavsna Nov 1, 2025
be9459e
Added CancerLINC logo
pranavsna Nov 1, 2025
0fed45f
Committed routes.ts as well
pranavsna Jan 14, 2026
befd50d
Added CancerLINC logo to top bar
tedthavisin Jan 15, 2026
f6f97cd
Merge pull request #2 from cssgunc/auth
SamanyuDixit Jan 30, 2026
fcfa8c6
Merge branch 'main' into ted
SamanyuDixit Jan 30, 2026
68079df
Merge pull request #3 from cssgunc/ted
SamanyuDixit Jan 30, 2026
9d19b33
firebase setup
aryavenkatesan Jan 31, 2026
5f4d3c1
fixed links to prevent page from refreshing unnecessarily
tcbarzyk Feb 4, 2026
8492844
Merge pull request #5 from cssgunc/firebase_setup
SamanyuDixit Feb 5, 2026
d2053e2
Commit without .env
tcbarzyk Feb 17, 2026
2cfb35b
Profile page rework -- Ted and Hamzah
hamzahyous Feb 17, 2026
82966ea
Merge branch 'main' into tb/frontend_auth
SamanyuDixit Feb 20, 2026
b6e5093
feat: add referrals section
tedthavisin Feb 24, 2026
3257c1f
Updated referrals.tsx styling, updated ssr to false, and fixed useRef…
tedthavisin Feb 24, 2026
866cb60
Text color fix
hamzahyous Feb 26, 2026
886b1db
Merge pull request #6 from cssgunc/tb/frontend_auth
SamanyuDixit Feb 26, 2026
2aa9c54
built frontend for messaging
tcbarzyk Feb 27, 2026
55b893a
built basic messaging system
tcbarzyk Feb 27, 2026
572a405
Implemented card and list components for referrals. Added delete, edi…
tedthavisin Feb 28, 2026
f35ba58
Updated referral form keep patientId immutable.
tedthavisin Feb 28, 2026
525738b
Added TODO comment and installed react-router-dom for future router p…
tedthavisin Feb 28, 2026
8a95b31
Fixed routes and added comments
tedthavisin Feb 28, 2026
5855a41
Merge branch 'main' into referrals-feature
tedthavisin Feb 28, 2026
1707dd4
referral fields update
hamzahyous Mar 9, 2026
2fda810
Merge branch 'main' into hamzah-ted-profile-page-updates
SamanyuDixit Mar 25, 2026
10ad320
Merge pull request #7 from cssgunc/hamzah-ted-profile-page-updates
SamanyuDixit Mar 25, 2026
cf8bb71
Changed to firebase.js to resolve merge conflict
SamanyuDixit Mar 26, 2026
1920270
Merge pull request #8 from cssgunc/referrals-feature
SamanyuDixit Mar 26, 2026
2cc4e07
added attachments
tcbarzyk Apr 2, 2026
c53de63
updated chat spec
tcbarzyk Apr 5, 2026
629115c
fixed UI issues
tcbarzyk Apr 13, 2026
f0ec36b
updated dashboard
tcbarzyk Apr 14, 2026
9b84c62
merge: main
aryavenkatesan Apr 20, 2026
020e53e
feat: integrated referrals into profile page
aryavenkatesan Apr 20, 2026
3a5a266
feat: everything
aryavenkatesan Apr 20, 2026
28e1134
feat: filters
aryavenkatesan Apr 20, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ RUN mkdir -p /etc/apt/keyrings \
&& apt-get update \
&& apt-get install nodejs -y \
&& npm install -g npm@11.5.2 \
&& npm install -g @openai/codex \
&& rm -rf /var/lib/apt/lists/*

# Use a non-root user per https://code.visualstudio.com/remote/advancedcontainers/add-nonroot-user
Expand Down
11 changes: 9 additions & 2 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"service": "frontend",
"remoteUser": "vscode",
"forwardPorts": [5173],
"postCreateCommand": "npm install",
"postCreateCommand": "npm install && sudo npm install -g @anthropic-ai/claude-code",
"customizations": {
"vscode": {
"extensions": [
Expand Down Expand Up @@ -37,6 +37,13 @@
"editor.defaultFormatter": "esbenp.prettier-vscode"
}
}
}
},
"mounts": [
"source=claude-code-config-${devcontainerId},target=/home/vscode/.claude,type=volume"
],
"containerEnv": {
"CLAUDE_CONFIG_DIR": "/home/vscode/.claude"
},
"containerUser": "vscode"
}
}
1 change: 1 addition & 0 deletions .devcontainer/docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,4 @@ services:
command: /bin/sh -c "while sleep 1000; do :; done"
environment:
- windir # Defined on Windows but not on other platforms
privileged: true
8 changes: 8 additions & 0 deletions .env.template
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
#FIREBASE SETUP
VITE_FIREBASE_API_KEY=""
VITE_FIREBASE_AUTH_DOMAIN=""
VITE_FIREBASE_PROJECT_ID=""
VITE_FIREBASE_STORAGE_BUCKET=""
VITE_FIREBASE_MESSAGING_SENDER_ID=""
VITE_FIREBASE_APP_ID=""
VITE_FIREBASE_MEASUREMENT_ID=""
6 changes: 6 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,9 @@
# React Router
/.react-router/
/build/

#environment files
.env

# Firebase service account key — never commit this
scripts/service-account.json
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,3 +53,7 @@ Inside the dev container, you can use the following commands:
| `npm run lint:fix` | Lints and automatically fixes issues. |
| `npm run format` | Formats the code using Prettier. |
| `npm run typecheck` | Runs the TypeScript compiler to check for type errors. |
## Feature Notes
- Image messaging rollout and Firebase setup details: [`docs/chat-image-messaging.md`](/workspace/docs/chat-image-messaging.md)
62 changes: 61 additions & 1 deletion app/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,69 @@

html,
body {
@apply bg-white dark:bg-gray-950;
@apply bg-white text-gray-900 dark:bg-gray-950 dark:text-gray-100;

@media (prefers-color-scheme: dark) {
color-scheme: dark;
}
}

.search-hint {
position: absolute;
left: 0;
right: 0;
white-space: nowrap;
transform-origin: center;
}

.search-hint-active {
animation: search-hint-settle 420ms cubic-bezier(0.22, 1, 0.36, 1);
}

.search-hint-leave {
animation: search-hint-leave 420ms cubic-bezier(0.4, 0, 0.2, 1) forwards;
}

.search-hint-enter {
animation: search-hint-enter 420ms cubic-bezier(0.22, 1, 0.36, 1) forwards;
}

@keyframes search-hint-settle {
from {
opacity: 0;
transform: translate3d(-10px, 0, 0);
}

to {
opacity: 1;
transform: translate3d(0, 0, 0);
}
}

@keyframes search-hint-leave {
from {
opacity: 1;
transform: translate3d(0, 0, 0) rotateX(0deg);
clip-path: inset(0 0 0 0);
}

to {
opacity: 0;
transform: translate3d(12px, -8px, 0) rotateX(75deg);
clip-path: inset(0 100% 0 0);
}
}

@keyframes search-hint-enter {
from {
opacity: 0;
transform: translate3d(-12px, 8px, 0) rotateX(-75deg);
clip-path: inset(0 0 0 100%);
}

to {
opacity: 1;
transform: translate3d(0, 0, 0) rotateX(0deg);
clip-path: inset(0 0 0 0);
}
}
120 changes: 120 additions & 0 deletions app/components/ReferralCard.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
import { MoreHorizontal, ExternalLink } from "lucide-react";
import type { ReferralWithProvider } from "~/types/referral";

interface ReferralCardProps {
referral: ReferralWithProvider;
onEdit: () => void;
onDelete: (id: string) => void;
}

export default function ReferralCard({
referral,
onEdit,
onDelete,
}: ReferralCardProps) {
const contactName =
`${referral.referralFirstName ?? ""} ${referral.referralLastName ?? ""}`.trim() ||
"Unknown";
const title = referral.referralTitle || "";
const phone = referral.referralPhone || "";
const email = referral.referralEmail || "";
const websiteUrl = referral.websiteUrl?.trim() || "";

const socialWorkerName = referral.socialWorker
? `${referral.socialWorker.firstName ?? ""} ${referral.socialWorker.lastName ?? ""}`.trim()
: "";

const statusColors: Record<string, string> = {
pending: "bg-yellow-100 text-yellow-800",
accepted: "bg-green-100 text-green-800",
completed: "bg-blue-100 text-blue-800",
rejected: "bg-red-100 text-red-800",
};
const statusStyle =
statusColors[referral.status] || "bg-gray-100 text-gray-800";

return (
<article className="relative rounded-lg border border-gray-200 bg-white p-4 shadow-sm transition-colors">
{/* Options Menu */}
<div className="absolute right-2 top-2 group z-10">
<button
type="button"
className="p-1 text-gray-900 hover:text-gray-500 transition"
aria-label="More options"
>
<MoreHorizontal className="h-5 w-5" />
</button>

<div className="absolute right-0 top-full hidden w-32 flex-col pt-1 group-hover:flex">
<div className="flex flex-col overflow-hidden rounded-md border border-gray-200 bg-white shadow-lg">
<button
onClick={onEdit}
className="px-4 py-2 text-left text-[14px] text-gray-700 hover:bg-gray-50 transition-colors"
>
Edit
</button>
<button
onClick={() => {
if (window.confirm("Delete this referral?")) {
onDelete(referral.id);
}
}}
className="px-4 py-2 text-left text-[14px] text-red-600 hover:bg-red-50 transition-colors border-t border-gray-100"
>
Delete
</button>
</div>
</div>
</div>

{/* Status Badge */}
<span
className={`absolute right-2 top-10 rounded-full px-2.5 py-0.5 text-[11px] font-semibold capitalize ${statusStyle}`}
>
{referral.status}
</span>

{/* Content */}
<div className="pr-8">
<h3 className="text-[15px] font-bold text-gray-900 leading-tight">
{contactName}
</h3>
{title ? (
<p className="text-[14px] font-bold text-gray-900 leading-tight">
{title}
</p>
) : null}

<div className="mt-2 text-[14px] text-gray-900 leading-snug">
{phone ? <p>{phone}</p> : null}
{email ? <p>{email}</p> : null}
</div>

{socialWorkerName ? (
<p className="mt-3 text-[14px] font-bold text-gray-900">
Referred By: {socialWorkerName}
</p>
) : null}

<div className="mt-2">
{websiteUrl ? (
<a
href={websiteUrl}
target="_blank"
rel="noreferrer"
className="inline-flex items-center gap-1.5 rounded bg-[#A3D146] px-4 py-1.5 text-[14px] font-medium text-black hover:bg-[#92BC3F] transition-colors"
>
Website
<ExternalLink className="h-3.5 w-3.5" />
</a>
) : (
<span className="inline-flex items-center gap-1.5 rounded bg-gray-100 px-4 py-1.5 text-[14px] font-medium text-gray-400 cursor-not-allowed">
Website
<ExternalLink className="h-3.5 w-3.5" />
</span>
)}
</div>
</div>
</article>
);
}
Loading