Most active commenters
  • cluckindan(10)
  • zelphirkalt(9)
  • kelnos(6)
  • ivan_gammel(5)
  • respondo2134(5)
  • LtWorf(5)
  • TZubiri(4)
  • smaudet(4)
  • biggusdickus69(3)
  • skydhash(3)

←back to thread

1208 points jamesberthoty | 273 comments | | HN request time: 4.115s | source | bottom
1. kelnos ◴[] No.45266878[source]
As a user of npm-hosted packages in my own projects, I'm not really sure what to do to protect myself. It's not feasible for me to audit every single one of my dependencies, and every one of my dependencies' dependencies, and so on. Even if I had the time to do that, I'm not a typescript/javascript expert, and I'm certain there are a lot of obfuscated things that an attacker could do that I wouldn't realize was embedded malware.

One thing I was thinking of was sort of a "delayed" mode to updating my own dependencies. The idea is that when I want to update my dependencies, instead of updating to the absolute latest version available of everything, it updates to versions that were released no more than some configurable amount of time ago. As a maintainer, I could decide that a package that's been out in the wild for at least 6 weeks is less likely to have unnoticed malware in it than one that was released just yesterday.

Obviously this is not a perfect fix, as there's no guarantee that the delay time I specify is enough for any particular package. And I'd want the tool to present me with options sometimes: e.g. if my current version of a dep has a vulnerability, and the fix for it came out a few days ago, I might choose to update to it (better eliminate the known vulnerability than refuse to update for fear of an unknown one) rather than wait until it's older than my threshold.

replies(35): >>45266995 #>>45267024 #>>45267360 #>>45267489 #>>45267600 #>>45267697 #>>45267722 #>>45267967 #>>45268218 #>>45268503 #>>45268654 #>>45268764 #>>45269143 #>>45269397 #>>45269398 #>>45269524 #>>45269799 #>>45269945 #>>45270082 #>>45270083 #>>45270420 #>>45270708 #>>45270917 #>>45270938 #>>45272063 #>>45272548 #>>45273074 #>>45273291 #>>45273321 #>>45273387 #>>45273513 #>>45273935 #>>45274324 #>>45275452 #>>45277692 #
2. CraftThatBlock ◴[] No.45266995[source]
pnpm just added this: https://pnpm.io/blog/releases/10.16
replies(6): >>45267276 #>>45267443 #>>45267726 #>>45268030 #>>45268242 #>>45270530 #
3. gameman144 ◴[] No.45267024[source]
> It's not feasible for me to audit every single one of my dependencies, and every one of my dependencies' dependencies

I think this is a good argument for reducing your dependency count as much as possible, and keeping them to well-known and trustworthy (security-wise) creators.

"Not-invented-here" syndrome is counterproductive if you can trust all authors, but in an uncontrolled or unaudited ecosystem it's actually pretty sensible.

replies(8): >>45267054 #>>45267101 #>>45267444 #>>45268170 #>>45268880 #>>45270337 #>>45273381 #>>45273796 #
4. Ajedi32 ◴[] No.45267054[source]
If it's not feasible to audit every single dependency, it's probably even less feasible to rewrite every single dependency from scratch. Avoiding that duplicated work is precisely why we import dependencies in the first place.
replies(11): >>45267090 #>>45267094 #>>45267132 #>>45267222 #>>45267415 #>>45267471 #>>45268298 #>>45269164 #>>45270175 #>>45270363 #>>45270519 #
5. curtisf ◴[] No.45267090{3}[source]
This is true to the extent that you actually _use_ all of the features of a dependency.

You only need to rewrite what you use, which for many (probably most) libraries will be 1% or less of it

replies(1): >>45267507 #
6. AlecBG ◴[] No.45267094{3}[source]
Not sure I completely agree as you often use only a small part of a library
7. EGreg ◴[] No.45267101[source]
Exactly.

I always tried to keep the dependencies to a minimum.

Another thing you can do is lock versions to a year ago (this is what linux distros do) and wait for multiple audits of something, or lack of reports in the wild, before updating.

replies(1): >>45267246 #
8. lukan ◴[] No.45267132{3}[source]
"rewrite every single dependency from scratch"

No need to. But also no need to pull in a dependency that could be just a few lines of own (LLM generated) code.

replies(1): >>45267221 #
9. brianleb ◴[] No.45267221{4}[source]
>>a few lines of own (LLM generated) code.

... and now you've switched the attack vector to a hostile LLM.

replies(3): >>45267528 #>>45269094 #>>45272158 #
10. gameman144 ◴[] No.45267222{3}[source]
It isn't feasible to audit every line of every dependency, just as it's not possible to audit the full behavior of every employee that works at your company.

In both cases, the solution is similar: try to restrict access to vital systems only to those you trust,so that you have less need to audit their every move.

Your system administrators can access the server room, but the on-site barista can't. Your HTTP server is trusted enough to run in prod, but a color-formatting library isn't.

replies(1): >>45270529 #
11. gameman144 ◴[] No.45267246{3}[source]
I saw one of those word-substition browser plugins a few years back that swapped "dependency" for "liability", and it was basically never wrong.

(Big fan of version pinning in basically every context, too)

replies(1): >>45269333 #
12. jauntywundrkind ◴[] No.45267276[source]
minimumReleaseAge is pretty good! Nice!!

I do wish there were some lists of compromised versions, that package managers could disallow from.

13. eschneider ◴[] No.45267360[source]
If you pull something into your project, you're responsible for it working. Full stop. There are a lot of ways to manage/control dependencies. Pick something that works best for you, but be aware, due diligence, like maintenance is ultimately your responsibility.
replies(3): >>45267390 #>>45267968 #>>45268507 #
14. IshKebab ◴[] No.45267390[source]
That's very naive. We can do better than this.
replies(1): >>45267550 #
15. zelphirkalt ◴[] No.45267415{3}[source]
Most dependencies do much more than we need from them. Often it means we only need one or a few functions from them. This means one doesn't need to rewrite whole dependencies usually. Don't use dependencies for things you can trivially write yourself, and use them for cases where it would be too much work to write yourself.
replies(3): >>45267701 #>>45271035 #>>45271065 #
16. thepill ◴[] No.45267443[source]
bun is also working on it: https://github.com/oven-sh/bun/issues/22679
17. 2muchcoffeeman ◴[] No.45267444[source]
Have we all forgotten the left-pad incident?

This is an eco system that has taken code reuse to the (unreasonable) extreme.

When JS was becoming popular, I’m pretty sure every dev cocked an eyebrow at the dependency system and wondered how it’d be attacked.

replies(4): >>45267564 #>>45270790 #>>45274137 #>>45274653 #
18. bennyg ◴[] No.45267471{3}[source]
Sounds like the job for an LLM tool to extract what's actually used from appropriately-licensed OSS modules and paste directly into codebases.
replies(3): >>45267705 #>>45268191 #>>45269005 #
19. skybrian ◴[] No.45267489[source]
When using Go, you don't get updated indirect dependencies until you update a direct dependency. It seems like a good system, though it depends on your direct dependencies not updating too quickly.
replies(1): >>45270538 #
20. zahlman ◴[] No.45267507{4}[source]
Indeed. About 26% of the disk space for a freshly-installed copy of pip 25.2 for Python 3.13 comes from https://pypi.org/project/rich/ (and its otherwise-unneeded dependency https://pypi.org/project/Pygments/), "a Python library for rich text and beautiful formatting in the terminal", hardly any of the features of which are relevant to pip. This is in spite of an apparent manual tree-shaking effort (mostly on Pygments) — a separate installed copy of rich+Pygments is larger than pip. But even with that attempt, for example, there are hundreds of kilobytes taken up for a single giant mapping of "friendly" string names to literally thousands of emoji.

Another 20% or more is https://pypi.org/project/requests/ and its dependencies — this is an extremely popular project despite that the standard library already provides the ability to make HTTPS connections (people just hate the API that much). One of requests' dependencies is certifi, which is basically just a .pem file in Python package form. The vendored requests has not seen any tree-shaking as far as I can tell.

This sort of thing is a big part of why I'll be able to make PAPER much smaller.

replies(1): >>45270855 #
21. zelphirkalt ◴[] No.45267528{5}[source]
Though you will see the code at least, when you are copy pasting it and if it is really only a few lines, you may be able to review it. Should review it of course.
replies(1): >>45269090 #
22. hermannj314 ◴[] No.45267550{3}[source]
Almost all software has a no warranty clause. I am not a lawyer but in pretty plain English every piece of software I have ever used has said exactly that I can fuck off if I expect it to work or do anything.

To clarify - I dont think it is naive to assume the software is as-is with all responsibilities on the user since that is exactly what lawyers have made all software companies say that for over 50 years.

replies(2): >>45268051 #>>45268321 #
23. zelphirkalt ◴[] No.45267564{3}[source]
> This is an eco system that has taken code reuse to the (unreasonable) extreme.

Not even that actually. Actually the wheel is reinvented over and over again in this exact ecosystem. Many packages are low quality, and not even suitable to be reused much.

replies(1): >>45270066 #
24. Melatonic ◴[] No.45267600[source]
Lot of software has update policies like this and then also people will run a separate test environment updating to latest
25. spion ◴[] No.45267697[source]
pnpm just added minimum age for dependencies https://pnpm.io/blog/releases/10.16#new-setting-for-delayed-...
replies(3): >>45268420 #>>45269402 #>>45269599 #
26. btown ◴[] No.45267701{4}[source]
A brief but important point is that this primarily holds true in the context of rewriting/vendoring utilities yourself, not when discussing importing small vs. large dependencies.

Just because dependencies do a lot more than you need, doesn't mean you should automatically reach for the smallest dependency that fits your needs.

If you need 5 of the dozens of Lodash functions, for instance, it might be best to just install Lodash and let your build step shake out any unused code, rather than importing 5 new dependencies, each with far fewer eyes and release-management best practices than the Lodash maintainers have.

replies(3): >>45268248 #>>45268399 #>>45269728 #
27. philipwhiuk ◴[] No.45267705{4}[source]
Do you have any evidence it wouldn't just make up code.
28. duped ◴[] No.45267722[source]
Personally, I go further than this and just never update dependencies unless the dependency has a bug that affects my usage of it. Vulnerabilities are included.

It is insane to me how many developers update dependencies in a project regularly. You should almost never be updating dependencies, when you do it should be because it fixes a bug (including a security issue) that you have in your project, or a new feature that you need to use.

The only time this philosophy has bitten me was in an older project where I had to convince a PM who built some node project on their machine that the vulnerability warnings were not actually issues that affected our project.

Edit: because I don't want to reply to three things with the same comment - what are you using for dependencies where a) you require frequent updates and b) those updates are really hard?

Like for example, I've avoided updating node dependencies that have "vulnerabilities" because I know the vuln doesn't affect me. Rarely do I need to update to support new features because the dependency I pick has the features I need when I choose to use it (and if it only supports partial usage, you write it yourself!). If I see that a dependency frequently has bugs or breakages across updates then I stop using it, or freeze my usage of it.

