Fix logit bias for DeepSeek on OpenRouter
| @@ -37,6 +37,8 @@ import { | ||
| 37 | 37 | getTiktokenTokenizer, |
| 38 | 38 | sentencepieceTokenizers, |
| 39 | 39 | TEXT_COMPLETION_MODELS, |
| 40 | + webTokenizers, | |
| 41 | + getWebTokenizer, | |
| 40 | 42 | } from '../tokenizers.js'; |
| 41 | 43 | |
| 42 | 44 | const API_OPENAI = 'https://api.openai.com/v1'; |
| @@ -863,6 +865,14 @@ router.post('/bias', jsonParser, async function (request, response) { | ||
| 863 | 865 | return response.send({}); |
| 864 | 866 | } |
| 865 | 867 | encodeFunction = (text) => new Uint32Array(instance.encodeIds(text)); |
| 868 | + } else if (webTokenizers.includes(model)) { | |
| 869 | + const tokenizer = getWebTokenizer(model); | |
| 870 | + const instance = await tokenizer?.get(); | |
| 871 | + if (!instance) { | |
| 872 | + console.warn('Tokenizer not initialized:', model); | |
| 873 | + return response.send({}); | |
| 874 | + } | |
| 875 | + encodeFunction = (text) => new Uint32Array(instance.encode(text)); | |
| 866 | 876 | } else { |
| 867 | 877 | const tokenizer = getTiktokenTokenizer(model); |
| 868 | 878 | encodeFunction = (tokenizer.encode.bind(tokenizer)); |
| @@ -238,6 +238,15 @@ export const sentencepieceTokenizers = [ | ||
| 238 | 238 | 'jamba', |
| 239 | 239 | ]; |
| 240 | 240 | |
| 241 | +export const webTokenizers = [ | |
| 242 | + 'claude', | |
| 243 | + 'llama3', | |
| 244 | + 'command-r', | |
| 245 | + 'qwen2', | |
| 246 | + 'nemo', | |
| 247 | + 'deepseek', | |
| 248 | +]; | |
| 249 | + | |
| 241 | 250 | /** |
| 242 | 251 | * Gets the Sentencepiece tokenizer by the model name. |
| 243 | 252 | * @param {string} model Sentencepiece model name |
| @@ -276,6 +285,39 @@ export function getSentencepiceTokenizer(model) { | ||
| 276 | 285 | } |
| 277 | 286 | |
| 278 | 287 | /** |
| 288 | + * Gets the Web tokenizer by the model name. | |
| 289 | + * @param {string} model Web tokenizer model name | |
| 290 | + * @returns {WebTokenizer|null} Web tokenizer | |
| 291 | + */ | |
| 292 | +export function getWebTokenizer(model) { | |
| 293 | + if (model.includes('llama3')) { | |
| 294 | + return llama3_tokenizer; | |
| 295 | + } | |
| 296 | + | |
| 297 | + if (model.includes('claude')) { | |
| 298 | + return claude_tokenizer; | |
| 299 | + } | |
| 300 | + | |
| 301 | + if (model.includes('command-r')) { | |
| 302 | + return commandTokenizer; | |
| 303 | + } | |
| 304 | + | |
| 305 | + if (model.includes('qwen2')) { | |
| 306 | + return qwen2Tokenizer; | |
| 307 | + } | |
| 308 | + | |
| 309 | + if (model.includes('nemo')) { | |
| 310 | + return nemoTokenizer; | |
| 311 | + } | |
| 312 | + | |
| 313 | + if (model.includes('deepseek')) { | |
| 314 | + return deepseekTokenizer; | |
| 315 | + } | |
| 316 | + | |
| 317 | + return null; | |
| 318 | +} | |
| 319 | + | |
| 320 | +/** | |
| 279 | 321 | * Counts the token ids for the given text using the Sentencepiece tokenizer. |
| 280 | 322 | * @param {SentencePieceTokenizer} tokenizer Sentencepiece tokenizer |
| 281 | 323 | * @param {string} text Text to tokenize |