mirror of
https://github.com/Sendouc/sendou.ink.git
synced 2026-09-26 05:12:19 -05:00
Show text if in trusted group someone rejoined queue
This commit is contained in:
@@ -58,9 +58,11 @@ export function MatchmadeRejoinSection({
|
||||
export function TrustedRejoinSection({
|
||||
viewerGroup,
|
||||
hasJoinedNewGroup,
|
||||
someGroupMemberHasJoinedNewGroup,
|
||||
}: {
|
||||
viewerGroup: NonNullable<SendouQMatchLoaderData["match"]["groupAlpha"]>;
|
||||
hasJoinedNewGroup: boolean;
|
||||
someGroupMemberHasJoinedNewGroup: boolean;
|
||||
}) {
|
||||
const { t } = useTranslation(["q"]);
|
||||
const lookAgain = useActionSubmit(matchSchema);
|
||||
@@ -77,6 +79,15 @@ export function TrustedRejoinSection({
|
||||
);
|
||||
}
|
||||
|
||||
// the whole group has to be free for it, so offering it here could only fail
|
||||
if (someGroupMemberHasJoinedNewGroup) {
|
||||
return (
|
||||
<RejoinQueueSection
|
||||
explanation={t("q:match.rematch.memberJoinedNewGroup")}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="stack md items-center">
|
||||
<SendouButton
|
||||
@@ -96,14 +107,18 @@ export function TrustedRejoinSection({
|
||||
|
||||
function DeclinedSection() {
|
||||
const { t } = useTranslation(["q"]);
|
||||
|
||||
return <RejoinQueueSection explanation={t("q:match.rematch.declined")} />;
|
||||
}
|
||||
|
||||
function RejoinQueueSection({ explanation }: { explanation: string }) {
|
||||
const { t } = useTranslation(["q"]);
|
||||
const rejoinQueue = useActionSubmit(frontPageSchema, {
|
||||
action: SENDOUQ_PAGE,
|
||||
});
|
||||
return (
|
||||
<div className="stack md items-center">
|
||||
<p className="text-lighter text-sm text-center">
|
||||
{t("q:match.rematch.declined")}
|
||||
</p>
|
||||
<p className="text-lighter text-sm text-center">{explanation}</p>
|
||||
<SendouButton
|
||||
variant="minimal"
|
||||
className="text-sm font-bold"
|
||||
|
||||
@@ -286,6 +286,9 @@ function RequeueTab({
|
||||
<TrustedRejoinSection
|
||||
viewerGroup={viewerGroup}
|
||||
hasJoinedNewGroup={data.hasJoinedNewGroup}
|
||||
someGroupMemberHasJoinedNewGroup={
|
||||
data.someGroupMemberHasJoinedNewGroup
|
||||
}
|
||||
/>
|
||||
) : null}
|
||||
{isOnReporterTeam ? <hr className={styles.divider} /> : null}
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
import { beforeEach, describe, expect, test } from "vitest";
|
||||
import * as SQGroupFactory from "~/db/seed/factories/SQGroupFactory";
|
||||
import * as SQMatchFactory from "~/db/seed/factories/SQMatchFactory";
|
||||
import * as UserFactory from "~/db/seed/factories/UserFactory";
|
||||
import { db } from "~/db/sql";
|
||||
import { refreshSendouQInstance } from "~/features/sendouq/core/SendouQ.server";
|
||||
import type { SerializeFrom } from "~/utils/remix";
|
||||
import { wrappedLoader } from "~/utils/Test";
|
||||
import { loader } from "./q.match.$id.server";
|
||||
@@ -21,11 +23,14 @@ describe("q match loader", () => {
|
||||
await users.create(10);
|
||||
});
|
||||
|
||||
const createMatch = () =>
|
||||
SQMatchFactory.create({
|
||||
alphaUserIds: alphaUserIds(),
|
||||
bravoUserIds: bravoUserIds(),
|
||||
});
|
||||
const createMatch = (options: { isConcluded?: boolean } = {}) =>
|
||||
SQMatchFactory.create(
|
||||
{
|
||||
alphaUserIds: alphaUserIds(),
|
||||
bravoUserIds: bravoUserIds(),
|
||||
},
|
||||
options,
|
||||
);
|
||||
|
||||
const groupChatRoomId = async (groupId: number) =>
|
||||
(
|
||||
@@ -93,4 +98,50 @@ describe("q match loader", () => {
|
||||
|
||||
expect(data.chatRooms).toEqual([]);
|
||||
});
|
||||
|
||||
describe("requeueing with the same group", () => {
|
||||
const queueElsewhere = async (userId: number) => {
|
||||
await SQGroupFactory.create({ memberUserIds: [userId] });
|
||||
await refreshSendouQInstance();
|
||||
};
|
||||
|
||||
test("offers the requeue while every member is free of other groups", async () => {
|
||||
const match = await createMatch({ isConcluded: true });
|
||||
await refreshSendouQInstance();
|
||||
|
||||
const data = await loadAs(alphaUserIds()[0], match.id);
|
||||
|
||||
expect(data.hasJoinedNewGroup).toBe(false);
|
||||
expect(data.someGroupMemberHasJoinedNewGroup).toBe(false);
|
||||
});
|
||||
|
||||
test("points the member who queued elsewhere to their new group", async () => {
|
||||
const match = await createMatch({ isConcluded: true });
|
||||
await queueElsewhere(alphaUserIds()[1]);
|
||||
|
||||
const data = await loadAs(alphaUserIds()[1], match.id);
|
||||
|
||||
expect(data.hasJoinedNewGroup).toBe(true);
|
||||
});
|
||||
|
||||
test("blocks the requeue for the rest of the group too", async () => {
|
||||
const match = await createMatch({ isConcluded: true });
|
||||
await queueElsewhere(alphaUserIds()[1]);
|
||||
|
||||
const data = await loadAs(alphaUserIds()[0], match.id);
|
||||
|
||||
expect(data.hasJoinedNewGroup).toBe(false);
|
||||
expect(data.someGroupMemberHasJoinedNewGroup).toBe(true);
|
||||
});
|
||||
|
||||
test("leaves the other group's requeue alone", async () => {
|
||||
const match = await createMatch({ isConcluded: true });
|
||||
await queueElsewhere(alphaUserIds()[1]);
|
||||
|
||||
const data = await loadAs(bravoUserIds()[0], match.id);
|
||||
|
||||
expect(data.hasJoinedNewGroup).toBe(false);
|
||||
expect(data.someGroupMemberHasJoinedNewGroup).toBe(false);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -46,12 +46,23 @@ export const loader = async ({ params }: LoaderFunctionArgs) => {
|
||||
|
||||
const match = SendouQ.mapMatch(matchUnmapped, user);
|
||||
|
||||
const currentGroup = user ? SendouQ.findOwnGroup(user.id) : undefined;
|
||||
const viewerGroup = user
|
||||
? [matchUnmapped.groupAlpha, matchUnmapped.groupBravo].find((group) =>
|
||||
group.members.some((member) => member.id === user.id),
|
||||
)
|
||||
: undefined;
|
||||
|
||||
const joinedNewGroup = (userId: number) => {
|
||||
const currentGroup = SendouQ.findOwnGroup(userId);
|
||||
return Boolean(currentGroup && currentGroup.matchId !== matchId);
|
||||
};
|
||||
|
||||
return {
|
||||
// e.g. the group already requeued, so the viewer has nothing left to requeue with
|
||||
hasJoinedNewGroup: Boolean(
|
||||
currentGroup && currentGroup.matchId !== matchId,
|
||||
hasJoinedNewGroup: Boolean(user && joinedNewGroup(user.id)),
|
||||
// requeueing with the same group needs every member of it free of other groups
|
||||
someGroupMemberHasJoinedNewGroup: Boolean(
|
||||
viewerGroup?.members.some((member) => joinedNewGroup(member.id)),
|
||||
),
|
||||
...(await UserCardRepository.findAllByUserIds({
|
||||
userIds: matchUsers,
|
||||
|
||||
5
changelog/2026-09-20-sendouq-look-again-blocked.md
Normal file
5
changelog/2026-09-20-sendouq-look-again-blocked.md
Normal file
@@ -0,0 +1,5 @@
|
||||
---
|
||||
navItem: sendouq
|
||||
type: bug
|
||||
---
|
||||
"Look again with same group" is no longer offered when someone from your group has already joined another group. Instead you are told so and can rejoin the queue right away
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "No, I'm done",
|
||||
"match.rematch.vote.noConfirm": "Vote no? You can't change your vote afterwards.",
|
||||
"match.rematch.declined": "You are not continuing with this group",
|
||||
"match.rematch.memberJoinedNewGroup": "A member of your group already joined another group",
|
||||
"match.rematch.fizzled": "Nobody wanted to continue",
|
||||
"match.rematch.rejoinQueue": "Rejoin queue",
|
||||
"match.rematch.backToQueue": "Back to queue",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "No, he terminado",
|
||||
"match.rematch.vote.noConfirm": "¿Votar no? No podrás cambiar tu voto después.",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "Nadie quiso continuar",
|
||||
"match.rematch.rejoinQueue": "Volver a la cola",
|
||||
"match.rematch.backToQueue": "Volver a la cola",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "No, he terminado",
|
||||
"match.rematch.vote.noConfirm": "¿Votar no? No podrás cambiar tu voto después.",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "Nadie quiso continuar",
|
||||
"match.rematch.rejoinQueue": "Volver a la cola",
|
||||
"match.rematch.backToQueue": "Volver a la cola",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "",
|
||||
"match.rematch.vote.noConfirm": "",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "",
|
||||
"match.rematch.rejoinQueue": "",
|
||||
"match.rematch.backToQueue": "",
|
||||
|
||||
@@ -165,6 +165,7 @@
|
||||
"match.rematch.vote.no": "不,到此为止",
|
||||
"match.rematch.vote.noConfirm": "确认投反对票吗?投票后将无法更改。",
|
||||
"match.rematch.declined": "",
|
||||
"match.rematch.memberJoinedNewGroup": "",
|
||||
"match.rematch.fizzled": "无人想要继续排队",
|
||||
"match.rematch.rejoinQueue": "重新加入队列",
|
||||
"match.rematch.backToQueue": "返回队列",
|
||||
|
||||
Reference in New Issue
Block a user