replies(7): >>45268064 #>>45268307 #>>45268404 #>>45268944 #>>45269039 #>>45272068 #>>45272623 #
29. philipwhiuk ◴[] No.45267726[source]
Aren't they found quickly because people upgrade quickly?
30. TZubiri ◴[] No.45267967[source]
Install less dependencies, code more.
replies(2): >>45268314 #>>45268487 #
31. adrianmonk ◴[] No.45267968[source]
Acknowledging your responsibility doesn't make the problem go away. It's still better to have extra layers of protection.

I acknowledge that it is my responsibility to drive safely, and I take that responsibility seriously. But I still wear a seat belt and carry auto insurance.

32. drdaeman ◴[] No.45268030[source]
This sounds nice in theory, but does it really solve the issue? I think that if no one's installing that package then no one is noticing the malware and no one is reporting that package either. It merely slightly improves the chances that author would notice a version they didn't release, but this doesn't work if author is not particularly actively working the compromised project.
replies(3): >>45268331 #>>45268432 #>>45276196 #
33. gmueckl ◴[] No.45268051{4}[source]
Product liability is coming for software. Warranty disclaimers in licenses will be rendered ineffective by the end of 2026 at the latest.
replies(3): >>45268937 #>>45269110 #>>45269226 #
34. erulabs ◴[] No.45268064[source]
counterpoint, if the runtime itself (nodejs) has a critical issue, you haven't updated for years, you're on an end-of-life version, and you cannot upgrade because you have dependencies that do not support the new version of the runtime, you're in for a painful day. The argument for updating often is that when you -are- exposed to a vulnerability that you need a fix for, it's a much smaller project to revert or patch that single issue.

Otherwise, I agree with the sentiment that too many people try to update the world too often. Keeping up with runtime updates as often as possible (node.js is more trusted than any given NPM module) and updating only when dependencies are no longer compatible is a better middle ground.

replies(1): >>45268279 #
35. umvi ◴[] No.45268170[source]
"A little copying is better than a little dependency" -- Go proverb (also applies to other programming languages)
36. shakna ◴[] No.45268191{4}[source]
Requiring you to audit both security and robustness on the LLM generated code.

Creating two problems, where there was one.

replies(2): >>45269859 #>>45271077 #
37. Waterluvian ◴[] No.45268218[source]
I update my deps once a year or when I specifically need to. That helps a bit. Though it upsets the security theatre peeps at work who just blindly think dependabot issues means I need to change dependencies.
replies(1): >>45275373 #
38. brw ◴[] No.45268242[source]
there's apparently an npm RFC from 2022 proposing a similar (but potentially slightly better?) solution https://github.com/npm/rfcs/issues/646
39. jay_kyburz ◴[] No.45268248{5}[source]
Yes, fewer, larger, trustworthy dependencies with tree shaking is the way to go if you ask me.
replies(1): >>45268390 #
40. RussianCow ◴[] No.45268279{3}[source]
The same logic you used for runtimes also applies to libraries. Vulnerabilities are found in popular JS libraries all the time. The surface area is, of course, smaller than that of a runtime like Node.js, but there is still lots of potential for security issues with out-of-date libraries.

There really is no good solution other than to reduce the surface area for vulnerabilities by reducing the total amount of code you depend on (including third-party code). In practice, this means using as few dependencies as possible. If you only use one or two functions from lodash or some other helper library, you're probably better off writing or pulling in those functions directly instead.

41. kristianbrigman ◴[] No.45268298{3}[source]
One interesting side effect of AI is that it makes it sometimes easy to just recreate the behavior, perhaps without even realizing it..
42. 63stack ◴[] No.45268307[source]
Then you run the risk of drifting so much behind that when you actually have to upgrade it becomes a gargantuan task. Both ends of the scale have problems.
replies(2): >>45269319 #>>45270298 #
43. vvpan ◴[] No.45268314[source]
Copy-paste more.
replies(2): >>45268435 #>>45274357 #
44. IshKebab ◴[] No.45268321{4}[source]
I'm not sure what your point is. I was saying it's naive to think that everyone is going to review all dependencies, and we can do better than requiring them to.
replies(1): >>45268884 #
45. brw ◴[] No.45268331{3}[source]
These days compromised packages are often detected automatically by software that scans all packages uploaded to npm like https://socket.dev or https://snyk.io. So I imagine it's still useful to have those services scan these packages first, before they go out to the masses.

Measures like this also aren't meant to be "final solutions" either, but stop-gaps. Slowing the spread can still be helpful when a large scale attack like this does occur. But I'm also not entirely sure how much that weighs against potentially slowing the discovery as well.

Ultimately this is still a repository problem and not a package manager one. These are merely band-aids. The responsibility lies with npm (the repository) to implement proper solutions here.

> The responsibility lies with

46. _puk ◴[] No.45268390{6}[source]
Almost like a standard library..
replies(2): >>45268741 #>>45272423 #
47. Terr_ ◴[] No.45268399{5}[source]
I think the level of protection you get from that depends on how the unused code detection interacts with whatever tricks someone is using for malicious code.
48. kelnos ◴[] No.45268404[source]
Fully disagree. The problem is that when you do need to upgrade, either for a bug fix, security fix, or new feature that you need/want, it's a lot easier to upgrade if your last upgrade was 3 months ago than if it was 3 years ago.

This has bitten me so many times (usually at large orgs where policy is to be conservative about upgrades) that I can't even consider not upgrading all my dependencies at least once a quarter.

replies(1): >>45268964 #
49. kelnos ◴[] No.45268420[source]
Oh brilliant. I've been meaning to start migrating my use to pnpm; this is the push I needed.
50. kelnos ◴[] No.45268432{3}[source]
No, it doesn't solve the issue, but it probably helps.

And I agree that if everyone did this, it would slow down finding issues in new releases. Not really sure what to say to that... aside from the selfish idea that if I do it, but most other people don't, it won't affect me.

51. baobabKoodaa ◴[] No.45268435{3}[source]
I guess this is a joke, but imo it shouldn't be.
replies(2): >>45268861 #>>45269075 #
52. kelnos ◴[] No.45268487[source]
Sure, and I do that whenever I can. But I'm not going to write my own react, or even my own react-hook-form. I'm not going to rewrite stripe-js. Looking through my 16 direct dependencies -- that pull in a total of 653 packages, jesus christ -- there's only one of them that I'd consider writing myself (js-cookie) in order to reduce my dependency count. The rest would be a maintenance burden that I shouldn't have to take on.
replies(2): >>45268832 #>>45269431 #
53. homebrewer ◴[] No.45268503[source]
Don't update your dependencies manually. Setup renovate to do it for you, with a delay of at least a couple of weeks, and enable vulnerability alerts so that it opens PRs for publicly known vulnerabilities without delay

https://docs.renovatebot.com/configuration-options/#minimumr...

https://docs.renovatebot.com/presets-default/#enablevulnerab...

replies(1): >>45269456 #
54. kelnos ◴[] No.45268507[source]
Oh I'm well aware, and that's the problem. Unfortunately none of the available options hit anything close to the sweet spot that makes me comfortable.

I don't think this is a particularly unreasonable take; I'm a relative novice to the JS ecosystem, and I don't feel this uncomfortable taking on dependencies as I do in pretty much any other ecosystem I participate in, even those (like Rust) where the dependency counts can be high.

55. johtso ◴[] No.45268654[source]
Maybe one approach would be to pin all dependencies, and not use any new version of a package until it reaches a certain age. That would hopefully be enough time for any issues to be discovered?
replies(2): >>45268743 #>>45268876 #
56. jay_kyburz ◴[] No.45268741{7}[source]
Yeah, but perhaps we could have different flavors. If you like functional style you could have a very functional standard library that doesn't mutate anything, or if you like object oriented stuff you could have classes of object with methods that mutate themselves. And the Typescript folks could have a strongly typed library.
57. rapfaria ◴[] No.45268743[source]
People living on the latest packages with their dependabots never made any sense to me, ADR. They trusted their system too much
replies(1): >>45269166 #
58. 0xbadcafebee ◴[] No.45268764[source]
Stick to (pin) old stable versions, don't upgrade often. Pain in the butt to deal with eventual minimum-version-dependency limitations, but you don't get the brand new releases with bugs. Once a year, get all the newest versions and figure out all the weird backwards-incompatible bugs they've introduced. Do it over the holiday season when nobody's getting anything done anyway.
59. TZubiri ◴[] No.45268832{3}[source]
There's this defense mechanism that I don't know how it's called, but when someone takes a criticism to the extreme to complain about it being unfeasible.

Criticism: "You should shower every day"

Defense: "OH, maybe I should shower every hour, to the point where my skin dries and I can't get my work done because I'm in the shower all day."

No, there's a pretty standard way of doing things that you can care to learn, and it's very feasible, people shower every day during the week, sometimes they skip if they don't go out during weekends, if it's very cold you can skip a day, and if it's hot you can even shower twice. You don't even need to wash your hair every day. There's nuance that you can learn if you stop being so defeatist about it.

Similarly, you can of course install stripe-js since it's vendored from a paid provider with no incentive to fuck you with malware and with resources to audit dependency code, at any rate they are already a dependency of yours, so adding an npm package does not add a vendor to your risk profile.

Similarly you can add react-hook-form if it's an official react package, however if it isn't, then it's a risk, investigate who uploads it, if it's a random from github with an anime girl or furry image in their profile, maybe not. Especially if the package is something like an unofficial react-mcp-dotenv thing where it has access to critical secrets.

Another fallacy is that you have to rewrite the whole dependency you would otherwise import. False. You are not going to write a generic solution for all use cases, just for your own, and it will be tightly integrated and of higher quality and less space (which helps with bandwidth, memory and CPU caching), because of it. For god's sake, you used an example relating to forms? We've had forms since the dot com boom, how come you are still having trouble with those? You should know them like the back of your hand.

replies(1): >>45269078 #
60. TZubiri ◴[] No.45268861{4}[source]
I'm all for disregarding DRY and copypasting code you wrote.

But I think for untrusted third party code, it's much better to copy the code by hand, that way you are really forced to audit it. There really isn't much of an advantage to copying an install.sh script compared to just downloading a running the .sh, whereas writing the actual .sh commands on the command line (and following any other URLs before executing them) is golden.

61. pfych ◴[] No.45268876[source]
Packages can still be updated, even if pinned. If a dependency of a dependency is not pinned - it can still be updated.
62. respondo2134 ◴[] No.45268880[source]
>> and keeping them to well-known and trustworthy (security-wise) creators.

The true threat here isn't the immediate dependency though, it's the recursive supply chain of dependencies. "trustworthy" doesn't make any sese either when the root cause is almost always someone trustworthy getting phished. Finally if I'm not capable of auditing the dependencies it's unlikely I can replace them with my own code. That's like telling a vibe coder the solution to their brittle creations is to not use AI and write the code themselves.

replies(2): >>45270500 #>>45270620 #
63. hermannj314 ◴[] No.45268884{5}[source]
I thought my point was clearly made the 1st time.

How can we promise to "do better" when shit like "no author or distributor accepts responsibility to anyone for the consequences of using it or for whether it serves any particular purpose or works at all" is in the legal agreement of the software you are using?

Making someone agree to that while simultaneously on the side making promises that the software works is used car salesman gimmicks. The only things that matters is what you put in writing.

