Live data from Hacker News

A one-line package broke `npm create-react-app`

github.com

301–310 of 478 posts

Re: A one-line package broke `npm create-react-app`

#301
post #218

Earlier quoted context omitted.

This function is most likely an artifact of before promises got standardized. One way promises took off and became so ubiquitous is different implementations could interop seamlessly. And the reason for that is a promise was defined as 'an object or function having a then method which returns a promise when called'. Doesn't excuse the JS ecosystem and JS as a whole, which truly is a mess. But there's a history behind…

I think the point of the comment is: you should not be testing for this at all . If your API works with promises, call .then() on what is handed to you. That's it. Don't make up emergent, untestable behavior on the spot.

You need to do this test if you are creating a promise implementation. That was my point, there is a reason code like this exists.

Re: A one-line package broke `npm create-react-app`

#302

Earlier quoted context omitted.

This analogy doesn't hold up at all. The UHH is a fun read, yes, but the biggest real-world problem with the Unix Wars was cross-compatibility. Your Sun code didn't run on Irix didn't run on BSD and god help you if a customer wanted Xenix. OK, you can draw some parallel here between React vs. Vue vs. Zeit vs. whatever. But there was also the possibility, for non-software businesses, to pick a platform and stick to it…

> The UHH is a fun read, yes, but the biggest real-world problem with the Unix Wars was cross-compatibility. Your Sun code didn't run on Irix didn't run on BSD and god help you if a customer wanted Xenix. OK, you can draw some parallel here between React vs. Vue vs. Zeit vs. whatever POSIX is a set of IEEE standards that have been around in one form or another since the 80s, maybe JavaScript could follow Unix's path…

The existence of such a standard doesn't automatically guarantee compliance. There are plenty of APIs outside the scope of POSIX, plenty of places where POSIX has very under specified behavior, and even then, the compliance test suite doesn't test all of the rules and you still get tons of incompatibilities.

POSIX was, for the most part, not a major success. The sheer dominance of Linux monoculture makes that easy to forget, though.

Re: A one-line package broke `npm create-react-app`

#303
post #50

Earlier quoted context omitted.

Wow just wow. So here's your new Promise object: class World { then () { return 0; } } isPromise(new World) // true If there really isn't a safe and better way to tell if an object is an instance of Promise…then color me impressed.

I mean, if you have to assume deliberately adversarial action on the part of your own codebase, you may have worse problems than having to duck-type promises.

https://wiki.c2.com/?TheKenThompsonHack

Re: A one-line package broke `npm create-react-app`

#304
post #119

Everyone crying about this on the Internet would do better to just take it as an easy lesson: pin your dependency versions for projects running in production. This was an honest oversight, and even somewhat inevitable with so many expected supported ways to import/export between cjs mjs amd umd etc. It will happen again. And when it happens the next time, if it ruins your life again, take issue with yourself for not…

And everyone who depends on projects that pin their dependency versions gets to be victims of security exploits long after they are fixed. Dependency management is not as simple as you seem to think.

What you do is you pin dependencies, then automate regular dependency upgrade PRs. If your test suite and your CI/CD pipeline is reliable, this should be an easy addition.

Re: A one-line package broke `npm create-react-app`

#305

Can someone help me understand why a library like this is even necessary? Can't you just wrap everything and treat it like a promise? const aPromise = Promise.resolve(1); const notAPromise = 2; Promise.resolve(aPromise).then((x) => console.log(x)); Promise.resolve(notAPromise).then((y) => console.log(y)); // Logs: // 1 // 2

Somehow convoluted, but if you wrap in a promise like this then you make it async (similar to setTimeout(fn, 0)), so in some situations you might want to keep the non-promised code as non-promise:

https://journal.stuffwithstuff.com/2015/02/01/what-color-is-...

(red is async, blue is sync)

Re: A one-line package broke `npm create-react-app`

#306

Earlier quoted context omitted.

I don't think it should be a package. One-liners without dependencies like this should live as a function in a utility file. If justification is needed, there should be a comment with a link to this package's repo.

What's the difference between a utility file and a package? That seems like a distinction without a difference to me. If you use the same one liners in more than one project and you copy that utility file over, the line gets even fuzzier.

The utility file will never be updated and break your build without you doing it yourself.

Re: A one-line package broke `npm create-react-app`

#307
post #279

Earlier quoted context omitted.

I mind duck typing! That's why I'm so fond of Typescript, where everything that shows up where a promise should be is reliably either instanceof Promise, or instanceof something that implements Promise, or a compile-time error. Absent that evolved level of tooling, and especially in an environment still dealing with the legacy of slow standardization and competing implementations that I mentioned in another comment,…

