-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathcontent.ts
More file actions
205 lines (195 loc) · 6.51 KB
/
Copy pathcontent.ts
File metadata and controls
205 lines (195 loc) · 6.51 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
/**
* Flat content. Prose that carries citations lives in the section components,
* because a claim is a piece of typography and not a string.
*
* Source of truth for every fact here is the resume PDF in /public, plus the
* public repositories it points at. Numbers keep whatever hedge the resume
* gave them.
*/
export const CONTACT = {
name: "Vishal Khan",
email: "vishalkhan251@gmail.com",
github: "https://github.com/DataScienceVishal",
githubHandle: "DataScienceVishal",
linkedin: "https://www.linkedin.com/in/vishalkhandatascience/",
linkedinHandle: "in/vishalkhandatascience",
location: "London, United Kingdom",
twin: "https://ai-professional-twin.vercel.app/",
twinRepo: "https://github.com/DataScienceVishal/ai-professional-twin",
} as const;
/** Subject line is prefilled so the mail client opens ready to send. */
export const CALL_MAILTO =
"mailto:vishalkhan251@gmail.com" +
"?subject=" +
encodeURIComponent("Call about an AI/ML role") +
"&body=" +
encodeURIComponent(
"Hi Vishal,\n\nI would like to set up a call. Here is the role and a couple of times that work:\n\n",
);
/**
* The hero's evidence artifact. See DESIGN.md section 10.
*
* To use a screen capture instead of the still: drop the file in public/ and set
* `video` to its path. The still becomes the poster frame automatically, so the
* hero still paints immediately and nothing shifts.
*/
export const HERO_MODEL = {
/**
* The hero figure. From a 29 MB Sketchfab export down to 0.93 MB: welded,
* simplified to 28% of its triangles, then Draco geometry and WebP textures.
*
* The simplify ratio is the interesting number. It came from measuring, not
* from taste. At 519k triangles this model cost 1,164 ms of blocked main
* thread on a cold profile, and roughly half of that was its geometry rather
* than three.js starting up. At 241k it costs 52 ms. Going further, to 108k,
* shredded the wires into flat ribbons and punched holes in the face, so this
* is the floor: the last ratio where the wires still read as wires.
*
* `grade` retints it onto the page palette. The model arrives lavender and
* skin toned, which are two hues this page does not have. At full strength
* the grade drops each material's colour map, which is where a glTF export
* keeps its hue, and puts mapped surfaces on the mid-tone metal; unmapped
* ones ramp by luminance. Normal, roughness, metalness and AO maps stay, so
* the surface detail survives. See gradeToPalette in ModelStage.
*
* `scale` and `lift` push past the measured fit on purpose. The bounding box
* includes the whole spray of wires, so fitting it makes the head tiny; this
* frames the head and lets the wires leave the frame.
*/
model: "/models/robot.glb",
grade: 1,
spin: {
turns: 0.32,
tilt: 0.12,
baseY: -0.4,
baseX: 0.04,
scale: 1.62,
lift: 0.14,
},
} as const;
export const NAV_LINKS = [
{ href: "#twin", label: "Work" },
{ href: "#audits", label: "Audits" },
{ href: "#trajectory", label: "Trajectory" },
{ href: "#research", label: "Research" },
{ href: "#stack", label: "Stack" },
{ href: "#contact", label: "Contact" },
] as const;
/** Shown in Contact. There is no separate availability band on the page. */
/**
* Shown in Contact. There is no separate availability band on the page.
*
* Written permission-first, and bounded by date. The previous version led with
* "Student visa", which a UK screener reads as "needs sponsorship" before they
* reach the clause that says otherwise, and paired it with a bare "Part time"
* that reads as a preference rather than as a visa condition. The one fact a
* UK employer most needs, that no sponsor licence is required at any point,
* was not on the page at all: the only occurrence of the word "sponsorship"
* was a question to go and ask a chatbot.
*/
export const STATUS = [
{
term: "Sponsorship",
value:
"Not required, now or later. The Student visa and the Graduate Route both carry their own permission to work, so there is no sponsor licence and no Certificate of Sponsorship at any stage.",
},
{
term: "Now to January 2027",
value:
"AI and ML internships, alongside the MSc. Twenty hours a week in term time and full time through university vacations. No notice period, so the start date is whenever suits.",
},
{
term: "From early 2027",
value:
"Full time, on the Graduate Route. Two years of unrestricted work, following the MSc finishing in January.",
},
] as const;
export interface StackGroup {
heading: string;
qualifier: string;
items: string[];
}
/**
* Grouped by depth of use, not alphabetically. The bottom group exists so the
* top group means something.
*/
export const STACK: StackGroup[] = [
{
heading: "Shipped and maintained",
qualifier: "In production, or in a repository with tests around it.",
items: [
"Python",
"SQL",
"FastAPI",
"React 19",
"TypeScript",
"Databricks",
"ChromaDB",
"RAG retrieval",
"Azure OpenAI",
"pandas",
"NumPy",
"pytest",
"Git and GitHub",
"Vercel",
"Railway",
],
},
{
heading: "Used on project work",
qualifier:
"Coursework, dissertations, reporting that other people relied on.",
items: [
"PyTorch",
"TensorFlow",
"Keras",
"scikit-learn",
"LangChain",
"MCP",
"Azure",
"AWS",
"SQL Server",
"MySQL",
"MongoDB",
"statsmodels",
"Matplotlib",
"Seaborn",
"Plotly",
"Power BI",
"Streamlit",
"Excel with VBA",
],
},
{
heading: "Read the docs, would need a week",
qualifier: "Honest about it rather than padding the list above.",
items: ["R", "Neo4j", "Tableau"],
},
];
/**
* Real questions the twin handles. The first two come from its recruiter mode,
* the last two from interview mode.
*/
export const TWIN_QUESTIONS = [
"Summarise Vishal as a candidate in 60 seconds",
"Will he need visa sponsorship?",
"How do you handle prompt injection?",
"What chunking strategy did you use and why?",
] as const;
export interface OtherProject {
title: string;
meta: string;
href: string;
}
export const OTHER_PROJECTS: OtherProject[] = [
{
title: "CIFAR-10 image classification",
meta: "TensorFlow, Keras",
href: "https://github.com/DataScienceVishal/CIFAR-10-CNN",
},
{
title: "Telecom churn prediction",
meta: "Python, SQL, scikit-learn",
href: "https://github.com/DataScienceVishal/Telecom_Churn",
},
];