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

Production build fails on Next.js #1824

Closed
4 tasks done
alexandernanberg opened this issue Jun 10, 2024 · 10 comments
Closed
4 tasks done

Production build fails on Next.js #1824

alexandernanberg opened this issue Jun 10, 2024 · 10 comments
Labels
bug Something isn't working

Comments

@alexandernanberg
Copy link

Before you start - checklist

  • I followed instructions in documentation written for my React-PDF version
  • I have checked if this bug is not already reported
  • I have checked if an issue is not listed in Known issues
  • If I have a problem with PDF rendering, I checked if my PDF renders properly in PDF.js demo

Description

Running yarn build fails on /sample/next-app (and all other Next apps)

                                                                           ^^^^^^
    `----

Caused by:
    0: failed to parse input file
    1: Syntax Error


> Build failed because of webpack errors

Steps to reproduce

  1. Go to the next-app sample
  2. Run yarn build

Expected behavior

Production builds work

Actual behavior

Build throws a Webpack error

Additional information

It's working on 8.x.x so likely something to do with the .mjs extension of the worker

Environment

  • Browser (if applicable):
  • React-PDF version: 9.0.0
  • React version: 18.2.0
  • Webpack version (if applicable):
@alexandernanberg alexandernanberg added the bug Something isn't working label Jun 10, 2024
@danielbucher
Copy link

I have the same issue. I'm using the app router. Setting experimental.esmExternals to loose on next config did not solve it. I've setup a small project to help reproduce this at https://github.com/danielbucher/react-pdf-build-error-nextjs.

@wojtekmaj
Copy link
Owner

Actual error on non-minified worker file:


static/media/pdf.worker.1f09ce21.mjs from Terser
  x 'import', and 'export' cannot be used outside of module code
       ,-[56104:1]
 56104 | const pdfjsBuild = "0cec64437";
 56105 | 
 56106 | var __webpack_exports__WorkerMessageHandler = __webpack_exports__.WorkerMessageHandler;
 56107 | export { __webpack_exports__WorkerMessageHandler as WorkerMessageHandler };
       : ^^^^^^
 56108 | 
 56109 | //# sourceMappingURL=pdf.worker.mjs.map
       `----

@wojtekmaj
Copy link
Owner

wojtekmaj commented Jun 10, 2024

Related:
vercel/next.js#61549
vercel/next.js#33914

I found that

    config.optimization.minimize = false;

fixes the issue, but disables minification, which is not cool.

swcMinify: false,

also fixes the issue, but causes the build to be slightly slower.

I also found that the message is probably not coming from Terser, but SWC: https://github.com/swc-project/swc/blob/abcf21dfc27b61489b614ce4ec0ae6733700578f/crates/swc_ecma_parser/src/error.rs#L415

@wojtekmaj
Copy link
Owner

Since it's a bug in Next.js not React-PDF, I'm closing this issue after updating upgrade guide wiki. Please kindly share your further feedback on importing ESM workers with Next.js team.

@0livare
Copy link

0livare commented Jul 25, 2024

Using an external CDN also works around this issue

import {pdfjs} from 'react-pdf'

-pdfjs.GlobalWorkerOptions.workerSrc = new URL(
-  'pdfjs-dist/build/pdf.worker.min.mjs',
-  import.meta.url,
-).toString();
+pdfjs.GlobalWorkerOptions.workerSrc = `//unpkg.com/pdfjs-dist@${pdfjs.version}/build/pdf.worker.min.mjs`;

@j3rryl
Copy link

j3rryl commented Jul 30, 2024

Using an external CDN also works around this issue

import {pdfjs} from 'react-pdf'

-pdfjs.GlobalWorkerOptions.workerSrc = new URL(
-  'pdfjs-dist/build/pdf.worker.min.mjs',
-  import.meta.url,
-).toString();
+pdfjs.GlobalWorkerOptions.workerSrc = `//unpkg.com/pdfjs-dist@${pdfjs.version}/build/pdf.worker.min.mjs`;

@0livare Thank you!
This worked for me as well!

@holdenmatt
Copy link

This was a head-scratcher to track down.

I was trying to switch from using the CDN to hosting myself but hit this webpack issue.

I went back to CDN but Firefox shows CORS errors. Finally figured out that adding "https" fixes the CORS issue and this seems to work in all browsers I've tested:

pdfjs.GlobalWorkerOptions.workerSrc = `https://unpkg.com/pdfjs-dist@${pdfjs.version}/build/pdf.worker.min.mjs`;

@legancode
Copy link

legancode commented Aug 2, 2024

I solved it by using this directly:

// In a component that needs to use this
import 'pdfjs-dist/build/pdf.worker.min.mjs';

// And delete this or some example implementation shown in the doc:
pdfjs.GlobalWorkerOptions.workerSrc = new URL(
  'pdfjs-dist/build/pdf.worker.min.mjs',
  import.meta.url,
).toString();

Additionally, if you have errors in the tests as a result of this import, you can do the following:

// jest.config.ts
{
   ...
   moduleNameMapper:{
     'pdfjs-dist/build/pdf.worker.min.mjs': '<rootDir>/src/test/__mocks__/mock-pdf-worker.ts'
  } ,
  transformIgnorePatterns: ['/node_modules/(?!pdfjs-dist/)'],
}
// Create the mock-pdf-worker.ts file and it must match the path that was placed in jest.config.ts
const mockPdfWorker = {};
export default mockPdfWorker;

@umairabbasDev
Copy link

Using an external CDN also works around this issue

import {pdfjs} from 'react-pdf'

-pdfjs.GlobalWorkerOptions.workerSrc = new URL(
-  'pdfjs-dist/build/pdf.worker.min.mjs',
-  import.meta.url,
-).toString();
+pdfjs.GlobalWorkerOptions.workerSrc = `//unpkg.com/pdfjs-dist@${pdfjs.version}/build/pdf.worker.min.mjs`;

thanks

@islamCodehood
Copy link

islamCodehood commented Aug 29, 2024

I solved it by using this directly:

// In a component that needs to use this
import 'pdfjs-dist/build/pdf.worker.min.mjs';

// And delete this or some example implementation shown in the doc:
pdfjs.GlobalWorkerOptions.workerSrc = new URL(
  'pdfjs-dist/build/pdf.worker.min.mjs',
  import.meta.url,
).toString();

Additionally, if you have errors in the tests as a result of this import, you can do the following:

// jest.config.ts
{
   ...
   moduleNameMapper:{
     'pdfjs-dist/build/pdf.worker.min.mjs': '<rootDir>/src/test/__mocks__/mock-pdf-worker.ts'
  } ,
  transformIgnorePatterns: ['/node_modules/(?!pdfjs-dist/)'],
}
// Create the mock-pdf-worker.ts file and it must match the path that was placed in jest.config.ts
const mockPdfWorker = {};
export default mockPdfWorker;

Thanks you, @legancode
This solution worked fine

// In a component that needs to use this
import 'pdfjs-dist/build/pdf.worker.min.mjs';

// And delete this or some example implementation shown in the doc:
// pdfjs.GlobalWorkerOptions.workerSrc = new URL(
  // ' pdfjs-dist/build/pdf.worker.min.mjs',
  // import.meta.url,
// ).toString();

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

9 participants