tangled
alpha
login
or
join now
tynanpurdy.com
/
atprofile
3
fork
atom
Fork of atp.tools as a universal profile for people on the ATmosphere
3
fork
atom
overview
issues
pulls
pipelines
minimum prototype of simplified handle page
Tynan Purdy
8 months ago
c97c456f
2e0d3c96
+52
-27
2 changed files
expand all
collapse all
unified
split
src
components
repoIcons.tsx
routes
at:
$handle.index.tsx
+19
-6
src/components/repoIcons.tsx
···
68
68
return matchingKey ? iconMappings[matchingKey] : null;
69
69
}
70
70
71
71
+
function reverseDomain(collection: string) {
72
72
+
// Split by dot, reverse, join with dot
73
73
+
return collection.split(".").reverse().join(".");
74
74
+
}
75
75
+
71
76
function RepoIcons({
72
77
collections,
73
78
did,
···
79
84
}) {
80
85
let uniqueTypes = Array.from(
81
86
collections
82
82
-
.map((collection) => ({
83
83
-
id: collection,
84
84
-
Icon: getIconForCollection(collection)?.icon ?? <ShieldQuestionIcon />,
85
85
-
displayName: getIconForCollection(collection)?.label ?? "Unknown",
86
86
-
linkTemplate: getIconForCollection(collection)?.linkTemplate,
87
87
-
}))
87
87
+
.map((collection) => {
88
88
+
const iconObj = getIconForCollection(collection);
89
89
+
return {
90
90
+
id: collection,
91
91
+
Icon: iconObj?.icon ?? <ShieldQuestionIcon />,
92
92
+
displayName: iconObj?.label ?? "Unknown",
93
93
+
// If linkTemplate exists, use it; else generate URL from reversed domain
94
94
+
linkTemplate:
95
95
+
iconObj?.linkTemplate ??
96
96
+
`https://${reverseDomain(collection)}/{did}`,
97
97
+
};
98
98
+
})
88
99
.reduce((acc, current) => {
89
100
if (
90
101
!Array.from(acc.values()).some(
···
107
118
<a
108
119
href={linkTemplate?.replace("{handle}", handle).replace("{did}", did)}
109
120
key={id}
121
121
+
target="_blank"
122
122
+
rel="noopener noreferrer"
110
123
>
111
124
<div className="w-8 h-8 p-1 mr-2 rounded-full dark:bg-neutral-800 border border-neutral-500/50 text-white">
112
125
{typeof Icon === "string" ? (
+33
-21
src/routes/at:/$handle.index.tsx
···
252
252
<div className="pt-2">
253
253
<h2 className="text-xl font-bold mb-1">Collections</h2>
254
254
<ul className="list-inside space-y-1">
255
255
-
{data.collections.map((c, i) => (
256
256
-
<Fragment key={c}>
257
257
-
{c.split(".").slice(0, 2).join(".") !=
258
258
-
(i > 0 &&
259
259
-
data.collections[i - 1]
260
260
-
.split(".")
261
261
-
.slice(0, 2)
262
262
-
.join(".")) && (
263
263
-
<div className="w-min pt-2">
264
264
-
{c.split(".").slice(0, 2).join(".")}{" "}
265
265
-
</div>
266
266
-
)}
267
267
-
<li>
255
255
+
{Array.from(
256
256
+
data.collections
257
257
+
.reduce((map, c) => {
258
258
+
const prefix = c.split(".").slice(0, 2).join(".");
259
259
+
if (!map.has(prefix)) {
260
260
+
map.set(prefix, prefix);
261
261
+
}
262
262
+
return map;
263
263
+
}, new Map<string, string>())
264
264
+
.values(),
265
265
+
).map((prefix) => {
266
266
+
const domain = prefix.split(".").reverse().join(".");
267
267
+
const faviconUrl = `https://www.google.com/s2/favicons?sz=64&domain=${domain}`;
268
268
+
return (
269
269
+
<li key={prefix} className="flex items-center gap-2">
270
270
+
<img
271
271
+
src={faviconUrl}
272
272
+
alt={`${domain} favicon`}
273
273
+
className="w-4 h-4 rounded-sm flex-shrink-0"
274
274
+
onError={(e) => {
275
275
+
// Hide image if favicon not found
276
276
+
(e.target as HTMLImageElement).style.display = "none";
277
277
+
}}
278
278
+
/>
268
279
<Link
269
269
-
className="ml-4 text-blue-600 dark:text-blue-400 hover:no-underline border-b hover:border-border border-transparent w-min"
280
280
+
className="text-blue-600 dark:text-blue-400 hover:no-underline border-b hover:border-border border-transparent flex-1 break-all"
270
281
to="/at:/$handle/$collection"
271
282
params={{
272
272
-
handle: handle, // Use original handle for navigation consistency
273
273
-
collection: c,
283
283
+
handle: handle,
284
284
+
collection: prefix,
274
285
}}
286
286
+
title={`https://${domain}`}
275
287
>
276
276
-
{c}
288
288
+
{`https://${domain}`}
277
289
</Link>
278
290
</li>
279
279
-
</Fragment>
280
280
-
))}
291
291
+
);
292
292
+
})}
281
293
</ul>
282
294
</div>
283
295
)}
···
309
321
</Accordion>
310
322
)}
311
323
{/* Backlinks Section */}
312
312
-
{data?.did && (
324
324
+
{/* {data?.did && (
313
325
<div className="pt-4 pb-8 flex flex-col gap-2">
314
326
<AllBacklinksViewer aturi={data.did} />
315
327
</div>
316
316
-
)}
328
328
+
)} */}
317
329
</div>
318
330
</div>
319
331
);