julien-c HF Staff victor HF Staff commited on
Commit
7abe934
·
unverified ·
1 Parent(s): 066b070

Link to provider (#1938)

Browse files

* Upgrade dep

* link to provider's page on the Hub

* add rounding

* Update ChatMessage.svelte

* Update provider type to InferenceProvider

Replaces the provider type from string to InferenceProvider in endpoint and message update types for improved type safety and consistency with @huggingface/inference.

* Remove model author avatar from chat message link

Eliminated the model author avatar image from the chat message model link and adjusted the link's padding for consistency. Also fixed the Hugging Face organization link to use curly braces for variable interpolation.

* Switch provider logos to dynamic avatars from Hugging Face

Replaces static SVG provider logos with dynamic avatars fetched from Hugging Face organization API. Removes all local SVG assets for provider logos and updates the settings page to use the new avatar URLs, improving maintainability and ensuring up-to-date branding.

* Remove unused variable and fix type in settings page

Deleted an unused 'modelAuthor' constant in ChatMessage.svelte. Updated type assertion for 'hubOrg' in the settings page to ensure correct key usage with PROVIDERS_HUB_ORGS.

---------

Co-authored-by: Victor Muštar <victor.mustar@gmail.com>

package-lock.json CHANGED
@@ -10,7 +10,7 @@
10
  "dependencies": {
11
  "@elysiajs/swagger": "^1.3.0",
12
  "@huggingface/hub": "^2.2.0",
13
- "@huggingface/inference": "^3.12.1",
14
  "@iconify-json/bi": "^1.1.21",
15
  "@resvg/resvg-js": "^2.6.2",
16
  "autoprefixer": "^10.4.14",
@@ -970,31 +970,31 @@
970
  }
971
  },
972
  "node_modules/@huggingface/inference": {
973
- "version": "3.15.0",
974
- "resolved": "https://registry.npmjs.org/@huggingface/inference/-/inference-3.15.0.tgz",
975
- "integrity": "sha512-C+Adt4fu4ztlq0Al9EOgEdK5Hl8ebV1eoDEWegJPdAJ97U8A1aqBbl1Sp4S4+wIy3nLApTrtcLuoizGZmLtDMA==",
976
  "license": "MIT",
977
  "dependencies": {
978
- "@huggingface/jinja": "^0.5.0",
979
- "@huggingface/tasks": "^0.19.9"
980
  },
981
  "engines": {
982
  "node": ">=18"
983
  }
984
  },
985
  "node_modules/@huggingface/jinja": {
986
- "version": "0.5.0",
987
- "resolved": "https://registry.npmjs.org/@huggingface/jinja/-/jinja-0.5.0.tgz",
988
- "integrity": "sha512-Ptc03/jGRiYRoi0bUYKZ14MkDslsBRT24oxmsvUlfYrvQMldrxCevhPnT+hfX8awKTT8/f/0ZBBWldoeAcMHdQ==",
989
  "license": "MIT",
990
  "engines": {
991
  "node": ">=18"
992
  }
993
  },
994
  "node_modules/@huggingface/tasks": {
995
- "version": "0.19.11",
996
- "resolved": "https://registry.npmjs.org/@huggingface/tasks/-/tasks-0.19.11.tgz",
997
- "integrity": "sha512-oBhSgVlg7Pp643MsH8BiI3OAXIMJNxdSiMtv4mApRZV8dmAz8oasKhg6CVKIplO7vAO7F6dkmMn4bYM64I2A9w==",
998
  "license": "MIT"
999
  },
1000
  "node_modules/@humanwhocodes/config-array": {
 
10
  "dependencies": {
11
  "@elysiajs/swagger": "^1.3.0",
12
  "@huggingface/hub": "^2.2.0",
13
+ "@huggingface/inference": "^4.11.3",
14
  "@iconify-json/bi": "^1.1.21",
15
  "@resvg/resvg-js": "^2.6.2",
16
  "autoprefixer": "^10.4.14",
 
970
  }
971
  },
