Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

### Changed

- [backend] Updated all backend dependencies to latest compatible versions: NX 20.8.2 β†’ 22.5.2, TypeScript 5.8.3 β†’ 5.9.3, @swc/core 1.11.x β†’ 1.15.13, NestJS packages to 11.1.14, Fastify 5.0.0 β†’ 5.7.4, pino-http 10.2.0 β†’ 11.0.0, cron 3.x β†’ 4.4.0, and 50+ other packages.
- [backend] Upgraded Mongoose from 8.1.1 to 9.2.2 with complete API migration (FilterQuery β†’ mongodb.Filter) across 10 files.
- [backend] Upgraded Jest from 29.7.0 to 30.2.0 with API migration (toThrowError β†’ toThrow).
- [backend] Updated ESLint from 9.28.0 to 9.39.3 (latest 9.x compatible with NX).
- [backend] Updated @fastify/static from 8.3.0 to 9.0.0, @types/node from 22.15.21 to 22.19.11, and class-validator from 0.14.3 to 0.14.4.
- [shared] Refactored emoji data (keywords and categories) from inline component code into separate utility module (`frontend/src/lib/util/emoji-data.ts`) for better organization and reusability.
- [todo] Refactored backend architecture into three-layer design: `todo-persistence` (database layer), `todo-provider` (business logic), and `todo-controller` (API endpoints) for better separation of concerns and testability.
- [todo] Added comprehensive unit test coverage (39 tests) for all three layers with proper mocking and error handling.
Expand Down Expand Up @@ -71,6 +76,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

### Fixed

- [backend] Fixed 5 security vulnerabilities through dependency updates (21 β†’ 16 vulnerabilities, 24% reduction).
- [backend] Fixed TypeScript 5.9 stricter type checking in OCR service (Buffer β†’ Uint8Array conversion for Blob constructor).
- [shared] Fixed EmojiPicker modal integration issues by replacing Carbon's Popover with a custom inline expandable dropdown that works reliably within modal constraints.
- [todo] Fixed missing sync when re-adding todos from history - now properly syncs to shared lists.
- [todo] Fixed bi-directional sync issue where changes in one browser didn't appear in other browsers - converted sync setup from onMount to reactive $effect.
Expand Down
7 changes: 4 additions & 3 deletions backend/libs/chat/src/lib/chat.mongodb.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@ import { ChatEntityDto } from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { randomUUID } from 'crypto';
import { FilterQuery, Model } from 'mongoose';
import { Filter } from 'mongodb';
import { Model } from 'mongoose';
import { Chat, ChatDocument } from './schema/chat.schema';

