diff --git a/app-nest/src/bolt/enums/bolt-actions.enum.ts b/app-nest/src/bolt/enums/bolt-actions.enum.ts index 4fc5dfc..109835f 100644 --- a/app-nest/src/bolt/enums/bolt-actions.enum.ts +++ b/app-nest/src/bolt/enums/bolt-actions.enum.ts @@ -1,6 +1,7 @@ enum BoltActions { SYNC_USERS = "sync_users", REGISTER_PRESENCE = "register_presence", + SELECT_OFFICE_FOR_DATE = "select_office_for_date", } export default BoltActions; diff --git a/app-nest/src/entities/presence/presence.controller.ts b/app-nest/src/entities/presence/presence.controller.ts index 6a73d15..9c6eca2 100644 --- a/app-nest/src/entities/presence/presence.controller.ts +++ b/app-nest/src/entities/presence/presence.controller.ts @@ -20,4 +20,15 @@ export class PresenceController { date, }); } + + @BoltAction(BoltActions.SELECT_OFFICE_FOR_DATE) + async selectOfficeForDate({ ack, body, payload }: BoltActionArgs) { + await ack(); + const { value, date } = JSON.parse(payload["selected_option"].value); + await this.presenceService.upsert({ + userId: body.user.id, + date: dayjs(date).toDate(), + office: value, + }); + } } diff --git a/app-nest/src/entities/presence/presence.entity.ts b/app-nest/src/entities/presence/presence.entity.ts index 028e15c..26d2dcb 100644 --- a/app-nest/src/entities/presence/presence.entity.ts +++ b/app-nest/src/entities/presence/presence.entity.ts @@ -13,8 +13,11 @@ export class Presence { @PrimaryColumn({ type: "date" }) date: Date; - @Column({ type: "enum", enum: PresenceType }) - type: PresenceType; + @Column({ type: "enum", enum: PresenceType, nullable: true }) + type: PresenceType | null; + + @Column({ nullable: true }) + office: string | null; } export type PresenceRepository = Repository; diff --git a/app-nest/src/entities/presence/presence.service.ts b/app-nest/src/entities/presence/presence.service.ts index 09850e1..6c3ae5c 100644 --- a/app-nest/src/entities/presence/presence.service.ts +++ b/app-nest/src/entities/presence/presence.service.ts @@ -10,13 +10,20 @@ export class PresenceService { private dataSource: DataSource, ) {} - async upsert(presence: Presence) { + async upsert(presence: Partial) { + // Select only existing cols for the upsert operation to avoid overriding + // existing data with defaults/nulls. + const primaryKeys = ["userId", "date"]; + const updatableCols = Object.keys(presence).filter( + (key) => !primaryKeys.includes(key), + ); + return this.dataSource .createQueryBuilder() .insert() .into(Presence) .values(presence) - .orUpdate(["type"], ["userId", "date"]) + .orUpdate(updatableCols, primaryKeys) .execute(); } } diff --git a/app-nest/src/gui/tabs/home/day-list-item.blocks.ts b/app-nest/src/gui/tabs/home/day-list-item.blocks.ts index 6b728f4..1f6d01b 100644 --- a/app-nest/src/gui/tabs/home/day-list-item.blocks.ts +++ b/app-nest/src/gui/tabs/home/day-list-item.blocks.ts @@ -34,7 +34,7 @@ const getDayListItemBlocks = ({ date }: DayListItemProps) => [ }, }, { - action_id: "text1234", + action_id: BoltActions.SELECT_OFFICE_FOR_DATE, type: "static_select", placeholder: { type: "plain_text", @@ -45,7 +45,7 @@ const getDayListItemBlocks = ({ date }: DayListItemProps) => [ type: "plain_text", text: "Helsinki", }, - value: "hki", + value: JSON.stringify({ value: "hki", date: date.toISOString() }), }, options: [ { @@ -53,14 +53,14 @@ const getDayListItemBlocks = ({ date }: DayListItemProps) => [ type: "plain_text", text: "Helsinki", }, - value: "hki", + value: JSON.stringify({ value: "hki", date: date.toISOString() }), }, { text: { type: "plain_text", text: "Tampere", }, - value: "tre", + value: JSON.stringify({ value: "tre", date: date.toISOString() }), }, ], },