Skip to content
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

[Data rearchitecture] Revert "Sync with master" #6118

Merged
merged 25 commits into from
Jan 14, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
60a9b26
Revert "Adheres to `prefer-promise-reject-errors` eslint rule"
gabina Jan 14, 2025
926d7d1
Revert "Fixes `uploads.json` endpoint returns `500 internal server er…
gabina Jan 14, 2025
587a3cc
Revert "Chore: Rename `enableMutationChecks` to `enableReduxSafetyChe…
gabina Jan 14, 2025
35c2194
Revert "Fix: Prevent state mutation in fetchRevisionsPromise function"
gabina Jan 14, 2025
6e0cbe0
Revert "Localisation updates from https://translatewiki.net."
gabina Jan 14, 2025
a4f2093
Revert "Remove debugging line"
gabina Jan 14, 2025
3638657
Revert "Ensure that PagePile Category records are unique by pileid"
gabina Jan 14, 2025
d4ddbef
Revert "Fix: Prevent "Preview Question Group" button from rendering e…
gabina Jan 14, 2025
a82d9fe
Revert "Added rapid: false parameter to textarea set method for slowe…
gabina Jan 14, 2025
847c851
Revert "extended workflow to save screenshot of failed Capybara tests…
gabina Jan 14, 2025
3234a7a
Revert "Delete unused components"
gabina Jan 14, 2025
482e06d
Revert "Fix typos in training markup, add script for making a trainin…
gabina Jan 14, 2025
b4eb122
Revert "Localisation updates from https://translatewiki.net."
gabina Jan 14, 2025
a9d722c
Revert "fix: Replaced static error count with dynamically generated e…
gabina Jan 14, 2025
3870e5a
Revert "@fix: stubbed api request and updated test for LiftWing, refe…
gabina Jan 14, 2025
e01bf47
Revert "Send reminder email to new non-instructors who complete onboa…
gabina Jan 14, 2025
400f7a3
Revert "fix: update slide removal logic for conditional survey questi…
gabina Jan 14, 2025
86ee2c0
Revert "fix: marked flaky test in multiwiki_assignment_spec as pending"
gabina Jan 14, 2025
99e8ce7
Revert "refactor remaining violations"
gabina Jan 14, 2025
82179d5
Revert "Update dependency documentation"
gabina Jan 14, 2025
893be7f
Revert "Change threshold for ContinuedCourseActivityAlert"
gabina Jan 14, 2025
2c25fbe
Revert "Adds guard statements to prevent `NoMethodError`s when `get_u…
gabina Jan 14, 2025
7719e5e
Revert "fix guard clause violations"
gabina Jan 14, 2025
aea8df0
Revert "added script info in docker docs"
gabina Jan 14, 2025
a818182
Revert "added script to update hosts for Database Connection Issue Wh…
gabina Jan 14, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 0 additions & 8 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -81,14 +81,6 @@ jobs:
coverageCommand: bundle exec rspec spec/ --color --profile --format documentation
coverageLocations: |
${{github.workspace}}/public/js_coverage/lcov.info:lcov