replies(1): >>45270870 #
64. tcoff91 ◴[] No.45268937{5}[source]
Source? An open source library is not necessarily a ‘product’ at all.
replies(1): >>45269240 #
65. respondo2134 ◴[] No.45268944[source]
this seems to me to be trading one problem that might happen for one that is guaranteed: a very painful upgrade. Maybe you only do it once in a while but it will always suck.
66. respondo2134 ◴[] No.45268964{3}[source]
yeah, I typically start any substantial development work with getting things up to date so you're not building on something you'll find out is already broken when you do get around to that painful upgrade.
67. const_cast ◴[] No.45269005{4}[source]
This is already a thing, compiled languages have been doing this for decades. This is just C++ templates with extra steps.
68. 1970-01-01 ◴[] No.45269039[source]
Dependency hell exists at both ends. Too quick can bite you just as much as being too slow/lazy.
69. vvpan ◴[] No.45269075{4}[source]
Not entirely a joke actually. For example, I have worked at a large corp where dependencies were high discouraged. For example lodash was not used in the codebase I was working on and if you really needed something from lodash you were encouraged to copy-paste the function. This won't work for large libraries of course but the copy-paste-first mentality is not a bad one.
70. respondo2134 ◴[] No.45269078{4}[source]
Reductio ad Absurdum may be what you're thinking of, but Straw Man might also apply. Funny enough the responder didn't actually do what you said. They stated of the 600+ dependencies they counted there was only one they felt comfortable implementing themselves. Your accusation of them taking your statement to the extreme is reverse straw man rhetoric; you're misrepresenting their argument as extreme or absurd when it’s actually not.
replies(1): >>45272568 #
71. LtWorf ◴[] No.45269090{6}[source]
If it's that little review the dependency.
replies(1): >>45272950 #
72. appreciatorBus ◴[] No.45269094{5}[source]
Sure but that's a one time vector. If the attacker didn't infiltrate the LLM before it generated the code, then the code is not going to suddenly go hostile like an npm package can.
73. respondo2134 ◴[] No.45269110{5}[source]
this seems highly unlikely. Almost all of the software we're discussing in this context has little or no resources behind it. No lawyers are going to sue an OSS developer because there's no payday.
74. nostrademons ◴[] No.45269143[source]
npm shrinkwrap and then check in your node_modules folder. Don't have each developer (or worse, user) individually run npm install.

It's common among grizzled software engineering veterans to say "Check in the source code to all of your dependencies, and treat it as if it were your own source code." When you do that, version upgrades are actual projects. There's a full audit trail of who did what. Every build is reproducible. You have full visibility into all code that goes into your binary, and you can run any security or code maintenance tools on all of it. You control when upgrades happen, so you don't have a critical dependency break your upcoming project.

75. reaperducer ◴[] No.45269164{3}[source]
it's probably even less feasible to rewrite every single dependency from scratch.

When you code in a high-security environment, where bad code can cost the company millions of dollars in fines, somehow you find a way.

The sibling commenter is correct. You write what you can. You only import from trusted, vetted sources.

76. LtWorf ◴[] No.45269166{3}[source]
If you don't review the pinned versions, it makes no difference.
77. LtWorf ◴[] No.45269226{5}[source]
only if you pay for it… otherwise you are liable but don't have anyone else to blame.
78. LtWorf ◴[] No.45269240{6}[source]
No source because it's not real. There's talk about final products and making the companies selling them responsible. But open source developers are not responsible.
79. electroly ◴[] No.45269319{3}[source]
That's only a problem for you, the developer, though, and is merely an annoyance about time spent. And it's all stuff you had to do anyway to update--you're just doing it all at once instead of spread out over time. A supply chain malware attack is a problem for every one of your users--who will all leave you once the dust is settled--and you end up in headline news at the top of HN's front page. These problems are not comparable. One is a rough day. The other is the end of your project.
replies(2): >>45269903 #>>45273746 #
80. j1elo ◴[] No.45269333{4}[source]
I'm re-reading all these previous comments, replacing "dependency" for "liability" in my mind, and it's being quite fun to see how well everything still keeps meaning the same, but better
81. collinmanderson ◴[] No.45269397[source]
> sort of a "delayed" mode to updating my own dependencies. The idea is that when I want to update my dependencies, instead of updating to the absolute latest version available of everything, it updates to versions that were released no more than some configurable amount of time ago.

For Python's uv, you can do something like:

> uv lock --exclude-newer $(date --iso -d "2 days ago")

replies(2): >>45270781 #>>45271223 #
82. ◴[] No.45269398[source]
83. ojosilva ◴[] No.45269402[source]
From your link:

> In most cases, such attacks are discovered quickly and the malicious versions are removed from the registry within an hour.

By delaying the infected package availability (by "aging" dependencies), we're only delaying the time, and reducing samples, until it's detected. Infections that lay dormant are even more dangerous than explosives ones.

The only benefit would be if, during this freeze, repository maintainers were successfully pruning malware before it hits the fan, and the freeze would give scanners more time to finish their verification pipelines. That's not happening afaik, NPM is crazy fast going from `npm publish` to worldwide availability, scanning is insufficient by many standards.

replies(1): >>45269530 #
84. dismalaf ◴[] No.45269431{3}[source]
React has zero dependencies and Stripe has one... What else do you need?
85. collinmanderson ◴[] No.45269456[source]
Why was this comment downvoted? Please explain why you disagree.
replies(1): >>45269990 #
86. 1over137 ◴[] No.45269524[source]
>It's not feasible for me to audit every single one of my dependencies

Perhaps I’m just ignorant of web development, but why not? We do so with our desktop software.

replies(1): >>45271691 #
87. jkrems ◴[] No.45269530{3}[source]
Afaict many of these recent supply chain attacks _have_ been detected by scanners. Which ones flew under the radar for an extended period of time?

From what I can tell, even a few hours of delay for actually pulling dependencies post-publication to give security tools a chance to find it would have stopped all (?) recent attacks in their tracks.

88. oefrha ◴[] No.45269599[source]
Thank god, adopting this immediately. Next I’d like to see Go-style minimum version selection instead.
89. latexr ◴[] No.45269728{5}[source]
The argument wasn’t to import five dependencies, one for each of the functions, but to write the five functions yourself. Heck, you don’t even need to literally write them, check the Lodash source and copy them to your code.
replies(3): >>45269898 #>>45269917 #>>45272318 #
90. cmckn ◴[] No.45269799[source]
> instead of updating to the absolute latest version available of everything, it updates to versions that were released no more than some configurable amount of time ago

The problem with this approach is you need a certain number of guinea pigs on the bleeding edge or the outcome is the same (just delayed). There is no way for anyone involved to ensure that balance is maintained. Reducing your surface area is a much more effective strategy.

replies(1): >>45269963 #
91. bennyg ◴[] No.45269859{5}[source]
I didn't say generate :) - in all seriousness, I think you could reasonably have it copy the code for e.g. lodash.merge() and paste it into your codebase without the headaches you're describing. IMO, this method would be practical for a majority of npm deps in prod code. There are some I'd want to rely on the lib (and its maintenance over time), but also... a sort function is a sort function.
replies(1): >>45270170 #
92. halflife ◴[] No.45269898{6}[source]
And then when node is updated and natively supports set intersections you would go back to your copied code and fix it?
replies(2): >>45270249 #>>45273825 #
93. biggusdickus69 ◴[] No.45269903{4}[source]
The time upgrading is not linear, it’s exponential. If it hurts, do it more often! https://martinfowler.com/bliki/FrequencyReducesDifficulty.ht...
94. mandevil ◴[] No.45269917{6}[source]
This might be fine for some utility functions which you can tell at a glance have no errors, but for anything complex, if you copy you don't get any of the bug/security fixes that upstream will provide automatically. Oh, now you need a shim of this call to work on the latest Chrome because they killed an api- you're on your own or you have to read all of the release notes for a dependency you don't even have! But taking a dependency on some other library is, as you note, always fraught. Especially because of transitive dependencies, you end up having quite a target surface area for every dep you take.

Whether to take a dependency is a tricky thing that really comes down to engineering judgement- the thing that you (the developer) are paid to make the calls on.

replies(1): >>45270873 #
95. hedora ◴[] No.45269945[source]
I recently started using npm for an application where there’s no decent alternative ecosystem.

The signal desktop app is an electron app. Presumably it has the same problem.

Does anyone know of any reasonable approaches to using npm securely?

“Reduce your transitive dependencies” is not a reasonable suggestion. It’s similar to “rewrite all the Linux kernel modules you need from scratch” or “go write a web browser”.

replies(2): >>45270039 #>>45272896 #
96. biggusdickus69 ◴[] No.45269963[source]
Not necessarily, some supply chain compromises are detected within a day by the maintainers themselves, for example by their account being taken over. It would be good to mitigate those at least.
replies(1): >>45272633 #
97. biggusdickus69 ◴[] No.45269990{3}[source]
I didn’t downvote, but...

Depending on a commercial service is out of the question for most open source projects.

replies(1): >>45271839 #
98. umpalumpaaa ◴[] No.45270039[source]
Most big tech companies maintain their own NPM registry that only includes approved packages. If you need a new package available in that registry you have to request it. A security team will then review that package and its deps and add it to the list of approved packages…

I would love to have something like that "in the open"…

replies(1): >>45270334 #
99. wongarsu ◴[] No.45270066{4}[source]
The perfect storm of on the one side junior developers who are afraid of writing even trivial code and are glad if there's a package implementing functionality that can be done in a one-liner, and on the other side (often junior) developers who want to prove themselves and think the best way to do that is to publish a successful npm package
replies(2): >>45270499 #>>45272644 #
100. benoau ◴[] No.45270082[source]
I like to pin specific versions in my package.json so dependencies don't change without manual steps, and use "npm ci" to install specifically the versions in package-lock.json. My CI runs "npm audit" which will raise the alarms if a vulnerability emerges in those packages. With everything essentially frozen there either is malware within it, or there is not going to be, and the age of the packages softly implies there is not.
101. abrookewood ◴[] No.45270083[source]
The article explicitly mentions a way to do this:

Use NPM Package Cooldown Check

The NPM Cooldown check automatically fails a pull request if it introduces an npm package version that was released within the organization’s configured cooldown period (default: 2 days). Once the cooldown period has passed, the check will clear automatically with no action required. The rationale is simple - most supply chain attacks are detected within the first 24 hours of a malicious package release, and the projects that get compromised are often the ones that rushed to adopt the version immediately. By introducing a short waiting period before allowing new dependencies, teams can reduce their exposure to fresh attacks while still keeping their dependencies up to date.

replies(4): >>45270505 #>>45270653 #>>45270687 #>>45272601 #
102. shakna ◴[] No.45270170{6}[source]
LLMs don't copy and paste. They ingest and generate. The output will always be a generated something.
replies(2): >>45270709 #>>45281752 #
103. 8note ◴[] No.45270175{3}[source]
is it that infeasible with LLMs?

a lor of these dependencies are higher order function definitions, which never change, and could be copy/pasted around just fine. they're never gonna change

104. skydhash ◴[] No.45270249{7}[source]
If it works, why do so? Unless there's a clear performance boost, and if so you already know the code and can quickly locate your interpreted version.

Or At the time of adding you can add a NOTE or FIXME comment stating where you copied it from. A quick grep for such keyword can give you a nice overview of nice to have stuff. You can also add a ticket with all the details if you're using a project management tool and resuscitate it when that hypothetical moment happens.

