mirror of
https://github.com/coaidev/coai.git
synced 2025-05-19 04:50:14 +09:00
fix: fix sharing message use message action issue
This commit is contained in:
parent
a5d2c8c1ff
commit
f7a135af0e
@ -41,6 +41,7 @@ type MessageProps = {
|
||||
index: number;
|
||||
message: Message;
|
||||
end?: boolean;
|
||||
username?: string;
|
||||
onEvent?: (event: string, index?: number, message?: string) => void;
|
||||
ref?: Ref<HTMLElement>;
|
||||
sharing?: boolean;
|
||||
@ -216,10 +217,11 @@ function MessageContent({
|
||||
index,
|
||||
onEvent,
|
||||
selected,
|
||||
username,
|
||||
}: MessageProps) {
|
||||
const isUser = message.role === "user";
|
||||
|
||||
const username = useSelector(selectUsername);
|
||||
const user = useSelector(selectUsername);
|
||||
|
||||
const [open, setOpen] = useState(false);
|
||||
const [editedMessage, setEditedMessage] = useState<string | undefined>("");
|
||||
@ -239,7 +241,7 @@ function MessageContent({
|
||||
isUser ? (
|
||||
<Avatar
|
||||
className={`message-avatar animate-fade-in`}
|
||||
username={username}
|
||||
username={username ?? user}
|
||||
/>
|
||||
) : (
|
||||
<img
|
||||
|
@ -1,12 +0,0 @@
|
||||
import { EventCommitter } from "./struct.ts";
|
||||
import { Message } from "@/api/types.tsx";
|
||||
|
||||
export type SharingEvent = {
|
||||
refer: string;
|
||||
data: Message[];
|
||||
};
|
||||
|
||||
export const sharingEvent = new EventCommitter<SharingEvent>({
|
||||
name: "sharing",
|
||||
destroyedAfterTrigger: true,
|
||||
});
|
@ -19,7 +19,6 @@ import MessageSegment from "@/components/Message.tsx";
|
||||
import { Button } from "@/components/ui/button.tsx";
|
||||
import router from "@/router.tsx";
|
||||
import { useToast } from "@/components/ui/use-toast.ts";
|
||||
import { sharingEvent } from "@/events/sharing.ts";
|
||||
import { Message } from "@/api/types.tsx";
|
||||
import Avatar from "@/components/Avatar.tsx";
|
||||
import { toJpeg } from "html-to-image";
|
||||
@ -28,18 +27,20 @@ import { extractMessage } from "@/utils/processor.ts";
|
||||
import { cn } from "@/components/ui/lib/utils.ts";
|
||||
import { useMobile } from "@/utils/device.ts";
|
||||
import { ScrollArea } from "@/components/ui/scroll-area.tsx";
|
||||
import { useConversationActions } from "@/store/chat.ts";
|
||||
|
||||
type SharingFormProps = {
|
||||
refer?: string;
|
||||
data: ViewData | null;
|
||||
};
|
||||
|
||||
function SharingForm({ refer, data }: SharingFormProps) {
|
||||
function SharingForm({ data }: SharingFormProps) {
|
||||
if (data === null) return null;
|
||||
|
||||
const { t } = useTranslation();
|
||||
const { toast } = useToast();
|
||||
const mobile = useMobile();
|
||||
const { mask: setMask } = useConversationActions();
|
||||
const [maximized, setMaximized] = useState(false);
|
||||
const container = useRef<HTMLDivElement>(null);
|
||||
const date = new Date(data.time);
|
||||
@ -111,7 +112,12 @@ function SharingForm({ refer, data }: SharingFormProps) {
|
||||
</div>
|
||||
<div className={`shot-content`}>
|
||||
{data.messages.map((message, i) => (
|
||||
<MessageSegment message={message} key={i} index={i} />
|
||||
<MessageSegment
|
||||
message={message}
|
||||
key={i}
|
||||
index={i}
|
||||
username={data.username}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
@ -151,9 +157,11 @@ function SharingForm({ refer, data }: SharingFormProps) {
|
||||
<Button
|
||||
variant={`outline`}
|
||||
onClick={async () => {
|
||||
sharingEvent.emit({
|
||||
refer: refer as string,
|
||||
data: data?.messages as Message[],
|
||||
const message: Message[] = data?.messages || [];
|
||||
setMask({
|
||||
avatar: "",
|
||||
name: data.name,
|
||||
context: message,
|
||||
});
|
||||
await router.navigate("/");
|
||||
}}
|
||||
|
@ -14,10 +14,10 @@ type Limiter struct {
|
||||
Count int64
|
||||
}
|
||||
|
||||
func (l *Limiter) RateLimit(client *redis.Client, ip string, path string) bool {
|
||||
func (l *Limiter) RateLimit(client *redis.Client, ip string, path string) (bool, error) {
|
||||
key := fmt.Sprintf("rate:%s:%s", path, ip)
|
||||
rate := utils.IncrWithLimit(client, key, 1, l.Count, int64(l.Duration))
|
||||
return !rate
|
||||
rate, err := utils.IncrWithLimit(client, key, 1, l.Count, int64(l.Duration))
|
||||
return !rate, err
|
||||
}
|
||||
|
||||
var limits = map[string]Limiter{
|
||||
@ -64,14 +64,28 @@ func ThrottleMiddleware() gin.HandlerFunc {
|
||||
cache := utils.GetCacheFromContext(c)
|
||||
|
||||
limiter := GetPrefixMap[Limiter](path, limits)
|
||||
if limiter != nil && limiter.RateLimit(cache, ip, path) {
|
||||
c.JSON(200, gin.H{
|
||||
"status": false,
|
||||
"reason": "You have sent too many requests. Please try again later.",
|
||||
"error": "request_throttled",
|
||||
})
|
||||
c.Abort()
|
||||
return
|
||||
if limiter != nil {
|
||||
rate, err := limiter.RateLimit(cache, ip, path)
|
||||
|
||||
if err != nil {
|
||||
c.JSON(200, gin.H{
|
||||
"status": false,
|
||||
"reason": err.Error(),
|
||||
"error": err.Error(),
|
||||
})
|
||||
c.Abort()
|
||||
return
|
||||
}
|
||||
|
||||
if rate {
|
||||
c.JSON(200, gin.H{
|
||||
"status": false,
|
||||
"reason": "You have sent too many requests. Please try again later.",
|
||||
"error": "request_throttled",
|
||||
})
|
||||
c.Abort()
|
||||
return
|
||||
}
|
||||
}
|
||||
c.Next()
|
||||
}
|
||||
|
@ -53,25 +53,25 @@ func SetCache(cache *redis.Client, key string, value string, expiration int64) e
|
||||
return cache.Set(context.Background(), key, value, time.Duration(expiration)*time.Second).Err()
|
||||
}
|
||||
|
||||
func IncrWithLimit(cache *redis.Client, key string, delta int64, limit int64, expiration int64) bool {
|
||||
func IncrWithLimit(cache *redis.Client, key string, delta int64, limit int64, expiration int64) (bool, error) {
|
||||
// not exist
|
||||
if _, err := cache.Get(context.Background(), key).Result(); err != nil {
|
||||
if errors.Is(err, redis.Nil) {
|
||||
cache.Set(context.Background(), key, delta, time.Duration(expiration)*time.Second)
|
||||
return true
|
||||
return true, nil
|
||||
}
|
||||
return false
|
||||
return false, err
|
||||
}
|
||||
res, err := Incr(cache, key, delta)
|
||||
if err != nil {
|
||||
return false
|
||||
return false, err
|
||||
}
|
||||
if res > limit {
|
||||
// reset
|
||||
cache.Set(context.Background(), key, limit, time.Duration(expiration)*time.Second)
|
||||
return false
|
||||
return false, nil
|
||||
}
|
||||
return true
|
||||
return true, nil
|
||||
}
|
||||
|
||||
func DecrInt(cache *redis.Client, key string, delta int64) bool {
|
||||
|
@ -145,7 +145,8 @@ func (w *WebSocket) IncrRate(key string) bool {
|
||||
|
||||
func (w *WebSocket) IncrRateWithLimit(key string, limit int64, expiration int64) bool {
|
||||
cache := w.GetCache()
|
||||
return IncrWithLimit(cache, key, 1, limit, expiration)
|
||||
state, err := IncrWithLimit(cache, key, 1, limit, expiration)
|
||||
return state && err == nil
|
||||
}
|
||||
|
||||
func (w *WebSocket) GetCtx() *gin.Context {
|
||||
|
Loading…
Reference in New Issue
Block a user