Add shared rooms

This commit is contained in:
2024-10-04 17:09:59 +02:00
parent 39d02ab265
commit ecb91bedc3
7 changed files with 170 additions and 11 deletions

View File

@@ -0,0 +1,40 @@
"""Add shared rooms
Revision ID: a7122bc0b2ca
Revises: 74b2b0236931
Create Date: 2024-10-04 16:41:28.841889
"""
from typing import Sequence, Union
import sqlalchemy as sa
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "a7122bc0b2ca"
down_revision: Union[str, None] = "74b2b0236931"
branch_labels: Union[str, Sequence[str], None] = None
depends_on: Union[str, Sequence[str], None] = None
def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.add_column(
"room",
sa.Column(
"is_shared",
sa.Boolean(),
server_default=sa.text("0"),
nullable=False,
),
)
# ### end Alembic commands ###
def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.drop_column("room", "is_shared")
# ### end Alembic commands ###

View File

@@ -36,6 +36,9 @@ rooms = sqlalchemy.Table(
nullable=False, nullable=False,
server_default="automatic-2nd-participant", server_default="automatic-2nd-participant",
), ),
sqlalchemy.Column(
"is_shared", sqlalchemy.Boolean, nullable=False, server_default=false()
),
) )
@@ -53,6 +56,7 @@ class Room(BaseModel):
recording_trigger: Literal[ recording_trigger: Literal[
"none", "prompt", "automatic", "automatic-2nd-participant" "none", "prompt", "automatic", "automatic-2nd-participant"
] = "automatic-2nd-participant" ] = "automatic-2nd-participant"
is_shared: bool = False
class RoomController: class RoomController:
@@ -98,6 +102,7 @@ class RoomController:
room_mode: str, room_mode: str,
recording_type: str, recording_type: str,
recording_trigger: str, recording_trigger: str,
is_shared: bool,
): ):
""" """
Add a new room Add a new room
@@ -112,6 +117,7 @@ class RoomController:
room_mode=room_mode, room_mode=room_mode,
recording_type=recording_type, recording_type=recording_type,
recording_trigger=recording_trigger, recording_trigger=recording_trigger,
is_shared=is_shared,
) )
query = rooms.insert().values(**room.model_dump()) query = rooms.insert().values(**room.model_dump())
try: try:

View File

@@ -28,6 +28,7 @@ class Room(BaseModel):
room_mode: str room_mode: str
recording_type: str recording_type: str
recording_trigger: str recording_trigger: str
is_shared: bool
class Meeting(BaseModel): class Meeting(BaseModel):
@@ -49,6 +50,7 @@ class CreateRoom(BaseModel):
room_mode: str room_mode: str
recording_type: str recording_type: str
recording_trigger: str recording_trigger: str
is_shared: bool
class UpdateRoom(BaseModel): class UpdateRoom(BaseModel):
@@ -60,6 +62,7 @@ class UpdateRoom(BaseModel):
room_mode: str room_mode: str
recording_type: str recording_type: str
recording_trigger: str recording_trigger: str
is_shared: bool
class DeletionStatus(BaseModel): class DeletionStatus(BaseModel):
@@ -100,6 +103,7 @@ async def rooms_create(
room_mode=room.room_mode, room_mode=room.room_mode,
recording_type=room.recording_type, recording_type=room.recording_type,
recording_trigger=room.recording_trigger, recording_trigger=room.recording_trigger,
is_shared=room.is_shared,
) )

View File