105. skydhash ◴[] No.45270298{3}[source]
That's why there's an emphasis on stability. If things works fine, don't change. If you're applying security patches, don't break the API.

In NPM world, there's so much churn that it would be comical if not for the security aspects.

106. skydhash ◴[] No.45270334{3}[source]
A debian version of NPM? I've seen a lot of hates on Reddit and other places about Debian because the team focuses on stability. When you look at the project, it's almost always based on Rust or Python.
107. motorest ◴[] No.45270337[source]
> I think this is a good argument for reducing your dependency count as much as possible, and keeping them to well-known and trustworthy (security-wise) creators.

I wonder to which extent is the extreme dependency count a symptom of a standard library that is too minimalistic for the ecosystem's needs.

Perhaps this issue could be addressed by a "version set" approach to bundling stable npm packages.

replies(1): >>45270657 #
108. motorest ◴[] No.45270363{3}[source]
> If it's not feasible to audit every single dependency, it's probably even less feasible to rewrite every single dependency from scratch.

There is no need to rewrite dependencies. Sometimes it just so happens that a project can live without outputting fancy colorful text to stdout, or doesn't need to spread transitive dependencies on debug utilities. Perhaps these concerns should be a part of the standard library, perhaps these concerns are useless.

And don't get me started on bullshit polyfill packages. That's an attack vector waiting to be exploited.

109. glennericksen ◴[] No.45270420[source]
You can switch to the mentioned "delayed" mode if you're using pnpm. A few days ago, pnpm 10.16 introduced a minimumReleaseAge setting that delays the installation of newly released dependencies by a configurable amount of time.

https://pnpm.io/blog/releases/10.16

110. bobthepanda ◴[] No.45270499{5}[source]
The blessing and curse of frontend development is that there basically isn't a barrier to entry given that you can make some basic CSS/JS/HTML and have your browser render it immediately.

There's also the flavor of frontend developer that came from the backend and sneers at actually having to learn frontend because "it's not real development"

replies(2): >>45271721 #>>45274085 #
111. ◴[] No.45270500{3}[source]
112. loginatnine ◴[] No.45270505[source]
That's a feature of stepsecurity though, it's not built-in.
113. smrtinsert ◴[] No.45270519{3}[source]
Its much more feasible these days. These days for my personal projects I just have CC create only a plain html file with raw JS and script links.
114. autoexec ◴[] No.45270529{4}[source]
> It isn't feasible to audit every line of every dependency, just as it's not possible to audit the full behavior of every employee that works at your company.

Your employees are carefully vetted before hiring. You've got their names, addresses, and social security numbers. There's someone you're able to hold accountable if they steal from you or start breaking everything in the office.

This seems more like having several random contractors who you've never met coming into your business in the middle of night. Contractors that were hired by multiple anonymous agencies you just found online somewhere with company names like gkz00d or 420_C0der69 who you've also never even spoken to and who have made it clear that they can't be held accountable for anything bad that happens. Agencies that routinely swap workers into or out of various roles at your company without asking or telling you, so you don't have any idea who the person working in the office is, what they're doing, or even if they're supposed to be there.

"To make thing easier for us we want your stuff to require the use of a bunch of code (much of which does things you don't even need) that we haven't bothered looking at because that'd be too much work for us. Oh, and third parties we have no relationship with control a whole bunch of that code which means it can be changed at any moment introducing bugs and security issues we might not hear about for months/years" seems like it should be a hard sell to a boss or a client, but it's sadly the norm.

Assuming that something is going to go wrong and trying to limit the inevitable damage is smart, but limiting the amount of untrustworthy code maintained by the whims of random strangers is even better. Especially when the reasons for including something that carries so much risk is to add something trivial or something you could have just written yourself in the first place.

replies(2): >>45272298 #>>45273210 #
115. smrtinsert ◴[] No.45270530[source]
this btw would also solve social media. if only accounts required a month waiting period before they could speak.
116. silverwind ◴[] No.45270538[source]
The auto-updating behaviour dependencies because of the `^` version prefix is the root problem.

It's best to never use `^` and always specify exact version, but many maintainers apparently can't be bothered with updating their dependencies themselves so it became the default.

117. autoexec ◴[] No.45270620{3}[source]
> Finally if I'm not capable of auditing the dependencies it's unlikely I can replace them with my own code. That's like telling a vibe coder the solution to their brittle creations is to not use AI and write the code themselves.

In both cases, actually doing the work and writing a function instead of adding a dependency or asking an AI to write it for you will probably make you a better coder and one who is better able to audit code you want to blindly trust in the future.

replies(1): >>45273892 #
118. autoexec ◴[] No.45270653[source]
This is basically what I recommended people do with windows updates back when MS gave people a choice about when/if to install them, with shorter windows for critical updates and much longer ones for low priority updates or ones that only affected things they weren't using.
119. DrewADesign ◴[] No.45270657{3}[source]
I remember people in the JS crowd getting really mad at the implication that this all was pretty much inevitable, like 10/15 years ago. Can’t say they didn’t do great things since then, but it’s not like nobody saw this coming.
120. DrewADesign ◴[] No.45270687[source]
And hope there isn’t some recently patched zero-day RCE exploit at the same time.
121. pabs3 ◴[] No.45270708[source]
This is where distributed code audits come in, you audit what you can, others audit what they can, and the overlaps of many audits gives you some level of confidence in the audited code.

https://github.com/crev-dev/

122. TheBicPen ◴[] No.45270709{7}[source]
In 2022, sure. But not today. Even something as simple as generating and running a `git clone && cp xyz` command will create code not directly generated by the LLM.
replies(1): >>45288106 #
123. zygentoma ◴[] No.45270781[source]
Awesome tip, thanks!
124. smaudet ◴[] No.45270790{3}[source]
I found it funny back when people were abandoning Java for JavaScript thinking that was better somehow...(especially in terms of security)

NPM is good for building your own stack but it's a bad idea (usually) to download the Internet. No dep system is 100% safe (including AI, generating new security vulns yay).

I'd like to think that we'll all stop grabbing code we don't understand and thrusting it into places we don't belong, or at least, do it more slowly, however, I also don't have much faith in the average (especially frontend web) dev. They are often the same idiots doing XYZ in the street.

I predict more hilarious (scary even) kerfuffles, probably even major militaries losing control of things ala Terminator style.

replies(1): >>45271013 #
125. vasco ◴[] No.45270855{5}[source]
What paper?
replies(1): >>45271127 #
126. worik ◴[] No.45270870{6}[source]
> How can we promise to "do better" when shit like "no author or distributor accepts responsibility to anyone

One way or another that will end.

Free Software will have the same responsibilities. If you write software, negligently, and it causes damage, you will be liable

I should not be able to make a Crypto wallet that is easy to hack and distribute it without consequence

This will be a very good thing

We know how to make secure 4eliable software (some of us) but nobody will pay for it

127. jonquest ◴[] No.45270873{7}[source]
The massive amount of transitive dependencies is exactly the problem with regard to auditing them. There are successful businesses built solely around auditing project dependencies and alerting teams of security issues, and they make money at all because of the labor required to maintain this machine.

It’s not even a judgement call at this point. It’s more aligned with buckling your seatbelt, pointing your car off the road, closing your eyes, flooring it and hoping for a happy ending.

128. esafak ◴[] No.45270917[source]
> One thing I was thinking of was sort of a "delayed" mode to updating my own dependencies.

You can do it:

https://github.blog/changelog/2025-07-01-dependabot-supports...

https://docs.renovatebot.com/configuration-options/#minimumr...

https://www.stepsecurity.io/blog/introducing-the-npm-package...

129. travisgriggs ◴[] No.45270938[source]
Use less dependencies :)

And larger dependencies that can be trusted in larger blocks. I'll bet half of a given projects dependencies are there to "gain experience with" or be able to name drop that you've used them.

Less is More.

We used to believe that. And then W3C happened.

130. hshdhdhj4444 ◴[] No.45271013{4}[source]
It’s not clear to me what this has to do with Java vs JavaScript (unless you’re referring to the lack of a JS standard library which I think will pretty much minimize this issue).

In fact, when we did have Java in the browser it was loaded with security issues primarily because of the much greater complexity of the Java language.

replies(3): >>45271560 #>>45271770 #>>45273237 #
131. hshdhdhj4444 ◴[] No.45271035{4}[source]
I agree with this but the problem is that a lot of the extra stuff dependencies do is indeed to protect from security issues.

If you’re gonna reimplement only thr code you need from a dependency, it’s hard to know of the stuff you’re leaving out how much is just extra stuff you don’t need and how much might be security fixes that may not be apparent to you but the dependency by virtue of being worked upon and used by many people has fixed.

132. vFunct ◴[] No.45271065{4}[source]
I'm using LLMs to write stuff that would normally be in dependencies, mostly because I don't want to learn how to use the dependency, and writing a new one from scratch is really easy with LLMs.
replies(1): >>45272434 #
133. vFunct ◴[] No.45271077{5}[source]
LLMs can do the audits now.
134. what ◴[] No.45271127{6}[source]
Presumably this: https://github.com/zahlman/paper
replies(1): >>45278782 #
135. parlortricks ◴[] No.45271223[source]
oh that uv lock is neat, i am going to give that a go
136. lmz ◴[] No.45271560{5}[source]
It's not the language it's the library that's not designed to isolate untrusted code from the start. Much harder to exit the sandbox if your only I/O mechanism is the DOM, alert() and prompt().
replies(1): >>45271739 #
137. galaxy_gas ◴[] No.45271691[source]
Average .net core desktop complex app may have a dozen dependencies if it get to that point. Average npm todo list may have several thousand if not more
138. pxc ◴[] No.45271721{6}[source]
> There's also the flavor of frontend developer that came from the backend and sneers at actually having to learn frontend because "it's not real development"

What kind of code does this developer write?

replies(3): >>45271929 #>>45272283 #>>45278523 #
139. smaudet ◴[] No.45271739{6}[source]
And the whole rest of the Internet...

The issue here is not Java or it's complexity. The point is also not Java, it's incidental that it was popular at the time. It's people acting irrationally about things and jumping ship for an even-worse system.

Like, yes, if that really were the whole attack surface of JS, sure nobody would care. They also wouldn't use it...and nothing we cared about would use it either...

140. smaudet ◴[] No.45271770{5}[source]
Java has maven, and is far from immune from similar types of attacks. However, it doesn't have the technological monstrosity named NPM. In fact that aforementioned complexity is/was an asset in raising the bar, however slightly, in producing java packages. Crucially, that ecosystem is nowhere near as absurdly complex (note, I'm ignoring the I'll fated cousin that is Gradle, and is also notorious for being a steaming pile of barely-working inscrutable dependencies)

Anyways, I think you are missing the forest for the trees if you think this is a Java vs JavaScript comparison, don't worry it's also possible to produce junk enterprise code too...

Just amusing watching people be irrationally scared of one language/ecosystem vs another without stopping to think why or where the problems are coming from.

141. isbvhodnvemrwvn ◴[] No.45271839{4}[source]
Renovate is not commercial, it's an own source dependabot, quite more copable at that.
replies(1): >>45272364 #
142. garbagepatch ◴[] No.45271929{7}[source]
As little code as possible to get the job done without enormous dependencies. Avoiding js and using css and html as much as possible.
replies(1): >>45272213 #
143. franky47 ◴[] No.45272063[source]
> One thing I was thinking of was sort of a "delayed" mode to updating my own dependencies.

