mirror of
https://github.com/Monadical-SAS/reflector.git
synced 2025-12-20 12:19:06 +00:00
feat: search backend (#537)
* docs: transient docs * chore: cleanup * webvtt WIP * webvtt field * chore: webvtt tests comments * chore: remove useless tests * feat: search TASK.md * feat: full text search by title/webvtt * chore: search api task * feat: search api * feat: search API * chore: rm task md * chore: roll back unnecessary validators * chore: pr review WIP * chore: pr review WIP * chore: pr review * chore: top imports * feat: better lint + ci * feat: better lint + ci * feat: better lint + ci * feat: better lint + ci * chore: lint * chore: lint * fix: db datetime definitions * fix: flush() params * fix: update transcript mutability expectation / test * fix: update transcript mutability expectation / test * chore: auto review * chore: new controller extraction * chore: new controller extraction * chore: cleanup * chore: review WIP * chore: pr WIP * chore: remove ci lint * chore: openapi regeneration * chore: openapi regeneration * chore: postgres test doc * fix: .dockerignore for arm binaries * fix: .dockerignore for arm binaries * fix: cap test loops * fix: cap test loops * fix: cap test loops * fix: get_transcript_topics * chore: remove flow.md docs and claude guidance * chore: remove claude.md db doc * chore: remove claude.md db doc * chore: remove claude.md db doc * chore: remove claude.md db doc
This commit is contained in:
@@ -209,7 +209,6 @@ export const $GetTranscript = {
|
||||
},
|
||||
created_at: {
|
||||
type: "string",
|
||||
format: "date-time",
|
||||
title: "Created At",
|
||||
},
|
||||
share_mode: {
|
||||
@@ -395,7 +394,6 @@ export const $GetTranscriptMinimal = {
|
||||
},
|
||||
created_at: {
|
||||
type: "string",
|
||||
format: "date-time",
|
||||
title: "Created At",
|
||||
},
|
||||
share_mode: {
|
||||
@@ -758,8 +756,15 @@ export const $Page_GetTranscriptMinimal_ = {
|
||||
title: "Items",
|
||||
},
|
||||
total: {
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
anyOf: [
|
||||
{
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "Total",
|
||||
},
|
||||
page: {
|
||||
@@ -800,7 +805,7 @@ export const $Page_GetTranscriptMinimal_ = {
|
||||
},
|
||||
},
|
||||
type: "object",
|
||||
required: ["items", "total", "page", "size"],
|
||||
required: ["items", "page", "size"],
|
||||
title: "Page[GetTranscriptMinimal]",
|
||||
} as const;
|
||||
|
||||
@@ -814,8 +819,15 @@ export const $Page_Room_ = {
|
||||
title: "Items",
|
||||
},
|
||||
total: {
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
anyOf: [
|
||||
{
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "Total",
|
||||
},
|
||||
page: {
|
||||
@@ -856,7 +868,7 @@ export const $Page_Room_ = {
|
||||
},
|
||||
},
|
||||
type: "object",
|
||||
required: ["items", "total", "page", "size"],
|
||||
required: ["items", "page", "size"],
|
||||
title: "Page[Room]",
|
||||
} as const;
|
||||
|
||||
@@ -973,6 +985,136 @@ export const $RtcOffer = {
|
||||
title: "RtcOffer",
|
||||
} as const;
|
||||
|
||||
export const $SearchResponse = {
|
||||
properties: {
|
||||
results: {
|
||||
items: {
|
||||
$ref: "#/components/schemas/SearchResult",
|
||||
},
|
||||
type: "array",
|
||||
title: "Results",
|
||||
},
|
||||
total: {
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
title: "Total",
|
||||
description: "Total number of search results",
|
||||
},
|
||||
query: {
|
||||
type: "string",
|
||||
minLength: 1,
|
||||
title: "Query",
|
||||
description: "Search query text",
|
||||
},
|
||||
limit: {
|
||||
type: "integer",
|
||||
maximum: 100,
|
||||
minimum: 1,
|
||||
title: "Limit",
|
||||
description: "Results per page",
|
||||
},
|
||||
offset: {
|
||||
type: "integer",
|
||||
minimum: 0,
|
||||
title: "Offset",
|
||||
description: "Number of results to skip",
|
||||
},
|
||||
},
|
||||
type: "object",
|
||||
required: ["results", "total", "query", "limit", "offset"],
|
||||
title: "SearchResponse",
|
||||
} as const;
|
||||
|
||||
export const $SearchResult = {
|
||||
properties: {
|
||||
id: {
|
||||
type: "string",
|
||||
minLength: 1,
|
||||
title: "Id",
|
||||
},
|
||||
title: {
|
||||
anyOf: [
|
||||
{
|
||||
type: "string",
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "Title",
|
||||
},
|
||||
user_id: {
|
||||
anyOf: [
|
||||
{
|
||||
type: "string",
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "User Id",
|
||||
},
|
||||
room_id: {
|
||||
anyOf: [
|
||||
{
|
||||
type: "string",
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "Room Id",
|
||||
},
|
||||
created_at: {
|
||||
type: "string",
|
||||
title: "Created At",
|
||||
},
|
||||
status: {
|
||||
type: "string",
|
||||
minLength: 1,
|
||||
title: "Status",
|
||||
},
|
||||
rank: {
|
||||
type: "number",
|
||||
maximum: 1,
|
||||
minimum: 0,
|
||||
title: "Rank",
|
||||
},
|
||||
duration: {
|
||||
anyOf: [
|
||||
{
|
||||
type: "number",
|
||||
minimum: 0,
|
||||
},
|
||||
{
|
||||
type: "null",
|
||||
},
|
||||
],
|
||||
title: "Duration",
|
||||
description: "Duration in seconds",
|
||||
},
|
||||
search_snippets: {
|
||||
items: {
|
||||
type: "string",
|
||||
},
|
||||
type: "array",
|
||||
title: "Search Snippets",
|
||||
description: "Text snippets around search matches",
|
||||
},
|
||||
},
|
||||
type: "object",
|
||||
required: [
|
||||
"id",
|
||||
"created_at",
|
||||
"status",
|
||||
"rank",
|
||||
"duration",
|
||||
"search_snippets",
|
||||
],
|
||||
title: "SearchResult",
|
||||
description: "Public search result model with computed fields.",
|
||||
} as const;
|
||||
|
||||
export const $SourceKind = {
|
||||
type: "string",
|
||||
enum: ["room", "live", "file"],
|
||||
@@ -1397,6 +1539,7 @@ export const $WherebyWebhookEvent = {
|
||||
title: "Type",
|
||||
},
|
||||
data: {
|
||||
additionalProperties: true,
|
||||
type: "object",
|
||||
title: "Data",
|
||||
},
|
||||
@@ -1414,11 +1557,15 @@ export const $Word = {
|
||||
},
|
||||
start: {
|
||||
type: "number",
|
||||
minimum: 0,
|
||||
title: "Start",
|
||||
description: "Time in seconds with float part",
|
||||
},
|
||||
end: {
|
||||
type: "number",
|
||||
minimum: 0,
|
||||
title: "End",
|
||||
description: "Time in seconds with float part",
|
||||
},
|
||||
speaker: {
|
||||
type: "integer",
|
||||
|
||||
@@ -20,6 +20,8 @@ import type {
|
||||
V1TranscriptsListResponse,
|
||||
V1TranscriptsCreateData,
|
||||
V1TranscriptsCreateResponse,
|
||||
V1TranscriptsSearchData,
|
||||
V1TranscriptsSearchResponse,
|
||||
V1TranscriptGetData,
|
||||
V1TranscriptGetResponse,
|
||||
V1TranscriptUpdateData,
|
||||
@@ -276,6 +278,35 @@ export class DefaultService {
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Transcripts Search
|
||||
* Full-text search across transcript titles and content.
|
||||
* @param data The data for the request.
|
||||
* @param data.q Search query text
|
||||
* @param data.limit Results per page
|
||||
* @param data.offset Number of results to skip
|
||||
* @param data.roomId
|
||||
* @returns SearchResponse Successful Response
|
||||
* @throws ApiError
|
||||
*/
|
||||
public v1TranscriptsSearch(
|
||||
data: V1TranscriptsSearchData,
|
||||
): CancelablePromise<V1TranscriptsSearchResponse> {
|
||||
return this.httpRequest.request({
|
||||
method: "GET",
|
||||
url: "/v1/transcripts/search",
|
||||
query: {
|
||||
q: data.q,
|
||||
limit: data.limit,
|
||||
offset: data.offset,
|
||||
room_id: data.roomId,
|
||||
},
|
||||
errors: {
|
||||
422: "Validation Error",
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Transcript Get
|
||||
* @param data The data for the request.
|
||||
|
||||
@@ -141,7 +141,7 @@ export type MeetingConsentRequest = {
|
||||
|
||||
export type Page_GetTranscriptMinimal_ = {
|
||||
items: Array<GetTranscriptMinimal>;
|
||||
total: number;
|
||||
total?: number | null;
|
||||
page: number | null;
|
||||
size: number | null;
|
||||
pages?: number | null;
|
||||
@@ -149,7 +149,7 @@ export type Page_GetTranscriptMinimal_ = {
|
||||
|
||||
export type Page_Room_ = {
|
||||
items: Array<Room>;
|
||||
total: number;
|
||||
total?: number | null;
|
||||
page: number | null;
|
||||
size: number | null;
|
||||
pages?: number | null;
|
||||
@@ -181,6 +181,47 @@ export type RtcOffer = {
|
||||
type: string;
|
||||
};
|
||||
|
||||
export type SearchResponse = {
|
||||
results: Array<SearchResult>;
|
||||
/**
|
||||
* Total number of search results
|
||||
*/
|
||||
total: number;
|
||||
/**
|
||||
* Search query text
|
||||
*/
|
||||
query: string;
|
||||
/**
|
||||
* Results per page
|
||||
*/
|
||||
limit: number;
|
||||
/**
|
||||
* Number of results to skip
|
||||
*/
|
||||
offset: number;
|
||||
};
|
||||
|
||||
/**
|
||||
* Public search result model with computed fields.
|
||||
*/
|
||||
export type SearchResult = {
|
||||
id: string;
|
||||
title?: string | null;
|
||||
user_id?: string | null;
|
||||
room_id?: string | null;
|
||||
created_at: string;
|
||||
status: string;
|
||||
rank: number;
|
||||
/**
|
||||
* Duration in seconds
|
||||
*/
|
||||
duration: number | null;
|
||||
/**
|
||||
* Text snippets around search matches
|
||||
*/
|
||||
search_snippets: Array<string>;
|
||||
};
|
||||
|
||||
export type SourceKind = "room" | "live" | "file";
|
||||
|
||||
export type SpeakerAssignment = {
|
||||
@@ -272,7 +313,13 @@ export type WherebyWebhookEvent = {
|
||||
|
||||
export type Word = {
|
||||
text: string;
|
||||
/**
|
||||
* Time in seconds with float part
|
||||
*/
|
||||
start: number;
|
||||
/**
|
||||
* Time in seconds with float part
|
||||
*/
|
||||
end: number;
|
||||
speaker?: number;
|
||||
};
|
||||
@@ -346,6 +393,24 @@ export type V1TranscriptsCreateData = {
|
||||
|
||||
export type V1TranscriptsCreateResponse = GetTranscript;
|
||||
|
||||
export type V1TranscriptsSearchData = {
|
||||
/**
|
||||
* Results per page
|
||||
*/
|
||||
limit?: number;
|
||||
/**
|
||||
* Number of results to skip
|
||||
*/
|
||||
offset?: number;
|
||||
/**
|
||||
* Search query text
|
||||
*/
|
||||
q: string;
|
||||
roomId?: string | null;
|
||||
};
|
||||
|
||||
export type V1TranscriptsSearchResponse = SearchResponse;
|
||||
|
||||
export type V1TranscriptGetData = {
|
||||
transcriptId: string;
|
||||
};
|
||||
@@ -633,6 +698,21 @@ export type $OpenApiTs = {
|
||||
};
|
||||
};
|
||||
};
|
||||
"/v1/transcripts/search": {
|
||||
get: {
|
||||
req: V1TranscriptsSearchData;
|
||||
res: {
|
||||
/**
|
||||
* Successful Response
|
||||
*/
|
||||
200: SearchResponse;
|
||||
/**
|
||||
* Validation Error
|
||||
*/
|
||||
422: HTTPValidationError;
|
||||
};
|
||||
};
|
||||
};
|
||||
"/v1/transcripts/{transcript_id}": {
|
||||
get: {
|
||||
req: V1TranscriptGetData;
|
||||
|
||||
@@ -23,8 +23,8 @@ export const formatTimeDifference = (seconds: number): string => {
|
||||
hours > 0
|
||||
? `${hours < 10 ? "\u00A0" : ""}${hours}h ago`
|
||||
: minutes > 0
|
||||
? `${minutes < 10 ? "\u00A0" : ""}${minutes}m ago`
|
||||
: `<1m ago`;
|
||||
? `${minutes < 10 ? "\u00A0" : ""}${minutes}m ago`
|
||||
: `<1m ago`;
|
||||
|
||||
return timeString;
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user