@Injectable()
Expand All @@ -22,10 +23,10 @@ export class ChatMongoDbService {
* @returns An array of chat objects.
*/
async findAll(
filter: FilterQuery<ChatDocument> = {},
filter: Filter<ChatDocument> = {},
): Promise<ChatEntityDto[]> {
this.logger.debug({ input: { filter } }, ChatTexts.DB_ATTEMPT_FIND_ALL);
const chats = await this.chatModel.find(filter).exec();
const chats = await this.chatModel.find(filter as any).exec();
const chatEntities = chats.map((chat) => chat.toObject() as ChatEntityDto);
this.logger.debug(
{ output: { chats } },
Expand Down
4 changes: 2 additions & 2 deletions backend/libs/chat/src/lib/chat.service.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { ChatTexts } from '@backend/shared-texts';
import { ChatEntityDto } from '@backend/shared-types';
import { Injectable, Logger } from '@nestjs/common';
import { FilterQuery } from 'mongoose';
import { Filter } from 'mongodb';
import { ChatMongoDbService } from './chat.mongodb.service';
import { ChatDocument } from './schema/chat.schema';

Expand Down Expand Up @@ -31,7 +31,7 @@ export class ChatService {
* @returns An array of chat objects.
*/
async listChats(
filter: FilterQuery<ChatDocument> = {},
filter: Filter<ChatDocument> = {},
): Promise<ChatEntityDto[]> {
this.logger.verbose(ChatTexts.ATTEMPT_FIND_ALL);
const chats = await this.chatMongoDbService.findAll(filter);
Expand Down
7 changes: 4 additions & 3 deletions backend/libs/jokes/src/lib/jokes-mongodb.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@ import { JokeTexts } from '@backend/shared-texts';
import { JokeDto, ModifyJokeDto } from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { FilterQuery, Model } from 'mongoose';
import { Filter } from 'mongodb';
import { Model } from 'mongoose';
import { Joke, JokeDocument } from './schema/jokes.schema';

@Injectable()
Expand Down Expand Up @@ -89,9 +90,9 @@ export class JokesMongoDbService {
* @param filter Optional param to filter for specific joke results.
* @returns An array of joke objects.
*/
async findAll(filter: FilterQuery<JokeDocument> = {}): Promise<JokeDto[]> {
async findAll(filter: Filter<JokeDocument> = {}): Promise<JokeDto[]> {
this.logger.debug({ input: { filter } }, JokeTexts.ATTEMPT_FIND_ALL);
const jokes = await this.jokeModel.find(filter).exec();
const jokes = await this.jokeModel.find(filter as any).exec();
this.logger.debug({ output: jokes }, JokeTexts.FOUND_ALL);
return jokes.map((joke) => joke.toObject());
}
Expand Down
4 changes: 2 additions & 2 deletions backend/libs/jokes/src/lib/jokes.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { JokeDto, ModifyJokeDto } from '@backend/shared-types';
import { HttpService } from '@nestjs/axios';
import { Injectable, Logger } from '@nestjs/common';
import { Cron } from '@nestjs/schedule';
import { FilterQuery } from 'mongoose';
import { Filter } from 'mongodb';
import { firstValueFrom } from 'rxjs';
import { JokesMongoDbService } from './jokes-mongodb.service';
import { JokeDocument } from './schema/jokes.schema';
Expand Down Expand Up @@ -74,7 +74,7 @@ export class JokesService {
* @param filter Optional param to filter for specific joke results.
* @returns An array of jokes.
*/
async listJokes(filter: FilterQuery<JokeDocument> = {}): Promise<JokeDto[]> {
async listJokes(filter: Filter<JokeDocument> = {}): Promise<JokeDto[]> {
this.logger.log('Getting all jokes.');
return await this.jokesMongoDbService.findAll(filter);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {
UpdateIdentifierOutputDto,
} from '@backend/shared-types';
import { Injectable, Logger } from '@nestjs/common';
import { FilterQuery } from 'mongoose';
import { Filter } from 'mongodb';
import { IdentifiersMongoDbService } from './identifiers-mongodb.service';
import { IdentifierDocument } from './schema/identifiers.schema';

Expand All @@ -25,7 +25,7 @@ export class IdentifiersService {
* @returns An array of identifier objects.
*/
async listIdentifiers(
filter: FilterQuery<IdentifierDocument> = {},
filter: Filter<IdentifierDocument> = {},
): Promise<GetIdentifiersOutputDto[]> {
this.logger.log('Return a list of all identifiers.');
return await this.identifiersMongoDbService.findAll(filter);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@ import { IdentifierDto } from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { randomUUID } from 'crypto';
import { FilterQuery, Model } from 'mongoose';
import { Filter } from 'mongodb';
import { Model } from 'mongoose';
import { Identifier, IdentifierDocument } from './schema/identifiers.schema';

@Injectable()
Expand All @@ -22,10 +23,10 @@ export class IdentifiersMongoDbService {
* @returns An array of identifier objects.
*/
async findAll(
filter: FilterQuery<IdentifierDocument> = {},
filter: Filter<IdentifierDocument> = {},
): Promise<IdentifierDto[]> {
this.logger.debug({ input: { filter } }, IdentifiersTexts.ATTEMPT_FIND_ALL);
const identifiers = await this.identifierModel.find(filter).exec();
const identifiers = await this.identifierModel.find(filter as any).exec();
const identifierEntities = identifiers.map(
(identifier) => identifier.toObject() as IdentifierDto,
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ describe('KeystoreMongoDbService', () => {
mockKeystoreDto({ identifier: '1', key: 'key1' }),
mockKeystoreDto({ identifier: '2', key: 'key2' }),
];
jest.spyOn(keystoreModel, 'find').mockResolvedValue(expectedKeys);
jest.spyOn(keystoreModel, 'find').mockResolvedValue(expectedKeys as any);

// act
const keys = await service.findAll();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@ import { KeystoreDto, UpdateKeystoreInputBodyDto } from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { randomUUID } from 'crypto';
import { FilterQuery, Model } from 'mongoose';
import { Filter } from 'mongodb';
import { Model } from 'mongoose';
import { Keystore, KeystoreDocument } from './schema/keystore.schema';

@Injectable()
Expand All @@ -22,10 +23,10 @@ export class KeystoreMongoDbService {
* @returns An array of key objects.
*/
async findAll(
filter: FilterQuery<KeystoreDocument> = {},
filter: Filter<KeystoreDocument> = {},
): Promise<KeystoreDto[]> {
this.logger.debug({ input: { filter } }, KeystoreTexts.ATTEMPT_FIND_ALL);
const keys = await this.keystoreModel.find(filter);
const keys = await this.keystoreModel.find(filter as any);
this.logger.debug(
{ output: keys },
`MongoDb responded, found ${keys.length} keys.`,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ describe('SharedOcrService', () => {
.spyOn(httpService, 'post')
.mockReturnValueOnce(throwError(() => new Error(errorMsgMock)));

await expect(service.executeOcrProcess(fileMock)).rejects.toThrowError(
await expect(service.executeOcrProcess(fileMock)).rejects.toThrow(
errorMsgMock,
);
});
Expand Down
2 changes: 1 addition & 1 deletion backend/libs/shared/provider/ocr/src/lib/ocr.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ export class SharedOcrService {
body.set('OCREngine', '1');
body.set(
'file',
new Blob([file.buffer], { type: file.mimetype }),
new Blob([new Uint8Array(file.buffer)], { type: file.mimetype }),
fileName,
);

Expand Down
4 changes: 2 additions & 2 deletions backend/libs/shared/provider/todo/src/lib/todo.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import {
UpdateSharedTodoListOutputDto,
} from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { FilterQuery } from 'mongoose';
import { Filter } from 'mongodb';
import { TodoMongoDbService } from './todo-mongodb.service';
import { SharedTodoListDocument } from './schema/todo.schema';

Expand All @@ -26,7 +26,7 @@ export class TodoService {
* @returns An array of shared todo list objects.
*/
async listSharedTodoLists(
filter: FilterQuery<SharedTodoListDocument> = {},
filter: Filter<SharedTodoListDocument> = {},
): Promise<GetSharedTodoListsOutputDto[]> {
this.logger.log('Return a list of all shared todo lists.');
return (await this.todoMongoDbService.findAll()) as any;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import {
UpdateSharedTodoListOutputDto,
} from '@backend/shared-types';
import { Injectable, Logger, NotFoundException } from '@nestjs/common';
import { FilterQuery } from 'mongoose';
import { Filter } from 'mongodb';
import { TodoPersistenceService, SharedTodoListDocument } from '@backend/todo-persistence';

@Injectable()
Expand All @@ -25,7 +25,7 @@ export class TodoProviderService {
* @returns An array of shared todo list objects.
*/
async listSharedTodoLists(
filter: FilterQuery<SharedTodoListDocument> = {},
filter: Filter<SharedTodoListDocument> = {},
): Promise<GetSharedTodoListsOutputDto[]> {
this.logger.log('Return a list of all shared todo lists.');
return await this.todoPersistenceService.findAll() as any;
Expand Down
Loading
Loading