You can do this with npm (since version 6.9.0).

To only get registry deps that are over a week old:

    $ npm install --before="$(date -v -7d)"
Source: Darcy Clarke - https://bsky.app/profile/darcyclarke.me/post/3lyxir2yu6k2s
144. VMG ◴[] No.45272068[source]
The problem here is that there might be a bug fix or even security fix that is not backported to old versions, and you suddenly have to update to a much newer version in a short time
145. lukan ◴[] No.45272158{5}[source]
I did not say to do blind copy paste.

A few lines of code can be audited.

146. sfn42 ◴[] No.45272213{8}[source]
Sounds like the perfect frontend dev to me.
replies(1): >>45272303 #
147. lodovic ◴[] No.45272283{7}[source]
Usually they write only prompts and then accept whatever is generated, ignoring all typing and linting issues
replies(1): >>45272618 #
148. skwashd ◴[] No.45272298{5}[source]
> This seems more like having several random contractors who you've never met coming into your business in the middle of night. [...] Agencies that routinely swap workers into or out of various roles at your company without asking or telling you, so you don't have any idea who the person working in the office is, what they're doing, or even if they're supposed to be there.

Sounds very similar to how global SIs staff enterprise IT contracts.

149. cluckindan ◴[] No.45272303{9}[source]
The designer, the customer, and US/EU accessibility laws heavily disagree.
replies(6): >>45272642 #>>45272704 #>>45272774 #>>45272992 #>>45274092 #>>45280222 #
150. cluckindan ◴[] No.45272318{6}[source]
You have obviously never checked the Lodash source.
replies(1): >>45273560 #
151. wereHamster ◴[] No.45272364{5}[source]
AGPL is a no-go for many companies (even when it's just a tool that touches your code and not a dependency you link to).
replies(1): >>45274342 #
152. baq ◴[] No.45272423{7}[source]
I wanted to make a joke about

   npm install stdlib 
…but double checked before and @stdlib/stdlib has 58 dependencies, so the joke preempted me.
153. baq ◴[] No.45272434{5}[source]
Age of bespoke software is here. Did you have any hard to spot non-obvious bugs in these code units?
154. catlifeonmars ◴[] No.45272548[source]
I think it definitely couldn’t hurt. You’re right it doesn’t eliminate the threat of supply chain attacks, but it would certainly reduce them and wouldn’t require much effort to implement (either manually or via script). You’re basically giving maintainers and researchers time to identify new malware and patch or unrelease them before you’re exposed. Just make sure you still take security patches.
155. Eisenstein ◴[] No.45272568{5}[source]
Reductio ad Absurdum is not a fallacy but a legitimate rhetorical technique where you can point out obvious flaws in logic by taking that logic and applying it to something that people would find ridiculous. Note that this is not the most 'extreme' version, it is the same version, using the same logic.

Example:

Argument: People should be able to build whatever they want on their own property.

Reductio ad Absurdum position: I propose to build the world's largest Jenga tower next to your house.

Note that this does not take into account any counter arguments such as 'if it falls on me you will still be liable for negligence', but it makes a point without violating the logic of the original argument. To violate that logic would indeed be a straw man.

replies(1): >>45274838 #
156. throwawayqqq11 ◴[] No.45272601[source]
This attack was only targeting user environments.

Having secrets in a different security context, like root/secretsuser-owned secret files only accessible by the user for certain actions (the simplest way would be eg. sudoers file white listing a precise command like git push), which would prevent arbitrary reads of secrets.

The other part of this attack, creating new github actions, is also a privilege, normal users dont need to exercise that often or unconstrained. There are certainly ways to prevent/restrict that too.

All this "was a supply chain attack" fuzz here is IMO missing the forest for the trees. Changing the security context for these two actions is easier to implement than supply chain analysis and this basic approach is more reliable than trusting the community to find a backdoor before you apply the update. Its security 101. Sure, there are post-install scripts that can attack the system but that is a whole different game.

replies(1): >>45272776 #
157. 2muchcoffeeman ◴[] No.45272618{8}[source]
Prompts? React and Angular came out over 10 years ago. The left pad incident happened in 2016.

Let me assure you, devs were skeptical about all this well before AI.

158. catlifeonmars ◴[] No.45272623[source]
That works fine if you have few dependencies (obviously this is a good practice) and you have time to vet all updates and determine whether a vulnerability impacts your particular code, but that doesn’t scale if you’re a security organization at, say, a small company.
159. cmckn ◴[] No.45272633{3}[source]
In that specific scenario, sure; but I don't think that's a meaningful guardrail for a business.
160. Philadelphia ◴[] No.45272642{10}[source]
How is javascript required for accessibility? I wasn’t aware of that.
replies(1): >>45272968 #
161. whstl ◴[] No.45272644{5}[source]
People pushing random throwaway packages is not the issue.

A lot of the culture is built by certain people who make a living out of package maximalism.

More packages == more eyballs == more donations.

They have an agenda that small packages are good and made PRs into popular packages to inject their junk into the supply chain.

162. NackerHughes ◴[] No.45272704{10}[source]
The designer wants huge amounts of screen space wasted on unnnecessary padding, massive Fisher-Price rounded corners, and fancy fading and sliding animations that get in the way and slow things down. (Moreover, the designer just happens to want to completely re-design everything a few months later.)

The customer “ooh”s and “aah”s at said fancy animations running on the salesman’s top of the line macbook pro and is lured in, only realising too late that they’ve been bitten in the ass by the enormous amount of bloat that makes it run like a potato on any computer that costs less than four thousand dollars.

And US/EU laws are written by clueless bureaucrats whose most recent experience with technology is not even an electric typewriter.

What’s your point?

replies(3): >>45273543 #>>45273548 #>>45275705 #
163. whstl ◴[] No.45272774{10}[source]
The designer already disagrees with accessibility laws. Contrast is near zero.
164. ◴[] No.45272776{3}[source]
165. wolvesechoes ◴[] No.45272896[source]
> “Reduce your transitive dependencies” is not a reasonable suggestion. It’s similar to “rewrite all the Linux kernel modules you need from scratch” or “go write a web browser”.

Oh please, do not compare writing bunch of utilities for you "app" with writing a web browser.

166. lukan ◴[] No.45272950{7}[source]
The difference is, the dependency can change and is usually way harder to audit. Subfolders in subfolder, 2 lines here in a file, 3 line there vs locking at some files and check what they do.
167. boesboes ◴[] No.45272968{11}[source]
It is not. In fact, it is all the modern design sensibilities and front-end frameworks that make it nearly impossible to make accessible things.

We once had the rule HTML should be purely semantic and all styling should be in CSS. It was brilliant, even though not everything looked as fancy as today.

replies(1): >>45273553 #
168. sfn42 ◴[] No.45272992{10}[source]
A11y is mostly handled by just using semantic html.

The designer, in my experience, is totally fine with just using a normal select element, they don't demand that I reinvent the drop-down with divs just to put rounded corners on the options.

Nobody cares about that stuff. These are minor details, we can change it later if someone really wants it. As long as we're not just sitting on our hands for lack of work I'm not putting effort into reinventing things the browser has already solved.

replies(2): >>45273573 #>>45274188 #
169. PeterStuer ◴[] No.45273074[source]
Not you. But one would expect major cybersecurity vendors such as Crowdstrike to screen their dependencies, yet they are all over the affected list.
replies(1): >>45277284 #
170. xorcist ◴[] No.45273210{5}[source]
That hit much too close to reality. It's exactly like that. Even the names were spot on!
171. mike_hearn ◴[] No.45273237{5}[source]
In that era JavaScript was also loaded with security issues. That's why browsers had to invest so much in kernel sandboxing. Securing JavaScript VMs written by hand in C++ is a dead end, although ironically given this post, it's easier when they're written in Java [1]

But the reason Java is more secure than JavaScript in the context of supply chain attacks is fourfold:

1. Maven packages don't have install scripts. "Installing" a package from a Maven repository just means downloading it to a local cache, and that's it.

2. Java code is loaded lazily on demand, class at a time. Even adding classes to a JAR doesn't guarantee they'll run.

3. Java uses fewer, larger, more curated libraries in which upgrades are a more manual affair involving reading the release notes and the like. This does have its downsides: apps can ship with old libraries that have unfixed bugs. Corporate users tend to have scanners looking for such problems. But it also has an upside, in that pushing bad code doesn't immediately affect anything and there's plenty of time for the author to notice.

4. Corporate Java users often run internal mirrors of Maven rather than having every developer fetch from upstream.

The gap isn't huge: Java frameworks sometimes come with build system plugins that could inject malware as they compile the code, and of course if you can modify a JAR you can always inject code into a class that's very likely to be used on any reasonable codepath.

But for all the ragging people like to do on Java security, it was ahead of its time. A reasonable fix for these kind of supply chain attacks looks a lot like the SecurityManager! The SecurityManager didn't get enough adoption to justify its maintenance costs and was removed, partly because of those factors above that mean supply chain attacks haven't had a significant impact on the JVM ecosystem yet, and partly due to its complexity.

It's not clear yet what securing the supply chain in the Java world will look like. In-process sandboxing might come back or it might be better to adopt a Chrome-style microservice architecture; GraalVM has got a coarser-grained form of sandboxing that supports both in-process and out-of-process isolation already. I wrote about the tradeoffs involved in different approaches here:

https://blog.plan99.net/why-not-capability-languages-a8e6cbd...

[1] https://medium.com/graalvm/writing-truly-memory-safe-jit-com...

172. rkagerer ◴[] No.45273291[source]
> sort of a "delayed" mode

That's the secret lots of enterprises have relied on for ages. Don't be bleeding edge, let the rest of the world gineau pig the updates and listen for them to sound the alarm if something's wrong. Obviously you do still need to pay attention to the occasional, major, hot security issues and deal with them in a swift fashion.

Another good practice is to control when your updates occur - time them when it's ok to break things and your team has the bandwidth to fix things.

This is why I laughed hard when Microsoft moved to aggressively push Windows updates and the inevitable borking it did to people's computers at the worst possible times ("What's that you said? You've got a multi-million dollar deliverable pitch tomorrow and your computer won't start due to a broken graphics driver update?). At least now there's a "delay" option similar to what you described, but it still riles me that update descriptions are opaque (so you can't selectively manage risk) and you don't really have the degree of control you ought to.

173. robertlagrant ◴[] No.45273321[source]
> As a user of npm-hosted packages in my own projects, I'm not really sure what to do to protect myself. It's not feasible for me to audit every single one of my dependencies, and every one of my dependencies' dependencies, and so on. Even if I had the time to do that, I'm not a typescript/javascript expert, and I'm certain there are a lot of obfuscated things that an attacker could do that I wouldn't realize was embedded malware.

I think Github's Dependabot can help you here. You can also host your own little instance of DependencyTrack and keep up to date with vulnerabilities.

174. silon42 ◴[] No.45273381[source]
IMO, one thing I like in npm packages is that that usually they are small, and they should ideally converge towards stability (frozen)...

If they are not, something is bad and the dependency should be "reduced" if at all possible.