So, I mind poorly implemented duck typing, I also mildly mind dynamic typing, but in principle I think static duck typing could be not bad. With javascript promises in particular, the duck typing suffers from this unfortunate fact that you can't easily check if something can be awaited-upon or not. I don't think I really care if something is a promise, so long as I can do everything I want to to it. So I view the iss…

Now we're kind of just litigating how "is-promise" is used in CRA, or more accurately in whichever of CRA's nth-level dependencies uses it, because CRA's codebase itself never mentions it.

I don't care enough to go dig that out on a Saturday afternoon, but I suspect that if I did, we'd end up agreeing that whoever is using it could, by dint of sufficient effort, have found a better way.

On the other hand, this appears to be the first time it's been a significant problem, and that only for the space of a few hours, none of which were business hours. That's a chance I'd be willing to take - did take, I suppose, in the sense that my team's primary product is built on CRA - because I'm an engineer, not a scientist, and my remit is thus to produce not something that's theoretically correct in all circumstances, but instead something that's exactly as solid as it has to be to get the job done, and no more. Not that this isn't, in the Javascript world as in any other, sometimes much akin to JWZ's "trying to make a bookshelf out of mashed potatoes". But hey, you know what? If the client only asks for a bookshelf that lasts for a minute, and the mashed potatoes are good enough for that, then I'll break open a box of Idaho™ Brand I Can't Believe It's Not Real Promises and get to work.

I grant this is not a situation that everyone finds satisfactory, nor should they; the untrammeled desire for perfection, given sufficient capacity on the part of its possessor and sufficient scope for them to execute on their visions, is exactly what produces tools like Typescript, that make it easier for workaday engineers like yours truly to more closely approach perfection, within budget, than we otherwise could. There's value in that. But there's value in "good enough", too.

Re: A one-line package broke `npm create-react-app`

#308
post #280

Earlier quoted context omitted.

What's "yarn zero installs"? Googling did not do it for me.

Instead of node_modules containing source code of the packages, yarn generates a pnp.js file which contains a map linking a package name and version to a location on the disk, and another map linking a package name and version to its set of dependencies. All the installed packages are stored in zip form in .yarn/cache folder to provide a reproducible build whenever you install a package from anywhere. You can commit…

This is a great feature I did not know about, thanks

I don't understand how it applies to the OP problem. Even without "zero installs", yarn all by itself with a yarn.lock already ensures the same versions as in the yarn.lock will be installed -- which will still be a reproducible build as long as a given version hasn't changed in the npm repo.

(It looks to me like "yarn zero" is primarily intended to let you install without a reliable network and/or faster and/or reduce the size of your deployment artifacts; but, true, it also gives you defense against a package-version being removed or maliciously changed in the npm repo true. But this wasn't something that happened in OP case was it? A particular version of a particular package being removed or changed in repo?)

In this case, it was a new version that introduced the breakage, not changed artifact for an existing version. AND the problem occurs on trying to create a new project template (if I understand right), so I thin it's unlikely you'd already have a yarn.lock or a .yarn/cache?

Am i missing something? Dont' think it's related to OP. But it's a cool feature!

Re: A one-line package broke `npm create-react-app`

#309
post #33

Digging into the reason behind breakage, the change is this one: https://github.com/then/is-promise/commit/feb90a40501c8ef69b... Which adds support for ES modules: https://medium.com/@nodejs/announcing-core-node-js-support-f... However the exports syntax requires a relative url, e.g. ‘./index.mjs’ not ‘index.mjs’. The fix is here: https://github.com/then/is-promise/pull/15/commits/3b3ea4150...

From those commits, it seems this issue was fixed in 1h12min. That should be a new record, specially considering this is all volunteer work on a Saturday. While it's bad that things break, the speed at which this was fixed is truly amazing. A big thank you to everyone involved here.

Not sure where you're getting 1h12 from. First issue was reported at 12:18pm (my time) final update that fixed it was published at 3:08pm.

Not that long, but my issue with this release snafu is that:

- the build didn't pass CI in the first place

- the CI config wasn't updated to reflect the most recent LTS release of node

- the update happened directly to master (although that's to how the maintainer wants to run their repo. it's been my experience that it's much easier to revert a squashed PR than most other options)

- it took two patch versions to revert (where it may have only taken one if the author could have pressed "undo" in the PR)

Re: A one-line package broke `npm create-react-app`

#310
post #7

And the source code of the library is: function isPromise(obj) { return !!obj && (typeof obj === 'object' || typeof obj === 'function') && typeof obj.then === 'function'; }

It didn't break because of the source, it broke because of all the packaging/module bullshit around it. It seems the Javascript ec(h)osystem has firmly come down on the philosophy of "make modules very easy to use, but very difficult to make (correctly)".

The predictable explosion in dependency trees has caused the predictable problems like this one. I feel I much prefer the C/C++ way of "modules are easy to make, but difficult to use".

Post reply on HN