Compare commits

...

40 Commits

Author SHA1 Message Date
edX requirements bot
ddb37580b7 chore: update browserslist DB (#272)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-03-16 00:21:05 +00:00
edX requirements bot
30dd3a0ece chore: update browserslist DB (#271)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-03-09 00:22:48 +00:00
edX requirements bot
bda9798951 chore: update browserslist DB (#270)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-03-02 00:30:12 +00:00
edX requirements bot
87e605cb23 chore: update browserslist DB (#269)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-02-23 21:04:02 +00:00
edX requirements bot
35b3de8311 chore: update browserslist DB (#268)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-02-16 00:22:34 +00:00
Brian Smith
0c2cf9511f fix(deps): regenerate package-lock.json (#265)
Co-authored-by: Claude Code <noreply@anthropic.com>
2026-02-13 17:25:07 -05:00
edX requirements bot
2d6aeb9662 chore: update browserslist DB (#266)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-02-09 00:18:38 +00:00
edX requirements bot
8b84cfdf27 chore: update browserslist DB (#264)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2026-01-26 00:14:35 +00:00
Anton Melser
6223212751 docs: updates for outdated references (#262)
* docs: Generify currently supported node version

* docs: include 'standard' dev instructions

---------

Co-authored-by: Feanil Patel <feanil@axim.org>
2026-01-23 18:36:33 +00:00
Feanil Patel
4a346328ef build: Update package-lock.json
The file was missing some dependent packages for some reason.
2026-01-23 15:28:58 -03:00
PKulkoRaccoonGang
5d19b93d98 fix: added raw loader for tinymce conten.css 2026-01-19 15:14:02 -03:00
edX requirements bot
42e75a6372 chore: update browserslist DB (#261)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-11-10 00:13:49 +00:00
edX requirements bot
ac5fa76c1e chore: update browserslist DB (#258)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-11-06 13:22:05 -05:00
Stanislav Lunyachek
7ddc95003e fix: Remove extra margin around body element 2025-09-30 12:16:04 -03:00
Muhammad Anas
fa05fa25ab chore: bump frontend-component-header to v6.6.x 2025-09-30 11:55:12 -03:00
oleksandr.buhaienko
26099ea6d5 test: Remove support for Node 20 2025-09-26 10:35:39 -03:00
Feanil Patel
59dbee3fa9 Merge pull request #256 from openedx/feanil/remove-reactifex-packages
build: remove unused @edx/reactifex package
2025-09-25 13:15:44 -04:00
Feanil Patel
1c9e20e6a7 fix: Correct test parameters.
This test should be suppling a `courseModes` parameter not a
`courseMode` parameter with a missing `s`.
2025-09-25 10:13:24 -04:00
Feanil Patel
4af3a5a65a build: remove unused @edx/reactifex package
Remove @edx/reactifex package from devDependencies as it is no longer
needed. Translation extraction functionality has been verified to work
correctly without this dependency.

Co-Authored-By: Claude <noreply@anthropic.com>
2025-09-25 10:13:18 -04:00
PKulkoRaccoonGang
b106d0694f fix: fixed some problems with tests 2025-09-25 10:55:05 -03:00
oleksandr.buhaienko
ef6c498bb7 build: Upgrade to Node 24 2025-09-25 10:55:05 -03:00
edX requirements bot
70a40bf90b chore: update browserslist DB (#255)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-09-22 00:13:18 +00:00
bydawen
7727574280 test: Add Node 24 to CI matrix (#252) 2025-09-19 13:50:59 -04:00
edX requirements bot
51b8d7bac1 chore: update browserslist DB (#251)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-09-08 00:13:07 +00:00
Samuel Allan
95a3eb4959 fix: update frontend-build to fix install issues (#250)
Earlier versions of @openedx/frontend-build used on older version of
'sharp', which caused intermittent installation issues. The version of
'sharp' was updated in @openedx/frontend-build to fix these issues, so
the frontend-build version can be updated here, to fix the issues in
this project too. See
https://github.com/openedx/frontend-build/issues/664 and
https://github.com/openedx/frontend-build/pull/665 for more information.

The frontend-build dependency was updated by:

```
npm install --package-lock-only @openedx/frontend-build
```

Private-ref: https://tasks.opencraft.com/browse/BB-9953
2025-09-05 12:03:05 -06:00
edX requirements bot
975ab436ae chore: update browserslist DB (#249)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-09-01 00:14:46 +00:00
edX requirements bot
64b259a8a9 chore: update browserslist DB (#248)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-08-25 00:13:19 +00:00
edX requirements bot
795636f7a7 chore: update browserslist DB (#247)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-08-18 00:14:21 +00:00
Jacobo Dominguez
f8e2b3de03 refactor: replacing injectIntl with useIntl part 1 (#245) 2025-08-13 13:03:13 -04:00
Jacobo Dominguez
b5e4505665 refactor: replacing injectIntl with useIntl part 2 (#246) 2025-08-13 10:51:53 -04:00
edX requirements bot
74905663e1 chore: update browserslist DB (#241)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-07-07 00:14:01 +00:00
edX requirements bot
a1083d8142 chore: update browserslist DB (#240)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-06-30 00:13:54 +00:00
Brian Smith
20ef9002ec feat!: add design tokens support (#224)
BREAKING CHANGE: Pre-design-tokens theming is no longer supported.

Co-authored-by: Diana Olarte <dcoa@live.com>
2025-06-18 15:36:53 -04:00
edX requirements bot
d2cb5b5e1d chore: update browserslist DB (#237)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-06-16 00:13:32 +00:00
edX requirements bot
cd73b9992f chore: update browserslist DB (#235)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-06-09 00:14:00 +00:00
edX requirements bot
dd99ad7c57 chore: update browserslist DB (#234)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-06-02 00:13:44 +00:00
Brian Smith
f6dfc7f6cc fix(deps): update dependency @edx/frontend-platform to v8.3.7 (#232) 2025-05-19 11:06:25 -04:00
edX requirements bot
c3d9b62944 chore: update browserslist DB (#231)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-05-19 00:13:27 +00:00
edX requirements bot
c0a6133e78 chore: update browserslist DB (#230)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-05-12 00:13:22 +00:00
edX requirements bot
d62aa1df5a chore: update browserslist DB (#229)
Co-authored-by: arbrandes <759355+arbrandes@users.noreply.github.com>
2025-05-05 00:13:21 +00:00
23 changed files with 5026 additions and 2321 deletions

2
.env
View File

@@ -21,3 +21,5 @@ USER_INFO_COOKIE_NAME=''
SCHEDULE_EMAIL_SECTION=''
APP_ID=''
MFE_CONFIG_API_URL=''
# Fallback in local style files
PARAGON_THEME_URLS={}

View File

@@ -22,3 +22,5 @@ USER_INFO_COOKIE_NAME='edx-user-info'
SCHEDULE_EMAIL_SECTION='true'
APP_ID=''
MFE_CONFIG_API_URL=''
# Fallback in local style files
PARAGON_THEME_URLS={}

View File

@@ -20,3 +20,4 @@ USER_INFO_COOKIE_NAME='edx-user-info'
SCHEDULE_EMAIL_SECTION='true'
APP_ID=''
MFE_CONFIG_API_URL=''
PARAGON_THEME_URLS={}

3
.nvmrc
View File

@@ -1,2 +1 @@
20
24

View File

@@ -5,14 +5,24 @@ frontend-app-communications
Purpose
*******
********
A tool used by course teams to communicate with their learners. The interface for anything related to instructor-to-learner communications. Instructor bulk email, for example.
Getting started
---------------
Getting Started
***************
Prerequisites
=============
`Tutor`_ is currently recommended as a development environment for your
new MFE. Please refer
to the `relevant tutor-mfe documentation`_ to get started using it.
.. _Tutor: https://github.com/overhangio/tutor
.. _relevant tutor-mfe documentation: https://github.com/overhangio/tutor-mfe?tab=readme-ov-file#mfe-development
For now, this repo is not integrated with devstack. You'll be running the app locally and not through docker. This does make setup a little easier.
Cloning and Startup
===================
@@ -23,9 +33,9 @@ Cloning and Startup
git clone https://github.com/edx/frontend-app-communications.git
2. Use node v18.x.
2. Use the version of Node specified in the ``.nvmrc`` file.
The current version of the micro-frontend build scripts supports node 18.
The current version of the micro-frontend build scripts supports the version of Node found in ``.nvmrc``.
Using other major versions of node *may* work, but this is unsupported. For
convenience, this repository includes a ``.nvmrc`` file to help in setting the
correct node version via `nvm <https://github.com/nvm-sh/nvm>`_.

7179
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@@ -12,8 +12,8 @@
"scripts": {
"build": "fedx-scripts webpack",
"i18n_extract": "fedx-scripts formatjs extract",
"lint": "fedx-scripts eslint --ext .js --ext .jsx .",
"lint:fix": "fedx-scripts eslint --fix --ext .js --ext .jsx .",
"lint": "fedx-scripts eslint --ext .js --ext .jsx src/",
"lint:fix": "fedx-scripts eslint --fix --ext .js --ext .jsx src/",
"snapshot": "fedx-scripts jest --updateSnapshot",
"start": "fedx-scripts webpack-dev-server --progress",
"dev": "PUBLIC_PATH=/communications/ MFE_CONFIG_API_URL='http://localhost:8000/api/mfe_config/v1' fedx-scripts webpack-dev-server --progress --host apps.local.openedx.io",
@@ -31,8 +31,8 @@
"dependencies": {
"@edx/brand": "npm:@openedx/brand-openedx@^1.2.2",
"@edx/frontend-component-footer": "^14.6.0",
"@edx/frontend-component-header": "^6.4.0",
"@edx/frontend-platform": "^8.3.1",
"@edx/frontend-component-header": "^6.6.1",
"@edx/frontend-platform": "^8.3.7",
"@edx/openedx-atlas": "^0.6.0",
"@edx/tinymce-language-selector": "1.1.0",
"@fortawesome/fontawesome-svg-core": "1.2.36",
@@ -41,7 +41,7 @@
"@fortawesome/free-solid-svg-icons": "5.15.4",
"@fortawesome/react-fontawesome": "0.2.0",
"@openedx/frontend-plugin-framework": "^1.6.0",
"@openedx/paragon": "^22.16.0",
"@openedx/paragon": "^23.3.0",
"@tinymce/tinymce-react": "3.14.0",
"axios": "0.27.2",
"classnames": "2.3.2",
@@ -61,8 +61,8 @@
},
"devDependencies": {
"@edx/browserslist-config": "^1.2.0",
"@edx/reactifex": "^2.1.1",
"@openedx/frontend-build": "^14.3.3",
"@edx/typescript-config": "^1.1.0",
"@openedx/frontend-build": "^14.6.2",
"@testing-library/jest-dom": "^6.6.3",
"@testing-library/react": "^16.2.0",
"axios-mock-adapter": "1.21.2",

View File

@@ -8,7 +8,7 @@ import {
import {
SpinnerSimple, Cancel, Send, Event, Check,
} from '@openedx/paragon/icons';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import classNames from 'classnames';
import { getConfig } from '@edx/frontend-platform';
import TextEditor from '../text-editor/TextEditor';
@@ -51,8 +51,8 @@ function BulkEmailForm(props) {
courseId,
cohorts,
courseModes,
intl,
} = props;
const intl = useIntl();
const [{ editor }, dispatch] = useContext(BulkEmailContext);
const [emailFormStatus, setEmailFormStatus] = useState(FORM_SUBMIT_STATES.DEFAULT);
const [emailFormValidation, setEmailFormValidation] = useState({
@@ -392,7 +392,7 @@ BulkEmailForm.defaultProps = {
BulkEmailForm.propTypes = {
courseId: PropTypes.string.isRequired,
cohorts: PropTypes.arrayOf(PropTypes.string),
intl: intlShape.isRequired,
courseModes: PropTypes.arrayOf(
PropTypes.shape({
slug: PropTypes.string.isRequired,
@@ -401,4 +401,4 @@ BulkEmailForm.propTypes = {
).isRequired,
};
export default injectIntl(BulkEmailForm);
export default BulkEmailForm;

View File

@@ -39,7 +39,7 @@ function renderBulkEmailForm() {
function renderBulkEmailFormContext(value) {
return (
<BulkEmailContext.Provider value={[value, dispatchMock]}>
<BulkEmailForm courseId="test" courseMode={courseMode} />
<BulkEmailForm courseId="test" courseModes={courseMode} />
</BulkEmailContext.Provider>
);
}

View File

@@ -3,7 +3,7 @@
import React, { useMemo, useState } from 'react';
import PropTypes from 'prop-types';
import { useParams } from 'react-router-dom';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import {
Button, Collapsible, Icon,
@@ -14,7 +14,8 @@ import { getSentEmailHistory } from './data/api';
import BulkEmailTaskManagerTable from './BulkEmailHistoryTable';
import ViewEmailModal from './ViewEmailModal';
function BulkEmailContentHistory({ intl }) {
function BulkEmailContentHistory() {
const intl = useIntl();
const { courseId } = useParams();
const [emailHistoryData, setEmailHistoryData] = useState();
const [errorRetrievingData, setErrorRetrievingData] = useState(false);
@@ -154,7 +155,6 @@ function BulkEmailContentHistory({ intl }) {
}
BulkEmailContentHistory.propTypes = {
intl: intlShape.isRequired,
row: PropTypes.shape({
index: PropTypes.number,
}),
@@ -164,4 +164,4 @@ BulkEmailContentHistory.defaultProps = {
row: {},
};
export default injectIntl(BulkEmailContentHistory);
export default BulkEmailContentHistory;

View File

@@ -1,13 +1,14 @@
import React, { useState } from 'react';
import { useParams } from 'react-router-dom';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import { getInstructorTasks } from './data/api';
import messages from './messages';
import useInterval from '../../../utils/useInterval';
import BulkEmailTaskManagerTable from './BulkEmailHistoryTable';
function BulkEmailPendingTasks({ intl }) {
function BulkEmailPendingTasks() {
const intl = useIntl();
const { courseId } = useParams();
const [instructorTaskData, setInstructorTaskData] = useState();
@@ -89,8 +90,4 @@ function BulkEmailPendingTasks({ intl }) {
);
}
BulkEmailPendingTasks.propTypes = {
intl: intlShape.isRequired,
};
export default injectIntl(BulkEmailPendingTasks);
export default BulkEmailPendingTasks;

View File

@@ -1,6 +1,6 @@
import React, { useMemo, useState } from 'react';
import { useParams } from 'react-router-dom';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import { Icon, Collapsible } from '@openedx/paragon';
import { SpinnerSimple } from '@openedx/paragon/icons';
@@ -11,7 +11,8 @@ import BulkEmailTaskManagerTable from './BulkEmailHistoryTable';
import './bulkEmailTaskHistory.scss';
function BulkEmailTaskHistory({ intl }) {
function BulkEmailTaskHistory() {
const intl = useIntl();
const { courseId } = useParams();
const [emailTaskHistoryData, setEmailTaskHistoryData] = useState([]);
@@ -117,8 +118,4 @@ function BulkEmailTaskHistory({ intl }) {
);
}
BulkEmailTaskHistory.propTypes = {
intl: intlShape.isRequired,
};
export default injectIntl(BulkEmailTaskHistory);
export default BulkEmailTaskHistory;

View File

@@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import { getConfig } from '@edx/frontend-platform';
import BulkEmailContentHistory from './BulkEmailContentHistory';
import BulkEmailTaskHistory from './BulkEmailTaskHistory';
@@ -9,7 +9,8 @@ import messages from './messages';
import BulkEmailScheduledEmailsTable from './bulk-email-scheduled-emails-table';
import BulkEmailPendingTasksAlert from './BulkEmailPendingTasksAlert';
function BulkEmailTaskManager({ intl, courseId }) {
function BulkEmailTaskManager({ courseId }) {
const intl = useIntl();
return (
<div className="w-100">
{getConfig().SCHEDULE_EMAIL_SECTION && (
@@ -34,8 +35,7 @@ function BulkEmailTaskManager({ intl, courseId }) {
}
BulkEmailTaskManager.propTypes = {
intl: intlShape.isRequired,
courseId: PropTypes.string.isRequired,
};
export default injectIntl(BulkEmailTaskManager);
export default BulkEmailTaskManager;

View File

@@ -1,14 +1,15 @@
import React, { useContext } from 'react';
import PropTypes from 'prop-types';
import { ActionRow, Button, ModalDialog } from '@openedx/paragon';
import { FormattedMessage, injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { FormattedMessage, useIntl } from '@edx/frontend-platform/i18n';
import messages from './messages';
import { BulkEmailContext } from '../bulk-email-context';
import { copyToEditor } from '../bulk-email-form/data/actions';
function ViewEmailModal({
intl, messageContent, isOpen, setModalOpen,
messageContent, isOpen, setModalOpen,
}) {
const intl = useIntl();
const [, dispatch] = useContext(BulkEmailContext);
return (
<div>
@@ -72,7 +73,6 @@ function ViewEmailModal({
}
ViewEmailModal.propTypes = {
intl: intlShape.isRequired,
messageContent: PropTypes.shape({
subject: PropTypes.string,
requester: PropTypes.string,
@@ -86,4 +86,4 @@ ViewEmailModal.propTypes = {
setModalOpen: PropTypes.func.isRequired,
};
export default injectIntl(ViewEmailModal);
export default ViewEmailModal;

View File

@@ -4,7 +4,7 @@
import React, {
useCallback, useContext, useState, useEffect,
} from 'react';
import { injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { useIntl } from '@edx/frontend-platform/i18n';
import {
Alert, DataTable, Icon, IconButton, useToggle,
} from '@openedx/paragon';
@@ -32,7 +32,8 @@ function flattenScheduledEmailsArray(emails) {
}));
}
function BulkEmailScheduledEmailsTable({ intl }) {
function BulkEmailScheduledEmailsTable() {
const intl = useIntl();
const { courseId } = useParams();
const [{ scheduledEmailsTable }, dispatch] = useContext(BulkEmailContext);
const [tableData, setTableData] = useState([]);
@@ -196,8 +197,4 @@ function BulkEmailScheduledEmailsTable({ intl }) {
);
}
BulkEmailScheduledEmailsTable.propTypes = {
intl: intlShape.isRequired,
};
export default injectIntl(BulkEmailScheduledEmailsTable);
export default BulkEmailScheduledEmailsTable;

View File

@@ -1,13 +1,13 @@
import React from 'react';
import PropTypes from 'prop-types';
import { ActionRow, AlertModal, Button } from '@openedx/paragon';
import { FormattedMessage, injectIntl, intlShape } from '@edx/frontend-platform/i18n';
import { FormattedMessage, useIntl } from '@edx/frontend-platform/i18n';
function TaskAlertModal(props) {
const {
isOpen, close, alertMessage, intl,
isOpen, close, alertMessage,
} = props;
const intl = useIntl();
const messages = {
taskAlertTitle: {
id: 'bulk.email.task.alert.title',
@@ -57,7 +57,6 @@ TaskAlertModal.propTypes = {
isOpen: PropTypes.bool.isRequired,
close: PropTypes.func.isRequired,
alertMessage: PropTypes.node.isRequired,
intl: intlShape.isRequired,
};
export default injectIntl(TaskAlertModal);
export default TaskAlertModal;

View File

@@ -17,8 +17,8 @@ import 'tinymce/plugins/image';
import 'tinymce/plugins/codesample';
import '@edx/tinymce-language-selector';
import contentUiCss from 'tinymce/skins/ui/oxide/content.css';
import contentCss from 'tinymce/skins/content/default/content.css';
import contentUiCss from 'tinymce/skins/ui/oxide/content.css?raw';
import contentCss from 'tinymce/skins/content/default/content.css?raw';
export default function TextEditor(props) {
const {

View File

@@ -1,7 +1,4 @@
@import "~@edx/brand/paragon/fonts";
@import "~@edx/brand/paragon/variables";
@import "~@openedx/paragon/scss/core/core";
@import "~@edx/brand/paragon/overrides";
@use "@openedx/paragon/styles/css/core/custom-media-breakpoints" as paragonCustomMediaBreakpoints;
@import "~@edx/frontend-component-header/dist/index";
@import "~@edx/frontend-component-footer/dist/footer";

View File

@@ -3,7 +3,7 @@ import {
} from '@edx/frontend-platform';
// Jest needs this for module resolution
import * as app from '.'; // eslint-disable-line no-unused-vars
import * as app from '.'; // eslint-disable-line @typescript-eslint/no-unused-vars
// These need to be var not let so they get hoisted
// and can be used by jest.mock (which is also hoisted)

View File

@@ -13,6 +13,7 @@ import messages from './i18n';
jest.mock('@edx/frontend-platform/react/hooks', () => ({
...jest.requireActual('@edx/frontend-platform/react/hooks'),
useTrackColorSchemeChoice: jest.fn(),
useParagonTheme: () => [{ isThemeLoaded: true }, jest.fn()],
}));
Object.defineProperty(window, 'matchMedia', {
@@ -57,11 +58,6 @@ export function initializeMockApp() {
return { loggingService, i18nService, authService };
}
jest.mock('@edx/frontend-platform/react/hooks', () => ({
...jest.requireActual('@edx/frontend-platform/react/hooks'),
useTrackColorSchemeChoice: jest.fn(),
}));
function render(ui, options) {
// eslint-disable-next-line react/prop-types
function Wrapper({ children }) {

13
tsconfig.json Normal file
View File

@@ -0,0 +1,13 @@
{
"extends": "@edx/typescript-config",
"compilerOptions": {
"baseUrl": "./src",
"paths": {
"*": ["*"]
},
"rootDir": ".",
"outDir": "dist"
},
"include": ["*.js", ".eslintrc.js", "src/**/*", "plugins/**/*", "jest.config.ts"],
"exclude": ["*.js", ".eslintrc.js", "dist", "node_modules"]
}

View File

@@ -22,8 +22,13 @@ const webpack5esmInteropRule = {
},
};
const rawAssetRule = {
resourceQuery: /raw/,
type: 'asset/source',
};
const otherRules = config.module.rules;
config.module.rules = [webpack5esmInteropRule, ...otherRules];
config.module.rules = [rawAssetRule, webpack5esmInteropRule, ...otherRules];
module.exports = config;

View File

@@ -14,8 +14,13 @@ const webpack5esmInteropRule = {
},
};
const rawAssetRule = {
resourceQuery: /raw/,
type: 'asset/source',
};
const otherRules = config.module.rules;
config.module.rules = [webpack5esmInteropRule, ...otherRules];
config.module.rules = [rawAssetRule, webpack5esmInteropRule, ...otherRules];
module.exports = config;