972
  "node_modules/@huggingface/inference": {
973
+ "version": "4.11.3",
974
+ "resolved": "https://registry.npmjs.org/@huggingface/inference/-/inference-4.11.3.tgz",
975
+ "integrity": "sha512-Fqpj89DuB6i9j+cos9i0bfUKlpx5NFFsmvED0OAdE1gUSTHR86GpUZ0xkKy58IYXV1yFyHLFxQaOn0XDmD2m7Q==",
976
  "license": "MIT",
977
  "dependencies": {
978
+ "@huggingface/jinja": "^0.5.1",
979
+ "@huggingface/tasks": "^0.19.52"
980
  },
981
  "engines": {
982
  "node": ">=18"
983
  }
984
  },
985
  "node_modules/@huggingface/jinja": {
986
+ "version": "0.5.1",
987
+ "resolved": "https://registry.npmjs.org/@huggingface/jinja/-/jinja-0.5.1.tgz",
988
+ "integrity": "sha512-yUZLld4lrM9iFxHCwFQ7D1HW2MWMwSbeB7WzWqFYDWK+rEb+WldkLdAJxUPOmgICMHZLzZGVcVjFh3w/YGubng==",
989
  "license": "MIT",
990
  "engines": {
991
  "node": ">=18"
992
  }
993
  },
994
  "node_modules/@huggingface/tasks": {
995
+ "version": "0.19.52",
996
+ "resolved": "https://registry.npmjs.org/@huggingface/tasks/-/tasks-0.19.52.tgz",
997
+ "integrity": "sha512-ERporbPcWOeeN22PG3UoC3n/kgk50/Gn03A1NPwO2fqlzaP01ADug0DazPi8W3HandT6LHycv7tAjo+sCOBRtw==",
998
  "license": "MIT"
999
  },