175. heavyset_go ◴[] No.45273387[source]
If your employer paid your dependencies' verified authors to provide them licensed and signed software, you wouldn't have to rely on a free third party intermediary with a history of distributing massive amounts of malware for your security.
176. wvh ◴[] No.45273513[source]
As a security guy, for years, you get laughed out of the room suggesting devs limit their dependencies and don't download half of the internet while building. You are an obstruction for making profit. And obviously reading the code does very little since modern (and especially Javascript) code just glues together frameworks and libraries, and there's no way a single human being is going to read a couple million lines of code.

There are no real solutions to the problem, except for reducing exposure somewhat by limiting yourself to a mostly frozen subset of packages that are hopefully vetted more stringently by more people.

replies(9): >>45273591 #>>45274145 #>>45274168 #>>45274297 #>>45275495 #>>45275734 #>>45276496 #>>45277631 #>>45279275 #
177. cluckindan ◴[] No.45273543{11}[source]
Wow, those are some jaded and cynical views.
178. wvh ◴[] No.45273548{11}[source]
I think their point is that you might not have much of a choice, taking laws and modern aesthetic and economic concerns into consideration.

We "in the know" might agree, but we're not going to get it sold.

179. cluckindan ◴[] No.45273553{12}[source]
JS is in fact required for AA level compliance in some cases, usually to retain/move focus appropriately, or to provide expected keyboard controls.

https://www.w3.org/WAI/WCAG22/Techniques/#client-side-script

Also, when was that semantic HTML rule? You make it sound like ancient history, but semantic HTML has only been a thing since HTML5 (2008).

replies(4): >>45273635 #>>45273779 #>>45273867 #>>45273885 #
180. latexr ◴[] No.45273560{7}[source]
The point here isn’t a specific library. It’s not even one specific language or runtime. No one is talking about literally five functions. Let’s not be pedantic and lose sight of the major point.
replies(1): >>45273568 #
181. cluckindan ◴[] No.45273568{8}[source]
I get that, but if you’ve ever tried to extract a single utility function from lodash, you know that it may not be as simple as copy-pasting a single function.
replies(1): >>45274322 #
182. cluckindan ◴[] No.45273573{11}[source]
The word ”mostly” is the crux of the issue.
183. mgaunard ◴[] No.45273591[source]
I've always been very careful about dependencies, and freezing them to versions that are known to work well.

I was shocked when I found out that at some of the most profitable shops, most of their code is just a bunch of different third-party libraries badly cobbled together, with only a superficial understanding of how those libraries work.

184. lexicality ◴[] No.45273635{13}[source]
You only need to use scripts to move focus and provide keyboard controls if you have done something to mess with the focus and break the standard browser keyboard controls.

If you're using HTML/CSS sensibly then it's accessible from the get-go by dint of the browser being accessible.

> Also, when was that semantic HTML rule? You make it sound like ancient history, but semantic HTML has only been a thing since HTML5 (2008).

HTML5 added a million new tags, but HTML4 had plenty of semantic tags that people regularly ignored and replaced with <div>, for example <p>, <em>, <blockquote>...

replies(2): >>45276989 #>>45277224 #
185. 63stack ◴[] No.45273746{4}[source]
A log4j level vulnerability happens again. Do you need 10 minutes to update? 1 hour? 1 day? 1 week? Multiple months? The more you are drifting behind on updates, the worse it gets, which also affects every one of your users, your business, and might be the end of your project.
replies(1): >>45274132 #
186. sfn42 ◴[] No.45273779{13}[source]
In some cases, sure.

I'm not saying the ideal frontend dev writes no JS. I'm saying they write as little as possible. Some times you need JS, nothing wrong with that. The vast majority of the time you don't. And if you do I'd say it's a self-imposed requirement (or a direct/indirect result of a self imposed requirement) most of the time.

replies(1): >>45274152 #
187. tjpnz ◴[] No.45273796[source]
Easier said than done when your ecosystem of choice took the Unix philosophy of doing one thing well, misinterpreted it and then drove it off a cliff. The dependency tree of a simple Python service is incomparable to a Node service of similar complexity.
188. ClikeX ◴[] No.45273825{7}[source]
If you won't, do you expect the maintainer of some micro package to do that?
189. skipchris ◴[] No.45273867{13}[source]
The web standards project was founded in 1998.

https://www.webstandards.org/about/index.html

190. GoblinSlayer ◴[] No.45273885{13}[source]
Some of those are fixes for misbehaving javascript like disabling nonessential alerts, stopping blinking, reducing animation; some are antipatterns like opening new windows, changing link text, colors, scrolling.
191. user34283 ◴[] No.45273892{4}[source]
Just like it's going to make you a better engineer if you design the microchips in your workstation yourself instead of buying an x86 CPU.

It's still neither realistic nor helpful advice.

192. Hilift ◴[] No.45273935[source]
> I'm not really sure what to do

You need an EDR and code repo scanner. Exploring this as a technical problem of the infrastructure will accomplish. The people that create these systems are long gone and had/have huge gaps in their capabilities to stop creating these problems.

193. zelphirkalt ◴[] No.45274085{6}[source]
Ha, that's a funny attitude. And here I was thinking, that mostly doing backend work, I rather make the best out of the situation, if I have to do frontend dev, and try to do "real development" by writing trivial things myself, instead of worsening the situation by gluing together mountains of bloat.
194. zelphirkalt ◴[] No.45274092{10}[source]
The designer might only disagree, if they know a lot about frontend technology, and are not merely clicking together a figma castle.

But the middle management might actually praise the developer, because they "get the job done" with the minimal effort (so "efficient"!).

195. cesarb ◴[] No.45274132{5}[source]
> A log4j level vulnerability happens again. [...] The more you are drifting behind on updates, the worse it gets

