feat: add call duration

This commit is contained in:
Muhsin
2026-03-12 15:07:40 +04:00
parent fac4675dc5
commit e4f9355352
7 changed files with 79 additions and 7 deletions
@@ -77,4 +77,15 @@ describe('VoiceCall.vue', () => {
expect(wrapper.text()).toContain('You answered');
});
it('shows the formatted duration when a call has ended', () => {
messageContext.contentAttributes.value.data.status =
VOICE_CALL_STATUS.COMPLETED;
messageContext.contentAttributes.value.data.meta.duration = 133;
const wrapper = mountComponent();
expect(wrapper.text()).toContain('Call ended');
expect(wrapper.text()).toContain('02:13');
});
});
@@ -3,6 +3,7 @@ import { computed } from 'vue';
import { useI18n } from 'vue-i18n';
import { useMessageContext } from '../provider.js';
import { MESSAGE_TYPES, VOICE_CALL_STATUS } from '../constants';
import { formatDuration } from 'shared/helpers/timeHelper';
import Icon from 'dashboard/components-next/icon/Icon.vue';
import BaseBubble from 'next/message/bubbles/Base.vue';
@@ -29,6 +30,9 @@ const status = computed(() => data.value?.status?.toString());
const joinedBy = computed(() => {
return data.value?.meta?.joinedBy || data.value?.meta?.joined_by;
});
const callDuration = computed(() => {
return data.value?.meta?.duration;
});
const isOutbound = computed(() => messageType.value === MESSAGE_TYPES.OUTGOING);
const isFailed = computed(() =>
@@ -64,7 +68,10 @@ const subtext = computed(() => {
}
if (status.value === VOICE_CALL_STATUS.COMPLETED) {
return t('CONVERSATION.VOICE_CALL.CALL_ENDED');
return (
formatDuration(callDuration.value) ||
t('CONVERSATION.VOICE_CALL.CALL_ENDED')
);
}
if (status.value === VOICE_CALL_STATUS.IN_PROGRESS) {
@@ -5,6 +5,7 @@ import TwilioVoiceClient from 'dashboard/api/channel/voice/twilioVoiceClient';
import { useAlert } from 'dashboard/composables';
import { useCallsStore } from 'dashboard/stores/calls';
import Timer from 'dashboard/helper/Timer';
import { formatDuration } from 'shared/helpers/timeHelper';
export function useCallSession() {
const callsStore = useCallsStore();
@@ -98,9 +99,7 @@ export function useCallSession() {
};
const formattedCallDuration = computed(() => {
const minutes = Math.floor(callDuration.value / 60);
const seconds = callDuration.value % 60;
return `${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`;
return formatDuration(callDuration.value);
});
return {
@@ -4,6 +4,7 @@ import {
dynamicTime,
dateFormat,
shortTimestamp,
formatDuration,
getDayDifferenceFromNow,
hasOneDayPassed,
} from 'shared/helpers/timeHelper';
@@ -93,6 +94,24 @@ describe('#shortTimestamp', () => {
});
});
describe('#formatDuration', () => {
it('returns empty string for invalid values', () => {
expect(formatDuration(null)).toEqual('');
expect(formatDuration(undefined)).toEqual('');
expect(formatDuration(-1)).toEqual('');
expect(formatDuration('abc')).toEqual('');
});
it('formats short durations as mm:ss', () => {
expect(formatDuration(0)).toEqual('00:00');
expect(formatDuration(133)).toEqual('02:13');
});
it('formats long durations as hh:mm:ss', () => {
expect(formatDuration(3733)).toEqual('01:02:13');
});
});
describe('#getDayDifferenceFromNow', () => {
it('returns 0 for timestamps from today', () => {
// Mock current date: May 5, 2023
@@ -93,6 +93,32 @@ export const shortTimestamp = (time, withAgo = false) => {
return convertToShortTime;
};
/**
* Formats a duration in seconds into mm:ss or hh:mm:ss.
* @param {number|string} durationInSeconds - Duration in seconds.
* @returns {string} Formatted duration string.
*/
export const formatDuration = durationInSeconds => {
if (durationInSeconds === null || durationInSeconds === undefined) return '';
const totalSeconds = Number(durationInSeconds);
if (Number.isNaN(totalSeconds) || totalSeconds < 0) return '';
const hours = Math.floor(totalSeconds / 3600);
const minutes = Math.floor((totalSeconds % 3600) / 60);
const seconds = totalSeconds % 60;
if (hours > 0) {
return `${hours.toString().padStart(2, '0')}:${minutes
.toString()
.padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`;
}
return `${minutes.toString().padStart(2, '0')}:${seconds
.toString()
.padStart(2, '0')}`;
};
/**
* Calculates the difference in days between now and a given timestamp.
* @param {Date} now - Current date/time.