Git Product home page Git Product logo

Comments (15)

ekeijl avatar ekeijl commented on July 21, 2024 6

Webpack alias to the rescue!

Create ./date-fns-locale.js next to your Webpack config. Here you re-export all the locales you need:

export { default as enGB } from 'date-fns/locale/en-GB';
export { default as enUS } from 'date-fns/locale/en-US';

export { default as fr } from 'date-fns/locale/fr';
// ...etc

Here is the full list.

Add an alias to your webpack.config.js:

	resolve: {
		alias: {
			'date-fns/locale$': require.resolve('./date-fns-locales.js')
		}
	},

Mind the $ in the name! As explained in the Webpack alias documentation: this will only match imports ending in "date-fns/locale" and ensures that we can still import from "date-fns/locale/en-GB". Beware that other places you import x from "date-fns/locale" will also be aliased to date-fns-locales.js.

The resulting bundle:
image


Edit: if you try to use a locale that is not exported from your date-fns-locales.js, you will get the error Cannot read property 'localize' of undefined.

To use en-GB you also need to include en-US as it extends from the US locale! (I fixed this in the code above)

from picker.

guillaumeprevost avatar guillaumeprevost commented on July 21, 2024 2

Thanks for this workaround @ekeijl ! It worked in my case for the locales :)

It's still too bad that tree-shaking doesn't work out of the box, as this is one of the main points highlighted by date-fns ...

from picker.

devuxer avatar devuxer commented on July 21, 2024 1

The webpack workaround sounds great...if I weren't using Create React App. I could probably hack something together using CRACO, but hopefully a proper solution can be found ASAP.

from picker.

devuxer avatar devuxer commented on July 21, 2024 1

@matheusgrieger ,

That's amazing!

But it made me realize that even though I'm using Antd/rc-picker, the locales seem to be getting loaded by date-fns itself.

Any thoughts on what could be causing this? I'm hoping I can use a similar hack to fix that, but I'm not sure where to look.

EDIT No, I'm wrong. I forgot to do a build before analyzing. Applying your patch reduces my bundle size by almost 1 MB! Thanks for this solution!

from picker.

xsjcTony avatar xsjcTony commented on July 21, 2024 1

With Vite:

// vite.config.mts
resolve: {
  alias: {
    // fix DatePicker's date-fns bundle size
    'date-fns/locale': fileURLToPath(new URL('date-fns-locale', import.meta.url)),
  }
}
// date-fns-locale.mjs
export { enGB } from './node_modules/date-fns/locale.mjs';

from picker.

jquintozamora avatar jquintozamora commented on July 21, 2024

I'm having the same issue, is there any recommend solution to avoid increase bundle size ?

from picker.

tschanz-pcv avatar tschanz-pcv commented on July 21, 2024

I've just noticed this as well, sadly have no easy solution.

From the code it seems impossible to improve with just a configuration tweak. I guess the most straightforward "fix" would be to re-create the src/generate/dateFns.ts file in your project and tweak the imported locales. This will then also require changes in the places where the Locale object is used to make sure you have a fallback.

Would love to have an official solution though as https://ant.design/docs/react/replace-moment says You might want to replace Moment.js with another date library (now support dayjs and date-fns) to reduce bundle size. which might be a bit misleading if there is no way to also tweak locale imports.

from picker.

petrvecera avatar petrvecera commented on July 21, 2024

wow we just found out this issue, does anyone found a good solution yet? Or the only thing is to go with tschanz-pvc solution?

EDIT: My colleague cooked up this file which fixes the issue, however we hard coded enGB locale which is the one we need. Hope it helps https://gist.github.com/petrvecera/3daaab83c4a1efa0182ced135af717cf

from picker.

tigressbailey avatar tigressbailey commented on July 21, 2024

Same issue here.
Screen Shot 2021-08-16 at 9 27 57 AM

from picker.

bc-jaka avatar bc-jaka commented on July 21, 2024

Thank you @ekeijl - I will test this out to see how it works!

from picker.

matheusgrieger avatar matheusgrieger commented on July 21, 2024