That one is a funny example in this context. If you were drifting far behind on updates, so far that you were still on the obsolete log4j 1.x, you were immune to that vulnerability (log4shell). That obsolete log4j version had other known vulnerabilities, but most of them on rarely used optional components, and none of them affected basic uses of it to log to the console or disk. And even better, there were so many people using that obsolete log4j version, that a binary compatible fork quickly appeared (reload4j) which just removes the vulnerable components (and fixes everything that wasn't removed); it takes 10 minutes to update to it, or at worst 1 hour if you have to tweak your dependencies to exclude the log4j artifact.

(And then it happened again, this time with Spring (spring4shell): if you were far behind on updates, so far that you were still on the very old but still somewhat supported Java 8, you were immune to that vulnerability.)

196. darkwater ◴[] No.45274137{3}[source]
Not on HN, the land of "you should use a SaaS or PaaS for that (because I might eventually work there and make money)" or "I don't want to maintain that code because it's not strictly related to my CRUD app business! how you dare!"
197. p0w3n3d ◴[] No.45274145[source]
> You are an obstruction for making profit.

This explains a lot. Really, this is the great reason of why the society is collapsing as we speak.

"There should be no DRM in phones" - "You Are An Obstruction To Making Profit".

"People should own their devices, we must not disallow custom software on it" - "YAAOTMP"

"sir, the application will weigh 2G and do almost nothing yet, should we minify it or use different framework?" - "YAAOTMP".

"Madame, this product will cost too much and require unnecessary payments" - "YAAOTMP"

Etc. etc. Like in this "Silicon Valley" comedy series. But for real, and affecting us greatly.

replies(1): >>45275283 #
198. zelphirkalt ◴[] No.45274152{14}[source]
Recently I took a little dive into making some pages, that have fallback for when the user doesn't run JS. Those pages are polling an API and displaying updated status. I made sure the pages can be reloaded and show updated status information, and telling the user, that they can simply refresh the page to get that updated information, but only showing that hint about reloading, when they do not run JS. Thus I built a workflow, that people can use whether or not they run JS. I did that, because I think it is the right thing, and because I often preach, that most sites should work without JS.

For me as a mostly backend dev, this was actually quite easy to achieve. Tiny modification of the backend API, some work in the frontend using JS to remove hints that should not show when JS is running, and voila, it works. Of course my pages are very simple in nature, but the same principles can be applied to larger pages. One could even link/direct to different pages, depending on the user running JS or not, and then have a workflow without JS and one with JS. It is all possible and only a matter of wanting to make an effort. Of course, modern JS frameworks do not really encourage this kind of design. Though server side rendering becomes more popular these days, I don't think we are quite there yet.

A page that is blank when not running JS has exactly zero accessibility.

199. jen729w ◴[] No.45274168[source]
At my previous enterprise we had a saying:

Security: we put the ‘no’ in ‘innovation’.

200. zelphirkalt ◴[] No.45274188{11}[source]
I hope in the future I can work with that kind of designer. Maybe it is just my limited experience, but in that limited experience, web designers care way too much about details and design features/ideas/concepts, that are not part of HTML or CSS and then frontend developers would have to push back and tell the web designer, that form follows function and that the medium they design for is important. Basic design principles actually, that the designers should know themselves, just like they should know the medium they are targeting (semandic HTML, CSS, capabilities of them both, a tiny bit about JS too), to keep things reasonable. But most frontend devs are happy to build fancy things with JS instead of pushing back when it matters. And not so many frontend devs want to get into CSS deeply and do everything they can to avoid JS. So needless things do get implemented all the time.
201. 999900000999 ◴[] No.45274297[source]
The "solution" would be using a language with a strong standard library and then having a trusted 3rd party manually audit any approved packages.

THEN use artifactory on top of that.

That's boring and slow though. Whatever I want my packages and I want them now. Apart of the issue is the whole industry is built upon goodwill and hope.

Some 19 year old hacked together a new front end framework last week, better use it in prod because why not.

Occasionally I want to turn off my brain and just buy some shoes. The Timberland website made that nearly impossible last week. When I gave up on logging in for free shipping and just paid full price, I get an email a few days later saying they ran out of shoes.

Alright. I guess Amazon is dominant for a reason.

replies(5): >>45274427 #>>45274782 #>>45274799 #>>45275228 #>>45279075 #
202. zelphirkalt ◴[] No.45274322{9}[source]
If you are going to be that specific, then it would be good to post an example. If I remember correctly, lodash has some functions, that would be table stakes in functional languages, or easily built in functional languages. If such a function is difficult to extract, then it might be a good candidate to write in JS itself, which does have some of the typical tools, like map, reduce, and things like compose are easy to write oneself and part of every FP beginner tutorial. If such a function is difficult to extract, then perhaps lodash's design is not all that great. Maybe one could also copy them from elsewhere, where the code is more modular.

But again, if the discussion is going to be that specific, then you would need to provide actual examples, so that we could judge, whether we would implement that ourselves or it would be difficult to do so. Note, that often it is also not required for ones use-case, to have a 100% matching behavior either. The goal is not to duplicate lodash. The purpose of the extracted or reimplemented function would still be ones own project, where the job of that function might be much more limited.

replies(1): >>45275698 #
203. 1oooqooq ◴[] No.45274324[source]
would you pay a subscription for a vetted repo?
204. 1oooqooq ◴[] No.45274342{6}[source]
good. that's the point.

agpl is a no go for companies not intending to ever contribute anything back. good riddance.

205. 1oooqooq ◴[] No.45274357{3}[source]
wonder how long for llms to spew the malware in those packages along the code when you request the same functionality.
206. silverliver ◴[] No.45274427{3}[source]
This is the right answer. I'm willing to stick my head out and assert that languages with a "minimal" standard library are defective by design. The argument of APIs being stuck is mood with approaches like Rust's epocs or "strict mode".

Standard libraries should include everything needed to interact with modern systems. This means HTTP parsing, HTTP requests, and JSON parsing. Some laguages are excellent (like python), while some are half way there (like go), and some are just broken (Rust).

External libraries are for niche or specialized functionality. External libraries are not for functionality that is used by most modern software. To put your head in the ground and insist otherwise is madness and will lead to ridiculous outcomes like this.

replies(7): >>45275250 #>>45275311 #>>45275318 #>>45275441 #>>45275539 #>>45276844 #>>45277579 #
207. fatchan ◴[] No.45274653{3}[source]
1.2 million weekly downloads to this day, when we've had builtin padStart since ES2017.

Yes, I remember thinking at the time "how are people not ashamed to install this?"

208. user3939382 ◴[] No.45274782{3}[source]
I don’t recall hearing about constant supply chain attacks with CPAN
replies(2): >>45275026 #>>45275366 #
209. Loudergood ◴[] No.45274799{3}[source]
I agree, it always seems to be NPM, and there's a reason for that.
210. TZubiri ◴[] No.45274838{6}[source]
Just wanted to comment that chatgpt also wrongly categorizes this as reductio ad absurdum and strawman.

This is very dead internet theory, but not automated, someone copied my comment, gave it to chatgpt, and returned the chatgpt answer, presumably passing it off as their own, but in effect we are talking with chatgpt lol.

replies(1): >>45275638 #
211. bleuarff ◴[] No.45275026{4}[source]
Because it's never been considered an interesting target, compared to npm's reach?
212. ivan_gammel ◴[] No.45275228{3}[source]
Java + Spring Boot BOM + Maven Central (signed jars) does fit the description.
213. CaptainOfCoit ◴[] No.45275250{4}[source]
> External libraries are not for functionality that is used by most modern software.

Where do you draw the line though? It seems like you mostly spend your time writing HTTP servers reading/writing JSON, but is that what everyone else also spends their time doing? You'll end up with a standard library weighing GBs, just because "most developers write HTTP servers", which doesn't sound like a better solution.

I'm willing to stick my head the other way, and say I think the languages today are too large. Instead, they should have a smaller core, and the language designed in a way that you can extend the language via libraries. Basically more languages should be inspired by Lisps and everything should be a library.

replies(2): >>45275344 #>>45278316 #
214. ivan_gammel ◴[] No.45275283{3}[source]
Death comes to corp CEO, he screams YAAOTMP, death leaves shocked. Startup CEO watches the scene. His jedi sword turns from blue to red.
215. Ygg2 ◴[] No.45275311{4}[source]
> Standard libraries should include everything needed to interact with modern systems.

So, databases? Which then begs the question, which - Postgres, MySQL, SQLite, MS SQL, etc.? And some NoSQL, because modern systems might need it.

That basically means you need to pull in everything and the kitchen sink. And freeze it in time (because of backwards compatibility). HTML, HTTP parsing, and SHA1024 are perfectly reasonable now; wait two decades, and they might be as antiquated as XML.

So what your language designers end up, is having to work on XML parsing, HTTP, JSON libraries rather than designing a language.

If JS way is madness, having everything available is another form of madness.

replies(1): >>45277331 #
216. Arcterus ◴[] No.45275318{4}[source]
> Standard libraries should include everything needed to interact with modern systems.

This is great when the stdlib is well-designed and kept current when new standards and so on become available, but often "batteries included" approaches fail to cover all needs adequately, are slow to adopt new standards or introduce poorly designed modules that then cannot be easily changed, and/or fail to keep up-to-date with the evolution of the language.

I think the best approach is to have a stdlib of a size that can be adequately maintained/improved, then bless a number of externally developed libraries (maybe even making them available in some official "community" module or something with weaker stability guarantees than the stdlib).

I find it a bit funny that you specifically say HTTP handling and JSON are the elements required when that's only a small subset of things needed for modern systems. For instance, cryptography is something that's frequently required, and built-in modules for it often suck and are just ignored in favor of external libraries.

EDIT: actually, I think my biggest issue with what you've said is that you're comparing Python, Go, and Rust. These languages all have vastly different design considerations. In a language like Python, you basically want to be able to just bash together some code quickly that can get things working. While I might dislike it, a "batteries included" approach makes sense here. Go is somewhat similar since it's designed to take someone from no knowledge of the language to productive quickly. Including a lot in the stdlib makes sense here since it's easier to find stuff that way. While Rust can be used like Python and Go, that's not really its main purpose. It's really meant as an alternative to C++ and the various niches C/C++ have dominated for years. In a language like that, where performance is often key, I'd rather have a higher quality external library than just something shoved into the stdlib.

replies(3): >>45275674 #>>45285262 #>>45286238 #
217. smaudet ◴[] No.45275344{5}[source]
I don't think things being libraries (modular) is at odds with a standard library.

If you have a well vetted base library, that is frequently reviewed, under goes regular security and quality checks, then you should be minimally concerned about the quality of code that goes on top.

In a well designed language, you can still export just what you need, or even replace parts of that standard library if you so choose.

This approach even handles your question: as use cases become more common, an active, invested* community (either paying or actively contributing) can add and vet modules, or remove old ones that no longer serve an active purpose.

But as soon as you find yourself "downloading the web" to get stuff done, something has probably gone horribly wrong.

replies(1): >>45275618 #
218. AdamN ◴[] No.45275366{4}[source]
That was a different era. The velocity of change is 100x now and the expectation for public libraries to do common things is 100x higher as well.
replies(1): >>45276159 #
219. LtWorf ◴[] No.45275373[source]
I never understood the "let's always pin everything to the latest version and let's update the pinned versions every day"… what is even the point of this exercise? Might as well not pin at all.
220. jajko ◴[] No.45275441{4}[source]
Java is around for much longer, has exactly same architecture re transitive dependencies, yet doesn't suffer from weekly attacks like these that affect half of the world. Not technically impossible, yet not happening (at least not at this scale).

If you want an actual solution, look for differences. If you somehow end up figuring out its about type of people using those, then there is no easy technical solution.

221. illegally ◴[] No.45275452[source]
Rather than the user doing that "delay" installation, it would be a good idea if the package repository (i.e. NPM) actually enforced something like that.

For example, whenever a new version of a package is released, it's published to the repository but not allowed to be installed for at least 48 hours, and this gives time to any third-party observers to detect a malware early.

222. epage ◴[] No.45275495[source]
This comes across as not being self-aware as to why security as laughed out of rooms: I read this as you correctly identifying some risks and said only offered the false-dichotomouy of solutions of "risk" and "no risk" without talking middle grounds between the two or finding third-ways that break the dichotomy.

I could just be projecting my own bad experiences with "security" folks (in quotes as I can't speak to their qualifications). My other big gripe is when they don't recongnize UX as a vital part of security (if their solution is unsuable, it won't be used).

replies(2): >>45275694 #>>45278882 #
223. goku12 ◴[] No.45275539{4}[source]
> This is the right answer. I'm willing to stick my head out and assert that languages with a "minimal" standard library are defective by design.

> Standard libraries should include everything needed to interact with modern systems. This means HTTP parsing, HTTP requests, and JSON parsing.

There is another way. Why not make the standard library itself pluggable? Rust has a standard library and a core library. The standard library is optional, especially for bare-metal targets.

Make the core library as light as possible, with just enough functionality to implement other libraries, including the interfaces/shims for absolutely necessary modules like allocators and basic data structures like vectors, hashmaps, etc. Then move all other stuff into the standard library. The official standard library can be minimal like the Rust standard library is now. However, we should be able to replace the official standard library with a 3rd party standard library of choice. (What I mean by standard library here is the 'base library', not the official library.) Third party standard library can be as light or as comprehensive as you might want. That also will make auditing the default codebase possible.

I don't know how realistic this is, but something similar is already there in Rust. While Rust has language features that support async programming, the actual implementation is in an external runtime like Tokio or smol. The clever bit here is that the other third party async libraries don't enforce or restrict your choice of the async runtime. The application developer can still choose whatever async runtime they want. Similarly, the 3rd party standard library must not restrict the choice of standard libraries. That means adding some interfaces in the core, as mentioned earlier.

replies(1): >>45286400 #
224. TylerE ◴[] No.45275618{6}[source]
IMO Python 2 was rhetorical gold standard for getting the std lib right. Mostly batteries included, but not going totally insane with it.
225. Eisenstein ◴[] No.45275638{7}[source]
It wouldn't be that annoying if it weren't wrong, I guess.
226. JoBrad ◴[] No.45275674{5}[source]
The tradeoff of “batteries included” vs not is real: Python developers famously reach for community libraries like requests right away to avoid using the built-in tooling.
replies(2): >>45276962 #>>45279966 #
227. romaniv ◴[] No.45275694{3}[source]
I've been a web developer for over two decades. I have specific well-tested solutions for avoiding external JS dependencies. Despite that, I have the exact same experience as the above security guy. Most developers love adding dependencies.
replies(1): >>45276366 #
228. cluckindan ◴[] No.45275698{10}[source]
Let’s start with something simple, like difference().

https://github.com/lodash/lodash/blob/main/dist/lodash.js#L7...

So you also need to copy isArrayLikeObject, baseDifference and baseFlatten.

For baseDifference, you also need to copy arrayMap and baseUnary.

For baseFlatten, you also need to copy arrayPush.

For isArrayLikeObject, you also need to copy isArrayLike and isObjectLike.

For isArrayLike, you also need to copy isLength and isFunction.

For isFunction, you also need to copy isObject and baseGetTag.

For baseGetTag, you also need to copy getRawTag and objectToString.

I don’t have time to dig any deeper, just use tree-shaking ffs.

replies(1): >>45276479 #
229. wbl ◴[] No.45275705{11}[source]
I think blind people should be able to use websites.
230. CerebralCerb ◴[] No.45275734[source]
The post you replied to suggested a real solution to the problem. It was implemented in my current org years ago (after log4j) and we have not been affected by any of the malware dependencies that has happened since.
231. Sophira ◴[] No.45276159{5}[source]
Perl and CPAN are still a thing, much as people would like to think otherwise.
232. dec0dedab0de ◴[] No.45276196{3}[source]
a long enough delay would solve the issue for account takeovers, and bold attacks like this.

It would not solve for a bad actor gaining trust over years, then contributing seemingly innocent code that contains an exploitable bug with enough plausible deniability to remain on the team after it is patched.

233. zelphirkalt ◴[] No.45276479{11}[source]
OK in this case it looks like it is doing a lot of at runtime checking of arguments to treat them differently, based on what type of argument they are. If we restrict use to only work with arrays, or whatever we have in our project, where we need `difference`, then it should become much simpler and an easy rewrite. An alternative could be to have another argument, that is the function that gives us the `next` thing. Then the logic for that is to be specified by the caller.

Tree shaking however, will not help you, if you have to first install a library using NPM. It will only help you reduce overhead in the code served to a browser. Malicious code can run much earlier, and would be avoided, if you rewrite or extract relevant code from a library, avoiding to install the library using NPM. Or is there some pre-installation tree shaking, that I am unaware of? That would actually be interesting.

replies(1): >>45277142 #
234. user34283 ◴[] No.45276496[source]
Your proposed solution does not work for web applications built with node packages.

Essentials tools such as Jest add 300 packages on their own.

You already have hundreds to thousands of packages installed, fretting over a few more for that DatePicker or something is pretty much a waste of time.

235. 999900000999 ◴[] No.45276844{4}[source]
It's not an easy problem to solve.

Doing it the right way would create friction, developers might need to actually understand what the code is doing rather than pulling in random libraries.

Try explaining to your CTO that development will slow down to verify the entire dependency chain.

I'm more thinking C# or Java. If Microsoft or Oracle is providing a library you can hope it's safe.

You *could* have a development ecosystem called Safe C# which only comes with vetted libraries and doesn't allow anything else.

I'm sure other solutions already exist though.

replies(2): >>45277609 #>>45278764 #
236. Natfan ◴[] No.45276962{6}[source]
I wasn't even aware there _was_ built-in tooling...
237. kbolino ◴[] No.45276989{14}[source]
IMO <em> is a terrible example.

For ca. ten years, the advice was to pointlessly "replace <i> with <em> and <b> with <strong>" and it utterly screwed over most new web developers' understanding of semantic tags. There are many reasons to use italics (and they vary between languages) but "emphasis" is just one of them, and none of the others ever materialized as tags.

It would have been far better to have recommended <i class="emphasis"> and <i class="media-title"> and <i class="snarky-aside"> etc. than to have added the <em> tag and said "just use it instead of <i>".

238. cluckindan ◴[] No.45277142{12}[source]
I guess that pre-installation tree shaking in this case is installing ’lodash.difference’ instead of ’lodash’. :)
239. cluckindan ◴[] No.45277224{14}[source]
”You only need to use scripts to move focus and provide keyboard controls if you have done something to mess with the focus and break the standard browser keyboard controls.”

That is straight up untrue. Some ARIA patterns require developers to implement focus management and keyboard access from scratch.

For example, ”Correct implementation of the tree role requires implementation of complex functionality that is not needed for typical site navigation that is styled to look like a tree with expandable sections.”

But sometimes you do need that kind of widget for something else.

https://www.w3.org/WAI/ARIA/apg/patterns/treeview/

replies(1): >>45278320 #
240. rpodraza ◴[] No.45277284[source]
It looks like they actually got infected as well. So it's not only that, their security practices seem crap
241. ivan_gammel ◴[] No.45277331{5}[source]
It is not madness. Java is a good example of rich and modular standard library. Some components of it are eventually deprecated and removed (e.g. Applets) and this process takes long enough. Its standard library does include good crypto and http client, database abstraction API (JDBC) which is implemented by database drivers etc.
replies(2): >>45278010 #>>45278133 #
242. pjmlp ◴[] No.45277579{4}[source]
Spot on, I rather have a Python, Java,.NET,.. standard library, that may have a few warts, but works everywhere there is full compliant implementation, than playing lego, with libraries that might not even support all platforms, and be more easily open to such attacks.

Is java.util.logging.Logger not that great?

Sure, yet everyone that used it had a good night rest when Log4J exploit came to be.

replies(1): >>45278516 #
243. pjmlp ◴[] No.45277609{5}[source]
Why?

This is a standard practice in most places I have worked, CI/CD only allowed to use internal repos, and libraries are only added after clearance.

replies(1): >>45278265 #
244. awaythrow999 ◴[] No.45277631[source]
Agree on the only solution being reducing dependencies.

Even more weird in the EU where things like Cyber Resilience Act mandate patching publicly known vulnerabilities. Cool, so let's just stay up2date? Supply-chain vuln goes Brrrrrr

245. Aldipower ◴[] No.45277692[source]
You can use Sonatype or Artifactory as an self-hosted provider for your NPM packages that keep their own NPM repository. This way you can delay and control updates. It is common enterprise practice.
246. Ygg2 ◴[] No.45278010{6}[source]
Yeah, and Java was always corporately funded, and to my knowledge no one really used neither the http client nor the XML parser. You basically have a collection of dead weight libs, that people have to begrudgingly maintain.

Granted some (JDBC) more useful than the others. Although JDBC is more of an API and less of a library.

replies(1): >>45278260 #
247. koakuma-chan ◴[] No.45278133{6}[source]
My favourite is java.awt.Robot
248. ivan_gammel ◴[] No.45278260{7}[source]
HttpClient is relatively new and getting HTTP/3 support next spring, so it’s certainly not falling into the dead weight category. You are probably confusing it with an older version from Java 1.1/1.4.

As for XML, JAXP was a common way to deal with it. Yes, there’s Xstream etc, but it doesn’t mean any of standard XML APIs are obsolete.

249. brazzy ◴[] No.45278265{6}[source]
Except that "clearance" invariably consists of bureaucratic rubber stamping and actually decreases security by making it harder and slower to fix newly discovered vulnerabilities.
replies(1): >>45278308 #
250. pjmlp ◴[] No.45278308{7}[source]
Depends on the skills of the respective DevOps security team.

There are also tools that break CI/CD based on CVE reports from existing dependencies.

251. groby_b ◴[] No.45278316{5}[source]
> everything should be a library.

That's exactly npm's problem, though. What everybody is avoiding to say is that you need a concept of "trusted vendors". And, for the "OSS accelerates me" business crowd, that means paying for the stuff you use.

But who would want that when you're busy chasing "market fit".

replies(1): >>45278443 #
252. lexicality ◴[] No.45278320{15}[source]
Sorry, I completely forgot about the existing semantic tree view element that exists and can be interacted with visually but doesn't provide any accessibility or keyboard support because the browser manufacturers decided to skip that one.

Or are you talking about a situation where the developer has implemented a custom component (aka "done something") which doesn't use the native focus system and therefore requires additional work to make accessible?

replies(1): >>45280687 #
253. CaptainOfCoit ◴[] No.45278443{6}[source]
> That's exactly npm's problem, though.

I don't think that's the problem with npm. The problem with npm is that no packages are signed, at all, so it ends up trivial for hackers to push new package versions, which they obviously shouldn't be able to do.

replies(1): >>45279111 #
254. ivan_gammel ◴[] No.45278516{5}[source]
slf4j is probably more common now than standard Logger, and it was a good night for those who used Logback as implementation.
255. bobthepanda ◴[] No.45278523{7}[source]
In my experience, generally speaking there is a kind of this developer that tries to write a language they’re familiar with, but in Javascript. As the pithy saying goes, it takes a lot of skill to write Java in every language.
256. Shorel ◴[] No.45278764{5}[source]
> Doing it the right way would create friction, developers might need to actually understand what the code is doing rather than pulling in random libraries.

Then let's add friction. Developers understanding code is what they should be doing.

CTOs understand the high cost of ransomware and disruption of service.

257. zahlman ◴[] No.45278782{7}[source]
Yes, that. I didn't want to be too spammy, especially since I honestly haven't been getting much of anything done recently (personal reasons).
258. bongodongobob ◴[] No.45278882{3}[source]
This is how our security lead is. "I've identified X as a vulnerability, recommended remediation is to remove it." "We literally can't." He pokes around finding obscure vulnerabilities and recommends removing business critical software, yet we don't have MFA, our servers and networking UIs are on the main VLAN accessable by anyone, we have no tools to patch third party software, and all of our root passwords are the same. We bring real security concerns to him like this, and they just get backlogged because his stupid tools he runs only detect software vulns. It's insanity.
259. nonethewiser ◴[] No.45279075{3}[source]
>Some 19 year old hacked together a new front end framework last week, better use it in prod because why not.

The thing is, you don't have to be this undiscerning to end up with tons of packages.

Let's init a default next.js project. How many dependencies are there?

react, react-dom, next, typescript, @types/node, @types/react, @types/react-dom.

OK so 7... seems like a lot in some sense but its still missing many reasonable dependencies. Some sort of styling solution (tailwind, styled components, etc). Some sort of http client or graphql. And more. But lets just use the base dependencies as an example. Is 7 so bad? Maybe, maybe not, but you need to go deeper. How many packages are there?

55. What are they? I have no idea, go read the lock file I guess.

All of this while being pretty reasonable.

260. carols10cents ◴[] No.45279111{7}[source]
Since Shai-Hulud scanned maintainers' computers, if the signing key was stored there too (without a password), couldn't the attackers have published signed packages?

That is, how does signing prevent publishing of malware, exactly?

replies(3): >>45283644 #>>45287865 #>>45290065 #
261. ozim ◴[] No.45279275[source]
Package registries should step up. They are doing some stuff but still NPM could do more.
262. bigstrat2003 ◴[] No.45279966{6}[source]
And yet, there are times where all I've had access to was the stdlib. I was damn glad for urllib2 at those times. It's worth it to have a batteries included stdlib, even if parts of it don't wind up being the most commonly used by the community.
replies(1): >>45283633 #
263. bigstrat2003 ◴[] No.45280222{10}[source]
As the customer, I think that's the perfect frontend dev. Fuck the JS monstrosities that people build, they are so much harder to use than plain HTML.
264. cluckindan ◴[] No.45280687{16}[source]
If by ”done something” you mean the devs made custom widgets have the proper ARIA roles so they’re usable for people who use a keyboard to navigate, or who need screen readers and their plethora of different navigation modes. This is usually the case when a suitable standard component does not exist or is not well supported across browsers. Hierarchical tri-state checkboxes come to mind.

The native focus system typically works just fine, but JS is needed for keyboard interactions and to set things like aria-activedescendant.

265. lgas ◴[] No.45281752{7}[source]
You can give an LLM access to tools that it can invoke to actually copy and paste.
266. yawaramin ◴[] No.45283633{7}[source]
The fact that there is a 'urllib2' implies that there's a 'urllib', which tells us something pretty important about the dangers of kitchen-sink standard libraries.
267. yawaramin ◴[] No.45283644{8}[source]
How did Shai-Hulud get access to maintainers' computers?
268. auraham ◴[] No.45285262{5}[source]
Related: Rust Dependencies Scare Me [1]

[1] https://vincents.dev/blog/rust-dependencies-scare-me/

269. wolvesechoes ◴[] No.45286238{5}[source]
But nothing prevents a language to have rich and OPTIONAL stdlib, so that devs can choose different solutions without linking bunch of junk they do not use.

Really, good stdlib still allows you to use better suited 3rd party libraries. Lack of good stdlib doesn't add anything.

270. qcnguy ◴[] No.45286400{5}[source]
This is the philosophy used by the Java world. Big parts of the standard library are plugin-based. For example, database access (JDBC), filesystem access (NIO), cryptography (JCA). The standard library defines the interfaces and sometimes provides a default implementation, but it can be extended or replaced.

It works well, but the downside of that approach is people complaining about how abstract things are.

271. CaptainOfCoit ◴[] No.45287865{8}[source]
> if the signing key was stored there too (without a password), couldn't the attackers have published signed packages?

Yeah, of course. Also if they hosted their private key for the signature on their public blog, anyone could use it for publishing.

But for the sake of the argument, why don't we assume people are correctly using the thing we're talking about?

272. boomlinde ◴[] No.45288106{8}[source]
In what way do you think this rebuts the message you responded to?
273. lelanthran ◴[] No.45290065{8}[source]
In past comments I said that a quick win would be to lean on certificates; those can't easily be forged once a certificate is accepted.