Merge branch 'master' of http://82.157.175.59:3000/GenarrativeAI/Genarrative
Some checks failed
CI / verify (push) Has been cancelled

This commit is contained in:
2026-05-08 22:12:10 +08:00
38 changed files with 1515 additions and 135 deletions

View File

@@ -9,6 +9,7 @@ import {
listRpgProfileBrowseHistory,
listRpgProfileSaveArchives,
resumeRpgProfileSaveArchive,
submitRpgProfileFeedback,
syncRpgProfileBrowseHistory,
upsertRpgProfileBrowseHistory,
} from './rpgProfileClient';
@@ -156,3 +157,59 @@ describe('rpgProfileClient save archive routes', () => {
);
});
});
describe('rpgProfileClient feedback routes', () => {
beforeEach(() => {
requestJsonMock.mockReset();
requestJsonMock.mockResolvedValue({
feedback: {
feedbackId: 'feedback:user-1:1',
status: 'open',
createdAt: '2026-05-08T10:00:00Z',
evidenceItems: [],
},
});
});
it('submits profile feedback through the profile route', async () => {
await submitRpgProfileFeedback({
description: '图片上传后没有展示预览',
contactPhone: null,
evidenceItems: [
{
fileName: 'preview.png',
contentType: 'image/png',
sizeBytes: 128,
dataUrl: 'data:image/png;base64,ZmVlZGJhY2s=',
},
],
});
expect(requestJsonMock).toHaveBeenCalledWith(
'/api/profile/feedback',
expect.objectContaining({
method: 'POST',
headers: { 'Content-Type': 'application/json' },
}),
'提交反馈失败',
expect.objectContaining({
retry: expect.objectContaining({
maxRetries: 1,
retryUnsafeMethods: true,
}),
}),
);
expect(JSON.parse(requestJsonMock.mock.calls[0][1].body)).toEqual({
description: '图片上传后没有展示预览',
contactPhone: null,
evidenceItems: [
{
fileName: 'preview.png',
contentType: 'image/png',
sizeBytes: 128,
dataUrl: 'data:image/png;base64,ZmVlZGJhY2s=',
},
],
});
});
});

View File

@@ -15,6 +15,8 @@ import type {
RedeemProfileReferralInviteCodeResponse,
RedeemProfileRewardCodeResponse,
RuntimeSettings,
SubmitProfileFeedbackRequest,
SubmitProfileFeedbackResponse,
} from '../../../packages/shared/src/contracts/runtime';
import { rehydrateSavedSnapshot } from '../../persistence/runtimeSnapshot';
import type { HydratedSavedGameSnapshot } from '../../persistence/runtimeSnapshotTypes';
@@ -101,6 +103,22 @@ export function createRpgProfileRechargeOrder(
);
}
export function submitRpgProfileFeedback(
payload: SubmitProfileFeedbackRequest,
options: RuntimeRequestOptions = {},
) {
return requestRpgRuntimeJson<SubmitProfileFeedbackResponse>(
'/profile/feedback',
{
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(payload),
},
'提交反馈失败',
options,
);
}
export function getRpgProfileReferralInviteCenter(
options: RuntimeRequestOptions = {},
) {
@@ -276,6 +294,7 @@ export const rpgProfileClient = {
getWalletLedger: getRpgProfileWalletLedger,
getRechargeCenter: getRpgProfileRechargeCenter,
createRechargeOrder: createRpgProfileRechargeOrder,
submitFeedback: submitRpgProfileFeedback,
getReferralInviteCenter: getRpgProfileReferralInviteCenter,
redeemReferralInviteCode: redeemRpgProfileReferralInviteCode,
getTasks: getRpgProfileTasks,