@@ -74,6 +74,9 @@ export default function TranscriptBrowser() {
React.useState<string>(); React.useState<string>();
const [deletedItemIds, setDeletedItemIds] = React.useState<string[]>(); const [deletedItemIds, setDeletedItemIds] = React.useState<string[]>();
const myRooms = rooms.filter((room) => !room.is_shared);
const sharedRooms = rooms.filter((room) => room.is_shared);
useEffect(() => { useEffect(() => {
setDeletedItemIds([]); setDeletedItemIds([]);
}, [page, response]); }, [page, response]);
@@ -102,6 +105,7 @@ export default function TranscriptBrowser() {
const handleSearch = () => { const handleSearch = () => {
setPage(1); setPage(1);
setSearchTerm(searchInputValue); setSearchTerm(searchInputValue);
setSelectedSourceKind(null);
setSelectedRoomId(""); setSelectedRoomId("");
refetch(); refetch();
}; };
@@ -205,13 +209,42 @@ export default function TranscriptBrowser() {
<Divider /> <Divider />
{rooms.length > 0 && ( {myRooms.length > 0 && (
<> <>
<Heading size="sm" mb={2}> <Heading size="sm">My Rooms</Heading>
My Rooms
</Heading>
{rooms.map((room) => ( {myRooms.map((room) => (
<Link
key={room.id}
as={NextLink}
href="#"
onClick={() => handleFilterTranscripts("room", room.id)}
color={
selectedSourceKind === "room" &&
selectedRoomId === room.id
? "blue.500"
: "gray.600"
}
_hover={{ color: "blue.300" }}
fontWeight={
selectedSourceKind === "room" &&
selectedRoomId === room.id
? "bold"
: "normal"
}
ml={4}
>
{room.name}
</Link>
))}
</>
)}
{sharedRooms.length > 0 && (
<>
<Heading size="sm">Shared Rooms</Heading>
{sharedRooms.map((room) => (
<Link <Link
key={room.id} key={room.id}
as={NextLink} as={NextLink}

View File

@@ -65,6 +65,7 @@ const roomInitialState = {
roomMode: "normal", roomMode: "normal",
recordingType: "cloud", recordingType: "cloud",
recordingTrigger: "automatic-2nd-participant", recordingTrigger: "automatic-2nd-participant",
isShared: false,
}; };
export default function RoomsList() { export default function RoomsList() {
@@ -159,6 +160,7 @@ export default function RoomsList() {
room_mode: room.roomMode, room_mode: room.roomMode,
recording_type: room.recordingType, recording_type: room.recordingType,
recording_trigger: room.recordingTrigger, recording_trigger: room.recordingTrigger,
is_shared: room.isShared,
}; };
if (isEditing) { if (isEditing) {
@@ -203,6 +205,7 @@ export default function RoomsList() {
roomMode: roomData.room_mode, roomMode: roomData.room_mode,
recordingType: roomData.recording_type, recordingType: roomData.recording_type,
recordingTrigger: roomData.recording_trigger, recordingTrigger: roomData.recording_trigger,
isShared: roomData.is_shared,
}); });
setEditRoomId(roomId); setEditRoomId(roomId);
setIsEditing(true); setIsEditing(true);
@@ -236,6 +239,11 @@ export default function RoomsList() {
}); });
}; };
const myRooms =
response?.items.filter((roomData) => !roomData.is_shared) || [];
const sharedRooms =
response?.items.filter((roomData) => roomData.is_shared) || [];
if (loading && !response) if (loading && !response)
return ( return (
<Flex flexDir="column" align="center" justify="center" h="100%"> <Flex flexDir="column" align="center" justify="center" h="100%">
@@ -375,6 +383,15 @@ export default function RoomsList() {
isDisabled={!room.zulipAutoPost} isDisabled={!room.zulipAutoPost}
/> />
</FormControl> </FormControl>
<FormControl mt={4}>
<Checkbox
name="isShared"
isChecked={room.isShared}
onChange={handleRoomChange}
>
Shared room
</Checkbox>
</FormControl>
</ModalBody> </ModalBody>
<ModalFooter> <ModalFooter>
@@ -396,9 +413,10 @@ export default function RoomsList() {
</Modal> </Modal>
</Flex> </Flex>
<VStack> <VStack align="start" mb={6} pt={4} gap={4}>
{response?.items && response.items.length > 0 ? ( <Heading size="md">My Rooms</Heading>
response.items.map((roomData) => ( {myRooms.length > 0 ? (
myRooms.map((roomData) => (
<Card w={"full"} key={roomData.id}> <Card w={"full"} key={roomData.id}>
<CardBody> <CardBody>
<Flex align={"center"}> <Flex align={"center"}>
@@ -445,9 +463,61 @@ export default function RoomsList() {
</Card> </Card>
)) ))
) : ( ) : (
<Flex flexDir="column" align="center" justify="center" h="100%"> <Text>No rooms found</Text>
<Text>No rooms found</Text> )}
</Flex> </VStack>
<VStack align="start">
<Heading size="md">Shared Rooms</Heading>
{sharedRooms.length > 0 ? (
sharedRooms.map((roomData) => (
<Card w={"full"} key={roomData.id}>
<CardBody>
<Flex align={"center"}>
<Heading size="md">
<Link href={`/${roomData.name}`}>{roomData.name}</Link>
</Heading>
<Spacer />
{linkCopied === roomData.name ? (
<Text mr={2} color="green.500">
Link copied!
</Text>
) : (
<IconButton
aria-label="Copy URL"
icon={<FaLink />}
onClick={() => handleCopyUrl(roomData.name)}
mr={2}
/>
)}
<Menu closeOnSelect={true}>
<MenuButton
as={IconButton}
icon={<FaEllipsisVertical />}
aria-label="actions"
/>
<MenuList>
<MenuItem
onClick={() => handleEditRoom(roomData.id, roomData)}
icon={<FaPencil />}
>
Edit
</MenuItem>
<MenuItem
onClick={() => handleDeleteRoom(roomData.id)}
icon={<FaTrash color={"red.500"} />}
>
Delete
</MenuItem>
</MenuList>
</Menu>
</Flex>
</CardBody>
</Card>
))
) : (
<Text>No shared rooms found</Text>
)} )}
</VStack> </VStack>
</Container> </Container>

View File

@@ -736,6 +736,10 @@ export const $Room = {
type: "string", type: "string",
title: "Recording Trigger", title: "Recording Trigger",
}, },
is_shared: {
type: "boolean",
title: "Is Shared",
},
}, },
type: "object", type: "object",
required: [ required: [
@@ -750,6 +754,7 @@ export const $Room = {
"room_mode", "room_mode",
"recording_type", "recording_type",
"recording_trigger", "recording_trigger",
"is_shared",
], ],
title: "Room", title: "Room",
} as const; } as const;

View File

@@ -143,6 +143,7 @@ export type Room = {
room_mode: string; room_mode: string;
recording_type: string; recording_type: string;
recording_trigger: string; recording_trigger: string;
is_shared: boolean;
}; };
export type RtcOffer = { export type RtcOffer = {