mirror of
https://github.com/direct-img/direct-img.link.git
synced 2026-10-08 22:45:19 +00:00
Feat: Add logo, favicon and bad.webp; move images to /assets
- New logo (svg + jpg) and multi-size favicon.ico - /favicon.ico still served at root so direct image views get the icon - Generated missing bad.webp placeholder - Moved limit.webp into /assets and routed error images via helper Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Binary file not shown.
|
After Width: | Height: | Size: 9.4 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 5.2 KiB |
|
Before Width: | Height: | Size: 24 KiB After Width: | Height: | Size: 24 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 23 KiB |
@@ -0,0 +1,12 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 64 64" fill="none" stroke-linecap="round" stroke-linejoin="round">
|
||||||
|
<style>
|
||||||
|
.f{stroke:#1a1a1a}.a{stroke:#0070f3}
|
||||||
|
@media (prefers-color-scheme:dark){.f{stroke:#f5f5f5}}
|
||||||
|
</style>
|
||||||
|
<!-- frame -->
|
||||||
|
<rect class="f" x="7" y="7" width="50" height="50" rx="13" stroke-width="4.5"/>
|
||||||
|
<!-- the URL "/" rising into a peak -->
|
||||||
|
<path class="f" d="M19 57 29 32l10 14 5-7 13 5" stroke-width="4.5"/>
|
||||||
|
<!-- a link as the sun -->
|
||||||
|
<path class="a" d="M-2-4h-3a4 4 0 0 0 0 8h3M2-4h3a4 4 0 0 1 0 8H2M-4 0h8" stroke-width="2.5" transform="translate(42 22) rotate(-45)"/>
|
||||||
|
</svg>
|
||||||
|
After Width: | Height: | Size: 627 B |
@@ -7,17 +7,17 @@ export async function onRequest(context) {
|
|||||||
const { request, env, params } = context;
|
const { request, env, params } = context;
|
||||||
const url = new URL(request.url);
|
const url = new URL(request.url);
|
||||||
const path = params.path?.join("/") || "";
|
const path = params.path?.join("/") || "";
|
||||||
|
const asset = f => env.ASSETS.fetch(new Request(new URL(`/assets/${f}`, url.origin)));
|
||||||
|
|
||||||
if (!path || path === "index.html" || path === "favicon.ico" || path === "robots.txt" || path === "limit.webp" || path === "bad.webp") {
|
if (!path || path === "index.html" || path === "robots.txt" || path.startsWith("assets/")) {
|
||||||
return env.ASSETS.fetch(request);
|
return env.ASSETS.fetch(request);
|
||||||
}
|
}
|
||||||
|
if (path === "favicon.ico") return asset("favicon.ico");
|
||||||
|
|
||||||
if (path === "_setup") return setupSurreal(env);
|
if (path === "_setup") return setupSurreal(env);
|
||||||
|
|
||||||
const rawQueryPart = url.pathname.slice(1).replace(/\/+$/, "");
|
const rawQueryPart = url.pathname.slice(1).replace(/\/+$/, "");
|
||||||
if (rawQueryPart.includes(".") || rawQueryPart.includes("/")) {
|
if (rawQueryPart.includes(".") || rawQueryPart.includes("/")) return asset("bad.webp");
|
||||||
return env.ASSETS.fetch(new Request(new URL("/bad.webp", url.origin)));
|
|
||||||
}
|
|
||||||
|
|
||||||
const query = normalizeQuery(path);
|
const query = normalizeQuery(path);
|
||||||
if (!query) return jsonResponse(400, { error: "Empty query" });
|
if (!query) return jsonResponse(400, { error: "Empty query" });
|
||||||
@@ -28,7 +28,7 @@ export async function onRequest(context) {
|
|||||||
|
|
||||||
const cached = await env.DIRECT_IMG_CACHE.get(cacheKey, "json");
|
const cached = await env.DIRECT_IMG_CACHE.get(cacheKey, "json");
|
||||||
if (cached) {
|
if (cached) {
|
||||||
if (cached.err) return env.ASSETS.fetch(new Request(new URL("/bad.webp", url.origin)));
|
if (cached.err) return asset("bad.webp");
|
||||||
const obj = await env.R2_IMAGES.get(r2Key);
|
const obj = await env.R2_IMAGES.get(r2Key);
|
||||||
if (obj) {
|
if (obj) {
|
||||||
const nowSec = Math.floor(Date.now() / 1000);
|
const nowSec = Math.floor(Date.now() / 1000);
|
||||||
@@ -120,7 +120,7 @@ export async function onRequest(context) {
|
|||||||
|
|
||||||
if (count > 20) {
|
if (count > 20) {
|
||||||
context.waitUntil(notify(env, { title: "Rate Limit Hit", message: `IP ${ip} hit limit for: ${query}`, tags: "warning,no_entry", priority: 2 }));
|
context.waitUntil(notify(env, { title: "Rate Limit Hit", message: `IP ${ip} hit limit for: ${query}`, tags: "warning,no_entry", priority: 2 }));
|
||||||
return env.ASSETS.fetch(new Request(new URL("/limit.webp", url.origin)));
|
return asset("limit.webp");
|
||||||
}
|
}
|
||||||
|
|
||||||
context.waitUntil(notify(env, { title: "New Search", message: `Query: ${query} (Search #${count} for ${ip})\n${url.origin}/${path}`, tags: "mag", priority: 2 }));
|
context.waitUntil(notify(env, { title: "New Search", message: `Query: ${query} (Search #${count} for ${ip})\n${url.origin}/${path}`, tags: "mag", priority: 2 }));
|
||||||
@@ -128,7 +128,7 @@ export async function onRequest(context) {
|
|||||||
const fail = async (t, m, tag, p) => {
|
const fail = async (t, m, tag, p) => {
|
||||||
context.waitUntil(notify(env, { title: t, message: m, tags: tag, priority: p }));
|
context.waitUntil(notify(env, { title: t, message: m, tags: tag, priority: p }));
|
||||||
await env.DIRECT_IMG_CACHE.put(cacheKey, JSON.stringify({ t: Math.floor(Date.now() / 1000), err: true }), { expirationTtl: 86400 });
|
await env.DIRECT_IMG_CACHE.put(cacheKey, JSON.stringify({ t: Math.floor(Date.now() / 1000), err: true }), { expirationTtl: 86400 });
|
||||||
return env.ASSETS.fetch(new Request(new URL("/bad.webp", url.origin)));
|
return asset("bad.webp");
|
||||||
};
|
};
|
||||||
|
|
||||||
let imageUrls = await braveImageSearch(query, env.BRAVE_API_KEY);
|
let imageUrls = await braveImageSearch(query, env.BRAVE_API_KEY);
|
||||||
|
|||||||
@@ -4,6 +4,7 @@
|
|||||||
<meta charset="UTF-8"><meta name="viewport" content="width=device-width,initial-scale=1.0">
|
<meta charset="UTF-8"><meta name="viewport" content="width=device-width,initial-scale=1.0">
|
||||||
<title>direct-img.link | Live images in markdown</title>
|
<title>direct-img.link | Live images in markdown</title>
|
||||||
<meta name="description" content="Embed live images in markdown powered by search. No APIs, no tokens, just search.">
|
<meta name="description" content="Embed live images in markdown powered by search. No APIs, no tokens, just search.">
|
||||||
|
<link rel="icon" href="/assets/favicon.ico" sizes="16x16 32x32 48x48"><link rel="icon" href="/assets/logo.svg" type="image/svg+xml">
|
||||||
<script defer src="https://c.planetrenox.com/tracker.js"></script>
|
<script defer src="https://c.planetrenox.com/tracker.js"></script>
|
||||||
<style>
|
<style>
|
||||||
:root{--bg:#fff;--text:#1a1a1a;--text-muted:#666;--accent:#0070f3;--warning:#eb5757;--code-bg:#f5f5f5;--border:#eaeaea;--radius:8px;}
|
:root{--bg:#fff;--text:#1a1a1a;--text-muted:#666;--accent:#0070f3;--warning:#eb5757;--code-bg:#f5f5f5;--border:#eaeaea;--radius:8px;}
|
||||||
|
|||||||
Reference in New Issue
Block a user