[AI assisted]: Improve system console statistics performance (#29899)

```release-note
NONE
```

Co-authored-by: Matthew Birtch <mattbirtch@gmail.com>
Этот коммит содержится в:
Agniva De Sarker
2025-02-04 21:54:01 +05:30
коммит произвёл GitHub
родитель 6046a304b2
Коммит ae9e6174e5
45 изменённых файлов: 1052 добавлений и 407 удалений

Просмотреть файл

@@ -128,25 +128,30 @@ describe('System Console > Site Statistics', () => {
cy.visit('/admin_console');
cy.wait('@resources');
// * Find site statistics and click it
cy.findByTestId('reporting.system_analytics', {timeout: TIMEOUTS.ONE_MIN}).click();
cy.dbRefreshPostStats().then(() => {
// * Find site statistics and click it
cy.findByTestId('reporting.system_analytics', {timeout: TIMEOUTS.ONE_MIN}).click();
let totalPostsDataSet;
let totalPostsFromBots;
let activeUsersWithPosts;
// * Expand the details
cy.findByTestId('details-expander', {timeout: TIMEOUTS.ONE_MIN}).click();
// # Grab all data from the 3 charts from there data labels
cy.findByTestId('totalPostsLineChart').then((el) => {
totalPostsDataSet = el[0].dataset.labels;
cy.findByTestId('totalPostsFromBotsLineChart').then((el2) => {
totalPostsFromBots = el2[0].dataset.labels;
cy.findByTestId('activeUsersWithPostsLineChart').then((el3) => {
activeUsersWithPosts = el3[0].dataset.labels;
let totalPostsDataSet;
let totalPostsFromBots;
let activeUsersWithPosts;
// * Assert that all the dates are the same
expect(totalPostsDataSet).equal(totalPostsFromBots);
expect(totalPostsDataSet).equal(activeUsersWithPosts);
expect(totalPostsFromBots).equal(activeUsersWithPosts);
// # Grab all data from the 3 charts from there data labels
cy.findByTestId('totalPostsLineChart').then((el) => {
totalPostsDataSet = el[0].dataset.labels;
cy.findByTestId('totalPostsFromBotsLineChart').then((el2) => {
totalPostsFromBots = el2[0].dataset.labels;
cy.findByTestId('activeUsersWithPostsLineChart').then((el3) => {
activeUsersWithPosts = el3[0].dataset.labels;
// * Assert that all the dates are the same
expect(totalPostsDataSet).equal(totalPostsFromBots);
expect(totalPostsDataSet).equal(activeUsersWithPosts);
expect(totalPostsFromBots).equal(activeUsersWithPosts);
});
});
});
});

Просмотреть файл

@@ -19,14 +19,16 @@ describe('System Console > Team Statistics', () => {
// # Create private channel.
cy.apiCreateChannel(team.id, 'mmt906-ch', 'mmt906-ch', 'P');
// # Visit team statistics page.
cy.visit('/admin_console/reporting/team_statistics');
cy.dbRefreshPostStats().then(() => {
// # Visit team statistics page.
cy.visit('/admin_console/reporting/team_statistics');
// # Select created team.
cy.get('select.team-statistics__team-filter__dropdown').select(team.id);
// # Select created team.
cy.get('select.team-statistics__team-filter__dropdown').select(team.id);
// # Explicit wait to allow stats to get loaded
cy.wait(TIMEOUTS.TWO_SEC);
// # Explicit wait to allow stats to get loaded
cy.wait(TIMEOUTS.TWO_SEC);
});
});
});

Просмотреть файл

@@ -127,9 +127,36 @@ function toLowerCase(config, name) {
return name.toLowerCase();
}
const dbRefreshPostStats = async ({dbConfig}) => {
if (!knexClient) {
knexClient = getKnexClient(dbConfig);
}
// Only run for PostgreSQL
if (dbConfig.client !== 'postgres') {
return {
skipped: true,
message: 'Refresh post stats is only supported for PostgreSQL',
};
}
try {
await knexClient.raw('REFRESH MATERIALIZED VIEW posts_by_team_day;');
await knexClient.raw('REFRESH MATERIALIZED VIEW bot_posts_by_team_day;');
return {
success: true,
};
} catch (error) {
const errorMessage = 'Failed to refresh post statistics materialized views.';
return {error, errorMessage};
}
};
module.exports = {
dbGetActiveUserSessions,
dbGetUser,
dbGetUserSession,
dbUpdateUserSession,
dbRefreshPostStats,
};

Просмотреть файл

@@ -11,6 +11,7 @@ const {
dbGetUser,
dbGetUserSession,
dbUpdateUserSession,
dbRefreshPostStats,
} = require('./db_request');
const externalRequest = require('./external_request').default;
const {fileExist, writeToFile} = require('./file_util');
@@ -42,6 +43,7 @@ module.exports = (on, config) => {
dbGetUser,
dbGetUserSession,
dbUpdateUserSession,
dbRefreshPostStats,
externalRequest,
fileExist,
writeToFile,

Просмотреть файл

@@ -96,6 +96,14 @@ function dbUpdateUserSession(params: UpdateUserSessionParam): ChainableT<UpdateU
}
Cypress.Commands.add('dbUpdateUserSession', dbUpdateUserSession);
function dbRefreshPostStats(): ChainableT<{success?: boolean; skipped?: boolean; message?: string}> {
return cy.task('dbRefreshPostStats', {dbConfig}).then(({success, skipped, message, errorMessage, error}) => {
verifyError(error, errorMessage);
return cy.wrap({success, skipped, message});
});
}
Cypress.Commands.add('dbRefreshPostStats', dbRefreshPostStats);
function verifyError(error, errorMessage) {
if (errorMessage) {
expect(errorMessage, `${errorMessage}\n\n${message}\n\n${JSON.stringify(error)}`).to.be.undefined;
@@ -150,6 +158,15 @@ declare global {
* @returns {Session} session
*/
dbUpdateUserSession: typeof dbUpdateUserSession;
/**
* Refreshes PostgreSQL materialized views for post statistics
* @returns {Object} result
* @returns {boolean} result.success - true if refresh was successful
* @returns {boolean} result.skipped - true if operation was skipped (non-PostgreSQL)
* @returns {string} result.message - message when operation is skipped
*/
dbRefreshPostStats: typeof dbRefreshPostStats;
}
}
}