-
Notifications
You must be signed in to change notification settings - Fork 4
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: Call LearningAssistantSummary endpoint #68
Changes from 6 commits
c702ca1
0e65fc3
f238e09
75dfdb7
4cdc186
5c3b5cf
6a4a2aa
3625ed2
9199c92
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,7 +1,7 @@ | ||
/* eslint-disable no-import-assign */ | ||
import * as auth from '@edx/frontend-platform/auth'; | ||
|
||
import { fetchLearningAssistantMessageHistory } from './api'; | ||
import { fetchLearningAssistantSummary } from './api'; | ||
|
||
jest.mock('@edx/frontend-platform/auth'); | ||
|
||
|
@@ -16,38 +16,45 @@ describe('API', () => { | |
jest.restoreAllMocks(); | ||
}); | ||
|
||
describe('fetchLearningAssistantMessageHistory()', () => { | ||
const fakeCourseId = 'course-v1:edx+test+23'; | ||
const apiPayload = [ | ||
{ | ||
role: 'user', | ||
content: 'Marco', | ||
timestamp: '2024-11-04T19:05:07.403363Z', | ||
describe('fetchLearningAssistantSummary()', () => { | ||
const courseId = 'course-v1:edx+test+23'; | ||
const apiPayload = { | ||
enabled: true, | ||
message_history: [ | ||
{ | ||
role: 'user', | ||
content: 'Marco', | ||
timestamp: '2024-11-04T19:05:07.403363Z', | ||
}, | ||
{ | ||
role: 'assistant', | ||
content: 'Polo', | ||
timestamp: '2024-11-04T19:05:21.357636Z', | ||
}, | ||
], | ||
audit_trial: { | ||
start_date: '2024-12-02T14:59:16.148236Z', | ||
expiration_date: '9999-12-16T14:59:16.148236Z', | ||
}, | ||
{ | ||
role: 'assistant', | ||
content: 'Polo', | ||
timestamp: '2024-11-04T19:05:21.357636Z', | ||
}, | ||
]; | ||
}; | ||
|
||
const fakeGet = jest.fn(async () => ({ | ||
const mockGet = jest.fn(async () => ({ | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nice renaming! |
||
data: apiPayload, | ||
catch: () => {}, | ||
catch: () => { }, | ||
})); | ||
|
||
beforeEach(() => { | ||
auth.getAuthenticatedHttpClient = jest.fn(() => ({ | ||
get: fakeGet, | ||
get: mockGet, | ||
})); | ||
}); | ||
|
||
it('should call the endpoint and process the results', async () => { | ||
const response = await fetchLearningAssistantMessageHistory(fakeCourseId); | ||
const response = await fetchLearningAssistantSummary(courseId); | ||
|
||
expect(response).toEqual(apiPayload); | ||
expect(fakeGet).toHaveBeenCalledTimes(1); | ||
expect(fakeGet).toHaveBeenCalledWith(`${CHAT_RESPONSE_URL}/${fakeCourseId}/history`); | ||
expect(mockGet).toHaveBeenCalledTimes(1); | ||
expect(mockGet).toHaveBeenCalledWith(`${CHAT_RESPONSE_URL}/${courseId}/summary`); | ||
}); | ||
}); | ||
}); |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -11,6 +11,10 @@ export const initialState = { | |
disclosureAcknowledged: false, | ||
sidebarIsOpen: false, | ||
isEnabled: false, | ||
auditTrial: { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Shouldn't the initial state be |
||
startDate: null, | ||
expirationDate: null, | ||
}, | ||
}; | ||
|
||
export const learningAssistantSlice = createSlice({ | ||
|
@@ -44,6 +48,9 @@ export const learningAssistantSlice = createSlice({ | |
setIsEnabled: (state, { payload }) => { | ||
state.isEnabled = payload; | ||
}, | ||
setAuditTrial: (state, { payload }) => { | ||
state.auditTrial = payload; | ||
}, | ||
}, | ||
}); | ||
|
||
|
@@ -57,6 +64,7 @@ export const { | |
setDisclosureAcknowledged, | ||
setSidebarIsOpen, | ||
setIsEnabled, | ||
setAuditTrial, | ||
} = learningAssistantSlice.actions; | ||
|
||
export const { | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -2,7 +2,10 @@ import { sendTrackEvent } from '@edx/frontend-platform/analytics'; | |
import { getAuthenticatedUser } from '@edx/frontend-platform/auth'; | ||
|
||
import trackChatBotMessageOptimizely from '../utils/optimizelyExperiment'; | ||
import { fetchChatResponse, fetchLearningAssistantMessageHistory, fetchLearningAssistantEnabled } from './api'; | ||
import { | ||
fetchChatResponse, | ||
fetchLearningAssistantSummary, | ||
} from './api'; | ||
import { | ||
setCurrentMessage, | ||
clearCurrentMessage, | ||
|
@@ -13,6 +16,7 @@ import { | |
setDisclosureAcknowledged, | ||
setSidebarIsOpen, | ||
setIsEnabled, | ||
setAuditTrial, | ||
} from './slice'; | ||
import { OPTIMIZELY_PROMPT_EXPERIMENT_KEY } from './optimizely'; | ||
|
||
|
@@ -73,33 +77,6 @@ export function getChatResponse(courseId, unitId, promptExperimentVariationKey = | |
}; | ||
} | ||
|
||
export function getLearningAssistantMessageHistory(courseId) { | ||
return async (dispatch) => { | ||
dispatch(setApiIsLoading(true)); | ||
|
||
try { | ||
const rawMessageList = await fetchLearningAssistantMessageHistory(courseId); | ||
|
||
if (rawMessageList.length) { | ||
const messageList = rawMessageList | ||
.map(({ timestamp, ...msg }) => ({ | ||
...msg, | ||
timestamp: new Date(timestamp), // Parse ISO time to Date() | ||
})); | ||
|
||
dispatch(setMessageList({ messageList })); | ||
|
||
// If it has chat history, then we assume the user already aknowledged. | ||
dispatch(setDisclosureAcknowledged(true)); | ||
} | ||
} catch (e) { | ||
// If fetching the messages fail, we just won't show it. | ||
} | ||
|
||
dispatch(setApiIsLoading(false)); | ||
}; | ||
} | ||
|
||
export function updateCurrentMessage(content) { | ||
return (dispatch) => { | ||
dispatch(setCurrentMessage({ currentMessage: content })); | ||
|
@@ -124,13 +101,46 @@ export function updateSidebarIsOpen(isOpen) { | |
}; | ||
} | ||
|
||
export function getIsEnabled(courseId) { | ||
export function getLearningAssistantSummary(courseId) { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I replaced the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nit: Could you rename this to |
||
return async (dispatch) => { | ||
dispatch(setApiIsLoading(true)); | ||
|
||
try { | ||
const data = await fetchLearningAssistantEnabled(courseId); | ||
const data = await fetchLearningAssistantSummary(courseId); | ||
|
||
// Enabled | ||
dispatch(setIsEnabled(data.enabled)); | ||
|
||
// Message History | ||
const rawMessageList = data.message_history; | ||
|
||
// If returned message history data is not empty | ||
if (rawMessageList.length) { | ||
const messageList = rawMessageList | ||
.map(({ timestamp, ...msg }) => ({ | ||
...msg, | ||
// NOTE to self: can't store Date() objects in store: https://github.com/reduxjs/redux-toolkit/issues/456 | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Question: would you just store as a string then and parse when needed? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Oh wait, that's what you're doing! My bad. So you can probably remove this comment? |
||
timestamp: new Date(timestamp).toString(), // Parse ISO time to Date() | ||
})); | ||
|
||
dispatch(setMessageList({ messageList })); | ||
|
||
// If it has chat history, then we assume the user already aknowledged. | ||
dispatch(setDisclosureAcknowledged(true)); | ||
} | ||
|
||
// Audit Trial | ||
const auditTrial = data.audit_trial; | ||
|
||
// If returned audit trial data is not empty | ||
if (Object.keys(auditTrial).length !== 0) { // eslint-disable-line no-undef | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What was the issue with There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. If There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Oh that's an artifact from when I was using lodash, I'll get rid of this |
||
dispatch(setAuditTrial(auditTrial)); | ||
} | ||
} catch (error) { | ||
// NOTE: When used to not show if fetching the messages failed | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Can you clarify what this comment means? I'm not following. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I meant to use "we" instead of "when", but also I don't think this comment is necessary so I'm removing it. |
||
// But we do know since this endpoint is combined. | ||
dispatch(setApiError()); | ||
} | ||
dispatch(setApiIsLoading(false)); | ||
}; | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
NOTE: This Ticket/PR has been modified such that we're now calling the "summary" endpoint that Michael is working on in his PR: edx/learning-assistant#140.
This endpoint gets all the data for
enabled
,message_history
, andaudit_trial
all in one GET request.