1000
  "node_modules/@humanwhocodes/config-array": {
package.json CHANGED
@@ -68,7 +68,7 @@
68
  "dependencies": {
69
  "@elysiajs/swagger": "^1.3.0",
70
  "@huggingface/hub": "^2.2.0",
71
- "@huggingface/inference": "^3.12.1",
72
  "@iconify-json/bi": "^1.1.21",
73
  "@resvg/resvg-js": "^2.6.2",
74
  "autoprefixer": "^10.4.14",
 
68
  "dependencies": {
69
  "@elysiajs/swagger": "^1.3.0",
70
  "@huggingface/hub": "^2.2.0",
71
+ "@huggingface/inference": "^4.11.3",
72
  "@iconify-json/bi": "^1.1.21",
73
  "@resvg/resvg-js": "^2.6.2",
74
  "autoprefixer": "^10.4.14",
src/lib/components/chat/ChatMessage.svelte CHANGED
@@ -1,7 +1,6 @@
1
  <script lang="ts">
2
  import type { Message } from "$lib/types/Message";
3
  import { tick } from "svelte";
4
- import { base } from "$app/paths";
5
 
6
  import { usePublicConfig } from "$lib/utils/PublicConfig.svelte";
7
  const publicConfig = usePublicConfig();
@@ -17,6 +16,7 @@
17
  import OpenReasoningResults from "./OpenReasoningResults.svelte";
18
  import Alternatives from "./Alternatives.svelte";
19
  import MessageAvatar from "./MessageAvatar.svelte";
 
20
 
21
  interface Props {
22
  message: Message;
@@ -177,7 +177,7 @@
177
  {#if publicConfig.isHuggingChat}
178
  <a
179
  href="/chat/settings/{message.routerMetadata.model}"
180
- class="truncate rounded bg-gray-100 px-1 font-mono hover:text-gray-500 dark:bg-gray-800 dark:hover:text-gray-300 sm:py-px"
181
  >
182
  {message.routerMetadata.model.split("/").pop()}
183
  </a>
@@ -190,18 +190,21 @@
190
  {/if}
191
  {/if}
192
  {#if message.routerMetadata.provider}
 
193
  <span class="text-gray-500 max-sm:hidden">via</span>
194
- <span
195
- class="flex items-center gap-1 truncate rounded bg-gray-100 pl-1 pr-1.5 font-mono dark:bg-gray-800 max-sm:hidden sm:py-px"
 
 
196
  >
197
  <img
198
- src={`${base}/huggingchat/providers/${message.routerMetadata.provider}.svg`}
199
  alt="{message.routerMetadata.provider} logo"
200
- class="size-2.5 flex-none"
201
  onerror={(e) => ((e.currentTarget as HTMLImageElement).style.display = "none")}
202
  />
203
  {message.routerMetadata.provider}
204
- </span>
205
  {/if}
206
  </div>
207
  {/if}
 
1
  <script lang="ts">
2
  import type { Message } from "$lib/types/Message";
3
  import { tick } from "svelte";
 
4
 
5
  import { usePublicConfig } from "$lib/utils/PublicConfig.svelte";
6
  const publicConfig = usePublicConfig();
 
16
  import OpenReasoningResults from "./OpenReasoningResults.svelte";
17
  import Alternatives from "./Alternatives.svelte";
18
  import MessageAvatar from "./MessageAvatar.svelte";
19
+ import { PROVIDERS_HUB_ORGS } from "@huggingface/inference";
20
 
21
  interface Props {
22
  message: Message;
 
177
  {#if publicConfig.isHuggingChat}
178
  <a
179
  href="/chat/settings/{message.routerMetadata.model}"
180
+ class="flex items-center gap-1 truncate rounded bg-gray-100 px-1 font-mono hover:text-gray-500 dark:bg-gray-800 dark:hover:text-gray-300 sm:py-px"
181
  >
182
  {message.routerMetadata.model.split("/").pop()}
183
  </a>
 
190
  {/if}
191
  {/if}
192
  {#if message.routerMetadata.provider}
193
+ {@const hubOrg = PROVIDERS_HUB_ORGS[message.routerMetadata.provider]}
194
  <span class="text-gray-500 max-sm:hidden">via</span>
195
+ <a
196
+ target="_blank"
197
+ href="https://huggingface.co/{hubOrg}"
198
+ class="flex items-center gap-1 truncate rounded bg-gray-100 px-1 font-mono hover:text-gray-500 dark:bg-gray-800 dark:hover:text-gray-300 max-sm:hidden sm:py-px"
199
  >
200
  <img
201
+ src="https://huggingface.co/api/organizations/{hubOrg}/avatar"
202
  alt="{message.routerMetadata.provider} logo"
203
+ class="size-2.5 flex-none rounded-sm"
204
  onerror={(e) => ((e.currentTarget as HTMLImageElement).style.display = "none")}
205
  />
206
  {message.routerMetadata.provider}
207
+ </a>
208
  {/if}
209
  </div>
210
  {/if}
src/lib/server/endpoints/endpoints.ts CHANGED
@@ -1,6 +1,10 @@
1
  import type { Conversation } from "$lib/types/Conversation";
2
  import type { Message } from "$lib/types/Message";
3
- import type { TextGenerationStreamOutput, TextGenerationStreamToken } from "@huggingface/inference";
 
 
 
 
4
  import { z } from "zod";
5
  import { endpointOAIParametersSchema, endpointOai } from "./openai/endpointOai";
6
  import type { Model } from "$lib/types/Model";
@@ -21,7 +25,7 @@ export interface EndpointParameters {
21
 
22
  export type TextGenerationStreamOutputSimplified = TextGenerationStreamOutput & {
23
  token: TextGenerationStreamToken;
24
- routerMetadata?: { route?: string; model?: string; provider?: string };
25
  };
26
  // type signature for the endpoint
27
  export type Endpoint = (
 
1
  import type { Conversation } from "$lib/types/Conversation";
2
  import type { Message } from "$lib/types/Message";
3
+ import type {
4
+ TextGenerationStreamOutput,
5
+ TextGenerationStreamToken,
6
+ InferenceProvider,
7
+ } from "@huggingface/inference";
8
  import { z } from "zod";
9
  import { endpointOAIParametersSchema, endpointOai } from "./openai/endpointOai";
10
  import type { Model } from "$lib/types/Model";
 
25
 
26
  export type TextGenerationStreamOutputSimplified = TextGenerationStreamOutput & {
27
  token: TextGenerationStreamToken;
28
+ routerMetadata?: { route?: string; model?: string; provider?: InferenceProvider };
29
  };
30
  // type signature for the endpoint
31
  export type Endpoint = (
src/lib/types/Message.ts CHANGED
@@ -1,3 +1,4 @@
 
1
  import type { MessageUpdate } from "./MessageUpdate";
2
  import type { Timestamps } from "./Timestamps";
3
  import type { v4 } from "uuid";
@@ -20,7 +21,7 @@ export type Message = Partial<Timestamps> & {
20
  routerMetadata?: {
21
  route: string;
22
  model: string;
23
- provider?: string;
24
  };
25
 
26
  // needed for conversation trees
 
1
+ import type { InferenceProvider } from "@huggingface/inference";
2
  import type { MessageUpdate } from "./MessageUpdate";
3
  import type { Timestamps } from "./Timestamps";
4
  import type { v4 } from "uuid";
 
21
  routerMetadata?: {
22
  route: string;
23
  model: string;
24
+ provider?: InferenceProvider;
25
  };
26
 
27
  // needed for conversation trees
src/lib/types/MessageUpdate.ts CHANGED
@@ -1,3 +1,5 @@
 
 
1
  export type MessageUpdate =
2
  | MessageStatusUpdate
3
  | MessageTitleUpdate
@@ -74,5 +76,5 @@ export interface MessageRouterMetadataUpdate {
74
  type: MessageUpdateType.RouterMetadata;
75
  route: string;
76
  model: string;
77
- provider?: string;
78
  }
 
1
+ import type { InferenceProvider } from "@huggingface/inference";
2
+
3
  export type MessageUpdate =
4
  | MessageStatusUpdate
5
  | MessageTitleUpdate
 
76
  type: MessageUpdateType.RouterMetadata;
77
  route: string;
78
  model: string;
79
+ provider?: InferenceProvider;
80
  }
src/routes/settings/(nav)/[...model]/+page.svelte CHANGED
@@ -14,6 +14,7 @@
14
  import { goto } from "$app/navigation";
15
  import { usePublicConfig } from "$lib/utils/PublicConfig.svelte";
16
  import Switch from "$lib/components/Switch.svelte";
 
17
 
18
  const publicConfig = usePublicConfig();
19
  const settings = useSettingsStore();
@@ -231,15 +232,17 @@
231
  </div>
232
  <ul class="mb-0.5 flex flex-wrap gap-2">
233
  {#each providerList as prov, i (prov.provider || i)}
 
234
  <li>
235
  <span
236
  class="flex items-center gap-1 rounded-md bg-gray-100 py-0.5 pl-1.5 pr-2 text-xs text-gray-700 dark:bg-gray-700/60 dark:text-gray-200"
237
  >
238
- {#if prov.provider}
239
  <img
240
- class="h-[14px] w-auto"
241
- src={`${base}/huggingchat/providers/${prov.provider}.svg`}
242
  alt="{prov.provider} logo"
 
 
243
  />
244
  {/if}
245
  {prov.provider}
 
14
  import { goto } from "$app/navigation";
15
  import { usePublicConfig } from "$lib/utils/PublicConfig.svelte";
16
  import Switch from "$lib/components/Switch.svelte";
17
+ import { PROVIDERS_HUB_ORGS } from "@huggingface/inference";
18
 
19
  const publicConfig = usePublicConfig();
20
  const settings = useSettingsStore();
 
232
  </div>
233
  <ul class="mb-0.5 flex flex-wrap gap-2">
234
  {#each providerList as prov, i (prov.provider || i)}
235
+ {@const hubOrg = PROVIDERS_HUB_ORGS[prov.provider as keyof typeof PROVIDERS_HUB_ORGS]}
236
  <li>
237
  <span
238
  class="flex items-center gap-1 rounded-md bg-gray-100 py-0.5 pl-1.5 pr-2 text-xs text-gray-700 dark:bg-gray-700/60 dark:text-gray-200"
239
  >
240
+ {#if hubOrg}
241
  <img
242
+ src="https://huggingface.co/api/organizations/{hubOrg}/avatar"
 
243
  alt="{prov.provider} logo"
244
+ class="size-2.5 flex-none rounded-sm"
245
+ onerror={(e) => ((e.currentTarget as HTMLImageElement).style.display = "none")}
246
  />
247
  {/if}
248
  {prov.provider}
static/huggingchat/providers/cerebras.svg DELETED

Git LFS Details

  • SHA256: 61db84752238ef350380000de9446428213e552d7c5f8b678331fcac5610eeb4
  • Pointer size: 129 Bytes
  • Size of remote file: 1.25 kB
static/huggingchat/providers/cohere.svg DELETED

Git LFS Details

  • SHA256: 5af5a88164451bb58ccc35110a3acf6cbf2d31f0aeaf351daaab752dfa14ab7e
  • Pointer size: 128 Bytes
  • Size of remote file: 870 Bytes
static/huggingchat/providers/featherless-ai.svg DELETED

Git LFS Details

  • SHA256: b17df915a2476b5d18e3bff8ce9a83898591657715c7f91e3c4874681f264dac
  • Pointer size: 129 Bytes
  • Size of remote file: 1.37 kB
static/huggingchat/providers/fireworks-ai.svg DELETED

Git LFS Details

  • SHA256: 65e81e5c45915b624a1eb2e07720de620fe42d53f8d447a86c39fc6a015eb29f
  • Pointer size: 129 Bytes
  • Size of remote file: 1.03 kB
static/huggingchat/providers/groq.svg DELETED

Git LFS Details

  • SHA256: 18f5b08e53b9c32763b6a3dc01c5b4ee12fa325ca6be92903a11c0cc32a17ba2
  • Pointer size: 128 Bytes
  • Size of remote file: 803 Bytes
static/huggingchat/providers/hf-inference.svg DELETED

Git LFS Details

  • SHA256: b82dedbac87d7ec3177673035245bd4ccc00ac331b9ac3ed04bbbb3c90b57ea4
  • Pointer size: 128 Bytes
  • Size of remote file: 502 Bytes
static/huggingchat/providers/hyperbolic.svg DELETED

Git LFS Details

  • SHA256: 56601fd942159f2564d2b75ef208f9a8fef8c88a89d639abd13d107a01e353aa
  • Pointer size: 129 Bytes
  • Size of remote file: 2.65 kB
static/huggingchat/providers/nebius.svg DELETED

Git LFS Details

  • SHA256: dc115615cf76d8920b5c430694e6cded27db0a0c7333f1cc4bfad4cd3d15b43a
  • Pointer size: 128 Bytes
  • Size of remote file: 629 Bytes
static/huggingchat/providers/novita.svg DELETED

Git LFS Details

  • SHA256: 7a4cd71df1adf5d5acec405525cfd75f029cf6d2ac56c7a58d871a4423ec2250
  • Pointer size: 128 Bytes
  • Size of remote file: 645 Bytes
static/huggingchat/providers/nscale.svg DELETED

Git LFS Details

  • SHA256: 787045bad4fc01fcc8ec2be3aa7d7b071fd1db182792880ca983b83115f9122e
  • Pointer size: 129 Bytes
  • Size of remote file: 1.14 kB
static/huggingchat/providers/publicai.svg DELETED

Git LFS Details

  • SHA256: 85600455d939bc2edc9403b6f13ab0f34ff902ff467f68d5c20deda8b9bdb53c
  • Pointer size: 128 Bytes
  • Size of remote file: 912 Bytes
static/huggingchat/providers/sambanova.svg DELETED

Git LFS Details

  • SHA256: 69a2eb84a103da8bf76467b4de98467c30188380add95d355107ee86e8e29323
  • Pointer size: 129 Bytes
  • Size of remote file: 2.26 kB
static/huggingchat/providers/scaleway.svg DELETED

Git LFS Details

  • SHA256: bda4cde0465c65906227744c6175085b66b12b4d56a23a5dd2e82f6b9fa108d3
  • Pointer size: 129 Bytes
  • Size of remote file: 2.47 kB
static/huggingchat/providers/together.svg DELETED

Git LFS Details

  • SHA256: 56b42dea680cab3620af8d5158c5e6387e23f58f664ea1d7774dc6729b8bc747
  • Pointer size: 129 Bytes
  • Size of remote file: 1.45 kB
static/huggingchat/providers/zai-org.svg DELETED

Git LFS Details

  • SHA256: 73b432ade577223bc82692e95b8d676e7dadd41b914a938e89179cfe608a13dc
  • Pointer size: 128 Bytes
  • Size of remote file: 980 Bytes