mirror of
https://github.com/danny-avila/LibreChat.git
synced 2025-12-17 08:50:15 +01:00
🪨 feat: AWS Bedrock support (#3935)
* feat: Add BedrockIcon component to SVG library * feat: EModelEndpoint.bedrock * feat: first pass, bedrock chat. note: AgentClient is returning `agents` as conversation.endpoint * fix: declare endpoint in initialization step * chore: Update @librechat/agents dependency to version 1.4.5 * feat: backend content aggregation for agents/bedrock * feat: abort agent requests * feat: AWS Bedrock icons * WIP: agent provider schema parsing * chore: Update EditIcon props type * refactor(useGenerationsByLatest): make agents and bedrock editable * refactor: non-assistant message content, parts * fix: Bedrock response `sender` * fix: use endpointOption.model_parameters not endpointOption.modelOptions * fix: types for step handler * refactor: Update Agents.ToolCallDelta type * refactor: Remove unnecessary assignment of parentMessageId in AskController * refactor: remove unnecessary assignment of parentMessageId (agent request handler) * fix(bedrock/agents): message regeneration * refactor: dynamic form elements using react-hook-form Controllers * fix: agent icons/labels for messages * fix: agent actions * fix: use of new dynamic tags causing application crash * refactor: dynamic settings touch-ups * refactor: update Slider component to allow custom track class name * refactor: update DynamicSlider component styles * refactor: use Constants value for GLOBAL_PROJECT_NAME (enum) * feat: agent share global methods/controllers * fix: agents query * fix: `getResponseModel` * fix: share prompt a11y issue * refactor: update SharePrompt dialog theme styles * refactor: explicit typing for SharePrompt * feat: add agent roles/permissions * chore: update @librechat/agents dependency to version 1.4.7 for tool_call_ids edge case * fix(Anthropic): messages.X.content.Y.tool_use.input: Input should be a valid dictionary * fix: handle text parts with tool_call_ids and empty text * fix: role initialization * refactor: don't make instructions required * refactor: improve typing of Text part * fix: setShowStopButton for agents route * chore: remove params for now * fix: add streamBuffer and streamRate to help prevent 'Overloaded' errors from Anthropic API * refactor: remove console.log statement in ContentRender component * chore: typing, rename Context to Delete Button * chore(DeleteButton): logging * refactor(Action): make accessible * style(Action): improve a11y again * refactor: remove use/mention of mongoose sessions * feat: first pass, sharing agents * feat: visual indicator for global agent, remove author when serving to non-author * wip: params * chore: fix typing issues * fix(schemas): typing * refactor: improve accessibility of ListCard component and fix console React warning * wip: reset templates for non-legacy new convos * Revert "wip: params" This reverts commitf8067e91d4. * Revert "refactor: dynamic form elements using react-hook-form Controllers" This reverts commit2150c4815d. * fix(Parameters): types and parameter effect update to only update local state to parameters * refactor: optimize useDebouncedInput hook for better performance * feat: first pass, anthropic bedrock params * chore: paramEndpoints check for endpointType too * fix: maxTokens to use coerceNumber.optional(), * feat: extra chat model params * chore: reduce code repetition * refactor: improve preset title handling in SaveAsPresetDialog component * refactor: improve preset handling in HeaderOptions component * chore: improve typing, replace legacy dialog for SaveAsPresetDialog * feat: save as preset from parameters panel * fix: multi-search in select dropdown when using Option type * refactor: update default showDefault value to false in Dynamic components * feat: Bedrock presets settings * chore: config, fix agents schema, update config version * refactor: update AWS region variable name in bedrock options endpoint to BEDROCK_AWS_DEFAULT_REGION * refactor: update baseEndpointSchema in config.ts to include baseURL property * refactor: update createRun function to include req parameter and set streamRate based on provider * feat: availableRegions via config * refactor: remove unused demo agent controller file * WIP: title * Update @librechat/agents to version 1.5.0 * chore: addTitle.js to handle empty responseText * feat: support images and titles * feat: context token updates * Refactor BaseClient test to use expect.objectContaining * refactor: add model select, remove header options params, move side panel params below prompts * chore: update models list, catch title error * feat: model service for bedrock models (env) * chore: Remove verbose debug log in AgentClient class following stream * feat(bedrock): track token spend; fix: token rates, value key mapping for AWS models * refactor: handle streamRate in `handleLLMNewToken` callback * chore: AWS Bedrock example config in `.env.example` * refactor: Rename bedrockMeta to bedrockGeneral in settings.ts and use for AI21 and Amazon Bedrock providers * refactor: Update `.env.example` with AWS Bedrock model IDs URL and additional notes * feat: titleModel support for bedrock * refactor: Update `.env.example` with additional notes for AWS Bedrock model IDs
This commit is contained in:
parent
8c14360263
commit
d59b62174f
134 changed files with 3684 additions and 1213 deletions
170
client/src/components/Messages/ContentRender.tsx
Normal file
170
client/src/components/Messages/ContentRender.tsx
Normal file
|
|
@ -0,0 +1,170 @@
|
|||
import { useRecoilValue } from 'recoil';
|
||||
import { useCallback, useMemo, memo } from 'react';
|
||||
import type { TMessage, TMessageContentParts } from 'librechat-data-provider';
|
||||
import type { TMessageProps } from '~/common';
|
||||
import ContentParts from '~/components/Chat/Messages/Content/ContentParts';
|
||||
import PlaceholderRow from '~/components/Chat/Messages/ui/PlaceholderRow';
|
||||
import SiblingSwitch from '~/components/Chat/Messages/SiblingSwitch';
|
||||
import HoverButtons from '~/components/Chat/Messages/HoverButtons';
|
||||
import Icon from '~/components/Chat/Messages/MessageIcon';
|
||||
import SubRow from '~/components/Chat/Messages/SubRow';
|
||||
import { useMessageActions } from '~/hooks';
|
||||
import { cn, logger } from '~/utils';
|
||||
import store from '~/store';
|
||||
|
||||
type ContentRenderProps = {
|
||||
message?: TMessage;
|
||||
isCard?: boolean;
|
||||
isMultiMessage?: boolean;
|
||||
isSubmittingFamily?: boolean;
|
||||
} & Pick<
|
||||
TMessageProps,
|
||||
'currentEditId' | 'setCurrentEditId' | 'siblingIdx' | 'setSiblingIdx' | 'siblingCount'
|
||||
>;
|
||||
|
||||
const ContentRender = memo(
|
||||
({
|
||||
isCard,
|
||||
siblingIdx,
|
||||
siblingCount,
|
||||
message: msg,
|
||||
setSiblingIdx,
|
||||
currentEditId,
|
||||
isMultiMessage,
|
||||
setCurrentEditId,
|
||||
isSubmittingFamily,
|
||||
}: ContentRenderProps) => {
|
||||
const {
|
||||
// ask,
|
||||
edit,
|
||||
index,
|
||||
agent,
|
||||
assistant,
|
||||
enterEdit,
|
||||
conversation,
|
||||
messageLabel,
|
||||
isSubmitting,
|
||||
latestMessage,
|
||||
handleContinue,
|
||||
copyToClipboard,
|
||||
setLatestMessage,
|
||||
regenerateMessage,
|
||||
} = useMessageActions({
|
||||
message: msg,
|
||||
currentEditId,
|
||||
isMultiMessage,
|
||||
setCurrentEditId,
|
||||
});
|
||||
|
||||
const fontSize = useRecoilValue(store.fontSize);
|
||||
const handleRegenerateMessage = useCallback(() => regenerateMessage(), [regenerateMessage]);
|
||||
// const { isCreatedByUser, error, unfinished } = msg ?? {};
|
||||
const isLast = useMemo(
|
||||
() =>
|
||||
!(msg?.children?.length ?? 0) && (msg?.depth === latestMessage?.depth || msg?.depth === -1),
|
||||
[msg?.children, msg?.depth, latestMessage?.depth],
|
||||
);
|
||||
|
||||
if (!msg) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const isLatestMessage = msg.messageId === latestMessage?.messageId;
|
||||
const showCardRender = isLast && !(isSubmittingFamily === true) && isCard === true;
|
||||
const isLatestCard = isCard === true && !(isSubmittingFamily === true) && isLatestMessage;
|
||||
const clickHandler =
|
||||
showCardRender && !isLatestMessage
|
||||
? () => {
|
||||
logger.log(`Message Card click: Setting ${msg.messageId} as latest message`);
|
||||
logger.dir(msg);
|
||||
setLatestMessage(msg);
|
||||
}
|
||||
: undefined;
|
||||
|
||||
return (
|
||||
<div
|
||||
aria-label={`message-${msg.depth}-${msg.messageId}`}
|
||||
className={cn(
|
||||
'final-completion group mx-auto flex flex-1 gap-3',
|
||||
isCard === true
|
||||
? 'relative w-full gap-1 rounded-lg border border-border-medium bg-surface-primary-alt p-2 md:w-1/2 md:gap-3 md:p-4'
|
||||
: 'md:max-w-3xl md:px-5 lg:max-w-[40rem] lg:px-1 xl:max-w-[48rem] xl:px-5',
|
||||
isLatestCard === true ? 'bg-surface-secondary' : '',
|
||||
showCardRender ? 'cursor-pointer transition-colors duration-300' : '',
|
||||
'focus:outline-none focus:ring-2 focus:ring-border-xheavy',
|
||||
)}
|
||||
onClick={clickHandler}
|
||||
onKeyDown={(e) => {
|
||||
if ((e.key === 'Enter' || e.key === ' ') && clickHandler) {
|
||||
clickHandler();
|
||||
}
|
||||
}}
|
||||
role={showCardRender ? 'button' : undefined}
|
||||
tabIndex={showCardRender ? 0 : undefined}
|
||||
>
|
||||
{isLatestCard === true && (
|
||||
<div className="absolute right-0 top-0 m-2 h-3 w-3 rounded-full bg-text-primary" />
|
||||
)}
|
||||
<div className="relative flex flex-shrink-0 flex-col items-end">
|
||||
<div>
|
||||
<div className="pt-0.5">
|
||||
<div className="flex h-6 w-6 items-center justify-center overflow-hidden rounded-full">
|
||||
<Icon
|
||||
message={msg}
|
||||
conversation={conversation}
|
||||
assistant={assistant}
|
||||
agent={agent}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
className={cn(
|
||||
'relative flex w-11/12 flex-col',
|
||||
msg.isCreatedByUser === true ? '' : 'agent-turn',
|
||||
)}
|
||||
>
|
||||
<h2 className={cn('select-none font-semibold', fontSize)}>{messageLabel}</h2>
|
||||
<div className="flex-col gap-1 md:gap-3">
|
||||
<div className="flex max-w-full flex-grow flex-col gap-0">
|
||||
<ContentParts
|
||||
content={msg.content as Array<TMessageContentParts | undefined>}
|
||||
messageId={msg.messageId}
|
||||
isCreatedByUser={msg.isCreatedByUser}
|
||||
isLast={isLast}
|
||||
isSubmitting={isSubmitting}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
{!(msg.children?.length ?? 0) && (isSubmittingFamily === true || isSubmitting) ? (
|
||||
<PlaceholderRow isCard={isCard} />
|
||||
) : (
|
||||
<SubRow classes="text-xs">
|
||||
<SiblingSwitch
|
||||
siblingIdx={siblingIdx}
|
||||
siblingCount={siblingCount}
|
||||
setSiblingIdx={setSiblingIdx}
|
||||
/>
|
||||
<HoverButtons
|
||||
index={index}
|
||||
isEditing={edit}
|
||||
message={msg}
|
||||
enterEdit={enterEdit}
|
||||
isSubmitting={isSubmitting}
|
||||
conversation={conversation ?? null}
|
||||
regenerate={handleRegenerateMessage}
|
||||
copyToClipboard={copyToClipboard}
|
||||
handleContinue={handleContinue}
|
||||
latestMessage={latestMessage}
|
||||
isLast={isLast}
|
||||
/>
|
||||
</SubRow>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
},
|
||||
);
|
||||
|
||||
export default ContentRender;
|
||||
Loading…
Add table
Add a link
Reference in a new issue