WIP: app.locals refactoring

WIP: appConfig

fix: update memory configuration retrieval to use getAppConfig based on user role

fix: update comment for AppConfig interface to clarify purpose
This commit is contained in:
Danny Avila 2025-08-05 18:09:25 -04:00
parent 5a14ee9c6a
commit b992fed16c
No known key found for this signature in database
GPG key ID: BF31EEB2C5CA0956
66 changed files with 706 additions and 366 deletions

View file

@ -11,6 +11,7 @@ const {
Constants,
} = require('librechat-data-provider');
const { getMessages, saveMessage, updateMessage, saveConvo, getConvo } = require('~/models');
const { getAppConfig } = require('~/server/services/Config');
const { checkBalance } = require('~/models/balanceMethods');
const { truncateToolCallOutputs } = require('./prompts');
const { getFiles } = require('~/models/File');
@ -567,6 +568,7 @@ class BaseClient {
}
async sendMessage(message, opts = {}) {
const appConfig = await getAppConfig({ role: this.options.req?.user?.role });
/** @type {Promise<TMessage>} */
let userMessagePromise;
const { user, head, isEdited, conversationId, responseMessageId, saveOptions, userMessage } =
@ -653,7 +655,7 @@ class BaseClient {
}
}
const balance = this.options.req?.app?.locals?.balance;
const balance = appConfig?.balance;
if (
balance?.enabled &&
supportsBalanceCheck[this.options.endpointType ?? this.options.endpoint]

View file

@ -34,6 +34,7 @@ const {
const { extractBaseURL, getModelMaxTokens, getModelMaxOutputTokens } = require('~/utils');
const { encodeAndFormat } = require('~/server/services/Files/images/encode');
const { addSpaceIfNeeded, sleep } = require('~/server/utils');
const { getAppConfig } = require('~/server/services/Config');
const { spendTokens } = require('~/models/spendTokens');
const { handleOpenAIErrors } = require('./tools/util');
const { createLLM, RunManager } = require('./llm');
@ -702,6 +703,7 @@ class OpenAIClient extends BaseClient {
* In case of failure, it will return the default title, "New Chat".
*/
async titleConvo({ text, conversationId, responseText = '' }) {
const appConfig = await getAppConfig({ role: this.options.req?.user?.role });
this.conversationId = conversationId;
if (this.options.attachments) {
@ -731,7 +733,7 @@ class OpenAIClient extends BaseClient {
};
/** @type {TAzureConfig | undefined} */
const azureConfig = this.options?.req?.app?.locals?.[EModelEndpoint.azureOpenAI];
const azureConfig = appConfig?.[EModelEndpoint.azureOpenAI];
const resetTitleOptions = !!(
(this.azure && azureConfig) ||
@ -1120,6 +1122,7 @@ ${convo}
}
async chatCompletion({ payload, onProgress, abortController = null }) {
const appConfig = await getAppConfig({ role: this.options.req?.user?.role });
let error = null;
let intermediateReply = [];
const errorCallback = (err) => (error = err);
@ -1166,7 +1169,7 @@ ${convo}
}
/** @type {TAzureConfig | undefined} */
const azureConfig = this.options?.req?.app?.locals?.[EModelEndpoint.azureOpenAI];
const azureConfig = appConfig?.[EModelEndpoint.azureOpenAI];
if (
(this.azure && this.isVisionModel && azureConfig) ||

View file

@ -9,6 +9,7 @@ const { logAxiosError } = require('@librechat/api');
const { logger } = require('@librechat/data-schemas');
const { ContentTypes, EImageOutputType } = require('librechat-data-provider');
const { getStrategyFunctions } = require('~/server/services/Files/strategies');
const { getAppConfig } = require('~/server/services/Config');
const { extractBaseURL } = require('~/utils');
const { getFiles } = require('~/models/File');
@ -123,7 +124,7 @@ function createAbortHandler() {
* @param {MongoFile[]} [fields.imageFiles] - The images to be used for editing
* @returns {Array} - Array of image tools
*/
function createOpenAIImageTools(fields = {}) {
async function createOpenAIImageTools(fields = {}) {
/** @type {boolean} Used to initialize the Tool without necessary variables. */
const override = fields.override ?? false;
/** @type {boolean} */
@ -131,8 +132,9 @@ function createOpenAIImageTools(fields = {}) {
throw new Error('This tool is only available for agents.');
}
const { req } = fields;
const imageOutputType = req?.app.locals.imageOutputType || EImageOutputType.PNG;
const appFileStrategy = req?.app.locals.fileStrategy;
const appConfig = await getAppConfig({ role: req?.user?.role });
const imageOutputType = appConfig?.imageOutputType || EImageOutputType.PNG;
const appFileStrategy = appConfig?.fileStrategy;
const getApiKey = () => {
const apiKey = process.env.IMAGE_GEN_OAI_API_KEY ?? '';

View file

@ -24,8 +24,8 @@ const {
const { primeFiles: primeCodeFiles } = require('~/server/services/Files/Code/process');
const { createFileSearchTool, primeFiles: primeSearchFiles } = require('./fileSearch');
const { getUserPluginAuthValue } = require('~/server/services/PluginService');
const { getCachedTools, getAppConfig } = require('~/server/services/Config');
const { loadAuthValues } = require('~/server/services/Tools/credentials');
const { getCachedTools } = require('~/server/services/Config');
const { createMCPTool } = require('~/server/services/MCP');
/**
@ -143,6 +143,7 @@ const loadTools = async ({
functions = true,
returnMap = false,
}) => {
const appConfig = await getAppConfig({ role: options?.req?.user?.role });
const toolConstructors = {
flux: FluxAPI,
calculator: Calculator,
@ -272,7 +273,7 @@ const loadTools = async ({
};
continue;
} else if (tool === Tools.web_search) {
const webSearchConfig = options?.req?.app?.locals?.webSearch;
const webSearchConfig = appConfig?.webSearch;
const result = await loadWebSearchAuth({
userId: user,
loadAuthValues,