- name: Archive capybara failure screenshots
uses: actions/upload-artifact@v4
if: failure()
with:
name: dist-without-markdown
path: tmp/capybara/*.png
if-no-files-found: ignore

- name: Ruby linting
run: bundle exec rubocop
2 changes: 2 additions & 0 deletions .rubocop.yml
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,8 @@ Rails/FilePath:
Enabled: false
Performance/UnfreezeString:
Enabled: false
Style/GuardClause:
Enabled: false
Rails/HasManyOrHasOneDependent:
Enabled: false
Rails/InverseOf:
Expand Down
14 changes: 4 additions & 10 deletions app/assets/javascripts/actions/revisions_actions.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@

import {
RECEIVE_REVISIONS,
REVISIONS_LOADING,
Expand Down Expand Up @@ -34,19 +35,12 @@ const fetchAllArticles = async (course) => {

const fetchRevisionsPromise = async (course, users, last_date, dispatch) => {
const { revisions, last_date: new_last_date } = await fetchRevisionsFromUsers(course, users, 7, last_date);
course.revisions = sortRevisionsByDate(revisions);

// Create a new course object with updated revisions
const updatedCourse = {
...course,
revisions: sortRevisionsByDate(revisions),
};

// we don't await this. When the assessments/references get loaded, the action is dispatched
// we don't await this. When the assessments/references get laoded, the action is dispatched
fetchRevisionsAndReferences(revisions, dispatch);

return { course: updatedCourse, last_date: new_last_date };
return { course, last_date: new_last_date };
};

const fetchRevisionsCourseSpecificPromise = async (course, users, last_date, dispatch, articles) => {
const trackedArticles = new Set(
articles.filter(article => article.tracked).map(article => article.title)
Expand Down
27 changes: 9 additions & 18 deletions app/assets/javascripts/actions/uploads_actions.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,34 +10,25 @@ const fetchUploads = (courseId) => {
if (res.ok && res.status === 200) {
return res.json();
}
return Promise.reject(new Error(`Failed to fetch uploads. Status: ${res.status}`));
return Promise.reject(res);
})
.catch((error) => {
logErrorMessage(error);
return { error: 'Failed to fetch uploads', status: error.status || 500 };
});
};

export const receiveUploads = courseId => (dispatch) => {
return fetchUploads(courseId)
.then((resp) => {
if (!resp) {
return dispatch({
type: API_FAIL,
data: { error: 'No response received' },
});
}
return dispatch({
return (
fetchUploads(courseId)
.then(resp => dispatch({
type: RECEIVE_UPLOADS,
data: resp,
});
})
.catch((resp) => {
dispatch({
}))
.catch(resp => dispatch({
type: API_FAIL,
data: resp,
});
});
data: resp
}))
);
};

const fetchUploadMetadata = (uploads) => {
Expand Down
123 changes: 123 additions & 0 deletions app/assets/javascripts/components/activity/activity_table.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
import React from 'react';
import PropTypes from 'prop-types';
import { useSelector } from 'react-redux';
import { flatten, zip } from 'lodash-es';
import { formatDateWithTime } from '../../utils/date_utils';
import ActivityTableRow from './activity_table_row.jsx';
import Loading from '../common/loading.jsx';

const ActivityTable = ({ onSort, activity, headers, loading, noActivityMessage }) => {
const openKey = useSelector(state => state.ui.openKey);

const sortItems = (e) => {
onSort(e.currentTarget.getAttribute('data-sort-key'));
};

const _renderActivites = () => {
return activity.map((revision) => {
const roundedRevisionScore = Math.round(revision.revision_score) || 'unknown';
const revisionDateTime = formatDateWithTime(revision.datetime);
const talkPageLink = `${revision.base_url}/wiki/User_talk:${revision.username}`;
const isOpen = openKey === `drawer_${revision.key}`;

return (
<ActivityTableRow
revision={revision}
key={revision.key}
rowId={revision.key}
articleUrl={revision.article_url}
diffUrl={revision.diff_url}
talkPageLink={talkPageLink}
reportUrl={revision.report_url}
title={revision.title}
revisionScore={roundedRevisionScore}
author={revision.username}
revisionDateTime={revisionDateTime}
isOpen={isOpen}
/>
);
});
};

const _renderDrawers = () => {
return activity.map((revision) => {
const courses = revision.courses.map((course) => {
return (
<li key={`${revision.key}-${course.slug}`}>
<a href={`/courses/${course.slug}`}>{course.title}</a>
</li>
);
});

return (
<tr key={`${revision.key}-${revision.username}`} className="activity-table-drawer drawer">
<td colSpan="5">
<span />
<table className="table">
<tbody>
<tr>
<td>
<span>
<h5>{I18n.t('recent_activity.active_courses')}</h5>
<ul className="activity-table__course-list">
{courses}
</ul>
</span>
</td>
</tr>
</tbody>
</table>
</td>
</tr>
);
});
};

const _renderHeaders = () => {
return headers.map((header) => {
return (
<th style={header.style || {}} key={header.key} onClick={sortItems} className="sortable asc" data-sort-key={header.key}>
{header.title}
<span className="sortable-indicator" />
</th>
);
});
};

if (loading) {
return <Loading />;
}

const renderedActivity = _renderActivites();
const drawers = _renderDrawers();
const ths = _renderHeaders();

let elements = flatten(zip(renderedActivity, drawers));
if (!elements.length) {
elements = <tr><td colSpan={headers.length + 1}>{noActivityMessage}</td></tr>;
}

return (
<table className="table table--expandable table--hoverable table--clickable table--sortable activity-table">
<thead>
<tr>
{ths}
<th />
</tr>
</thead>
<tbody>
{elements}
</tbody>
</table>
);
};

ActivityTable.propTypes = {
loading: PropTypes.bool,
activity: PropTypes.array,
headers: PropTypes.array,
noActivityMessage: PropTypes.string,
toggleDrawer: PropTypes.func
};

export default (ActivityTable);
83 changes: 83 additions & 0 deletions app/assets/javascripts/components/activity/activity_table_row.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
import React from 'react';
import PropTypes from 'prop-types';
import DiffViewer from '../revisions/diff_viewer.jsx';
import { toggleUI } from '../../actions';
import { useDispatch } from 'react-redux';

const ActivityTableRow = ({ isOpen, diffUrl, revisionDateTime,
revisionScore, reportUrl, revision, rowId, articleUrl, title, talkPageLink,
author }) => {
const dispatch = useDispatch();

const openDrawer = () => {
return dispatch(toggleUI(`drawer_${rowId}`));
};

let revDateElement;
let col2;
const className = isOpen ? 'open' : 'closed';

if (diffUrl) {
revDateElement = (
<a href={diffUrl} target="_blank">{revisionDateTime}</a>
);
}

if (revisionScore) {
col2 = (
<td>
{revisionScore}
</td>
);
}

if (reportUrl) {
col2 = (
<td>
<a href={reportUrl} target="_blank">{I18n.t('recent_activity.report')}</a>
</td>
);
}

let diffViewer;
if (revision && revision.api_url) {
diffViewer = <DiffViewer revision={revision} />;
}

return (
<tr className={className} key={rowId}>
<td onClick={openDrawer}>
<a href={articleUrl} target="_blank">{title}</a>
</td>
{col2}
<td onClick={openDrawer}>
<a href={talkPageLink} target="_blank">{author}</a>
</td>
<td onClick={openDrawer}>
{revDateElement}
</td>
<td>
{diffViewer}
</td>
</tr>
);
};

ActivityTableRow.propTypes = {
rowId: PropTypes.number,
diffUrl: PropTypes.string,
revisionDateTime: PropTypes.string,
reportUrl: PropTypes.string,
revisionScore: PropTypes.oneOfType([
PropTypes.string,
PropTypes.number
]),
articleUrl: PropTypes.string,
talkPageLink: PropTypes.string,
author: PropTypes.string,
title: PropTypes.string,
revision: PropTypes.object,
isOpen: PropTypes.bool,
};

export default ActivityTableRow;
10 changes: 5 additions & 5 deletions app/assets/javascripts/components/util/create_store.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,8 @@ export const getStore = () => {
};
}

// Determine if Redux Toolkit's safety checks should be enabled
const enableReduxSafetyChecks = false;
// Determine if mutation checks should be enabled
const enableMutationChecks = false;

const store = configureStore({
reducer,
Expand All @@ -39,9 +39,9 @@ export const getStore = () => {
getDefaultMiddleware({
// Temporarily disable mutation checks feature to facilitate Redux Toolkit migration.
// TODO: Gradually resolve state mutations and re-enable these checks in the future.
// Enable mutation checks when resolving or detecting these issues by setting enableReduxSafetyChecks to true.
immutableCheck: enableReduxSafetyChecks,
serializableCheck: enableReduxSafetyChecks,
// Enable mutation checks when resolving or detecting these issues by setting enableMutationChecks to true.
immutableCheck: enableMutationChecks,
serializableCheck: enableMutationChecks,
}),
});

Expand Down
2 changes: 1 addition & 1 deletion app/assets/javascripts/reducers/uploads.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ const SORT_DESCENDING = {
export default function uploads(state = initialState, action) {
switch (action.type) {
case RECEIVE_UPLOADS: {
const dataUploads = action.data?.course?.uploads || [];
const dataUploads = action.data.course.uploads;
// Intial sorting by upload date
const sortedModel = sortByKey(dataUploads, 'uploaded_at', state.sortKey, SORT_DESCENDING.uploaded_at);

Expand Down
Loading
Loading