For those using closed configurations like CRA and don't want to deal with CRACO or something like that, I was able to address this issue using patch-package. This is the diff it generated for me, and you can add other languages inside the new Locale object:

diff --git a/node_modules/rc-picker/lib/generate/dateFns.js b/node_modules/rc-picker/lib/generate/dateFns.js
index c8c7121..00de00d 100644
--- a/node_modules/rc-picker/lib/generate/dateFns.js
+++ b/node_modules/rc-picker/lib/generate/dateFns.js
@@ -1,7 +1,5 @@
 "use strict";
 
-var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard");
-
 Object.defineProperty(exports, "__esModule", {
   value: true
 });
@@ -9,7 +7,7 @@ exports.default = void 0;
 
 var _dateFns = require("date-fns");
 
-var Locale = _interopRequireWildcard(require("date-fns/locale"));
+var Locale = { enUS: require("date-fns/locale/en-US") };
 
 var dealLocal = function dealLocal(str) {
   return str.replace(/_/g, '');

from picker.

devuxer avatar devuxer commented on July 21, 2024

@matheusgrieger,

Follow-up: this seems to work in development, but in production, I'm getting all kinds of errors from dateFns.js for pages that have a Calendar or DatePicker on them, so I'm having to roll back the patch for now.

Still glad to know about patch-package, though!

from picker.

matheusgrieger avatar matheusgrieger commented on July 21, 2024

@devuxer that's weird, I'm using this patch in production and it seems to work just fine. Are you sure you added all locales your app needs?

from picker.

devuxer avatar devuxer commented on July 21, 2024

@matheusgrieger, My app only uses en-US as far as I know. Perhaps there's something about the server (Azure App Service, in my case) that's causing the issue (e.g., maybe the server locale is different than my development machine's locale, though it's a U.S. server, so it shouldn't be).

Edit:

More details:

If I attempt to open a page with an Antd Calendar component on it, I get this error in the console:

TypeError: Cannot read properties of undefined (reading 'weekStartsOn')
    at Object.getWeekFirstDay (dateFns.js:93:28)
    at dateUtil.js:96:44
    at me (DateBody.js:22:18)
    at ui (react-dom.production.min.js:157:137)
    at Yu (react-dom.production.min.js:267:460)
    at Tc (react-dom.production.min.js:250:347)
    at Oc (react-dom.production.min.js:250:278)
    at Sc (react-dom.production.min.js:250:138)
    at bc (react-dom.production.min.js:243:163)
    at react-dom.production.min.js:123:115

If I attempt to open a page with an Antd DatePicker components, I get this error in the console:

RangeError: locale must contain localize property
    at R (index.js:363:11)
    at Object.format (dateFns.js:130:27)
    at J (dateUtil.js:126:79)
    at useValueTexts.js:19:23
    at o (useMemo.js:6:30)
    at Ae (useValueTexts.js:8:10)
    at _e (RangePicker.js:409:24)
    at ui (react-dom.production.min.js:157:137)
    at Yu (react-dom.production.min.js:267:460)
    at Tc (react-dom.production.min.js:250:347)

from picker.

mendahu avatar mendahu commented on July 21, 2024

Coming up on three years of this bug being open. I just ran into it myself!

For anyone using Vite/Rollup instead of Webpack, the same workaround posted above works in your vite.config.js file, but for whatever reason I couldn't get the $ to work in the regex, despite it being supported according to Rollup documentation.

I have a central file where I manage all language imports anyway, so I just used the regular string to resolve, since I won't be importing anything directly from date-fns/locale/en-US for example.

// vite.config.js
    resolve: {
      alias: [
        { find: "date-fns/locale", replacement: "date-fns-locale-config.js" },
      ],
    },
    
// date-fns-locale.config.js
export { default as enCA } from "date-fns/esm/locale/en-CA";
export { default as enUS } from "date-fns/esm/locale/en-US";
export { default as es } from "date-fns/esm/locale/es";
export { default as ptBR } from "date-fns/esm/locale/pt-BR";

Then just import from date-fns/locale as needed.

import { enCA } from "date-fns/locale";

from picker.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.