-
Notifications
You must be signed in to change notification settings - Fork 4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
aws-cdk: separate dependencies from devDependencies to work with pnpm #23182
Comments
I don't understand this being reclassified as a Even outside of how package managers work, surely this is a defect, not a feature request? |
@aphex do you mean executing the CLI (i.e. |
FYI the published version of |
@corymhall this came up while using SST (https://sst.dev/) with pnpm. It is using the CDK we are using it and @mrgrain we were definitely getting a runtime error from the |
@aphex I can't reproduce this with the instructions you've provided. Can you please setup a repo that reproduced the issue? However, I strongly suspect however SST is using CDK is not something that we are currently aware of and thus likely don't support. Not that we strictly wouldn't but if we don't know what they are doing.... You might want to talk to them. package.json
app.ts
Running
|
This issue has not received a response in a while. If you want to keep this issue open, please leave a comment below and auto-close will be canceled. |
bump, I will try to get to a minimal example of this as soon as I can. |
Hello |
Thanks @douddle! Has anyone checked if there's an open issue with pnpm yet? I find it notable that this issues (apparently) started to occur fairly recently and independently in two different libraries. Both times it appears to be an issue with bundled dependencies. |
@mrgrain sorry for the delay on this, holidays always pile everything on. I think I have a very minimal example showcase the issue of bundling. This assumes you have node/pnpm installed. I am running node 16.17.0 and pnpm 7.18.2 Step 1: Project init mkdir aws-cdk-23182
cd aws-cdk-23182
pnpm init
pnpm i aws-cdk
pnpm i yaml Step 2: Change to module type Step 3: Create test import { serialize } from 'aws-cdk/lib/util/yaml-cfn.js'
console.log(serialize) Step 3: Run test node . Step 4: Expected Error Error [ERR_PACKAGE_PATH_NOT_EXPORTED]: Package subpath './types' is not defined by "exports" Step 5: Update package json "pnpm": {
"packageExtensions": {
"aws-cdk": {
"dependencies": {
"yaml": "1.10.2"
}
}
}
} Step 6: Kill and start over pnpx npkill
pnpm i Step 7: Run again node . Step 8: 🥳 Not totally following the bundle mentality for this package, so hoping you can help me understand. Is it simply the thought that tree shaking will make this a smaller install in ci environments? As package managers generally install all the |
No worries! I feel you with the Christmas time 😅 Thanks for the repro. That will be super helpful. I guess the The bundling strategy is driven from a supply chain security perspective. Every released CLI package will work within the tested parameters, no matter if a dependency has been compromised or vandalized. |
@mrgrain Not sure about the module type, I didn't try it without but it's just what is being used in our projects. Though seeing that Thanks for the bundle explanation, makes sense with issues like node-ipc or even leftpad. Though I wonder now if things are actually bundling as expected seeing that this package is reaching out into my However I would think pinning dependencies would also get you a similar result? If I remember correctly you cannot overwrite npm versions anymore, you can unpublish and republish but this has time restrictions, and unpublish after 72 hours requires manual intervention. The security downside to this strategy is that users are not able to do patch/minor updates to dependent packages that have security fixes. So now its the responsibility of the |
Might be worth noting that this is an issue for me with npm as a package manager as well (using the same sort of repro code). npm would never install the yaml package as it is nowhere in the dependency list for aws-cdk and instead gets "downgraded" to dev dependency. |
@zackheil that is an odd one, any chance you have a ENV laying around that might make npm think its production only time? Or maybe this situation is when you do a ci or production build? Either way this is a great point as it is totally possible this works fine in dev mode (when devDependencies are installed) but fails in a CI or production environment ref: |
FYI I'm on annual leave and will need more time to get to the bottom of some questions for this. The solution likely won't be to stop bundling (at least on the short term, and I appreciate the feedback on it), but sorting out the dependencies in package.json and/or the bundle itself. |
The issue is here: import { serialize } from 'aws-cdk/lib/util/yaml-cfn.js' This was never actually supported. Some people did it, and it worked for them. We then moved to bundling the CLI sources, and left the original source in place to not break people for whom this happened to work. (That does not include making it work for new people!) But the CLI package's contract is that it can be used as a CLI -- that's it. The fact that the CLI package doesn't advertise a |
Chiming in here as I work on SST and wrote the code that is impacted by this. We solved this for our users by making these packages direct dependencies of our package. For everyone else in this thread, there's plenty of issues across this repo where AWS has made it clear they're not interested in supporting programmatic access (for example #20196) . We made the decision at SST to take the risk and call into it programmatically anyway so keeping it working is probably our responsibility. The reason this is worth it for us is there are a lot of performance benefits - which are important because CDK has many performance issues to begin with so every little improvement makes a meaningful difference. I will say the approach the CDK project takes to bundling feels complicated and non-standard. Is there really a good reason to deviate from how 99% of other npm packages work? The security concern seems odd to me unless I'm misunderstanding as you can pin versions - it only protects against compromising the immutable constraints of npm - which CDK itself is still subject to. Very few projects seem to opt for this tradeoff. |
Honestly surprising to me. Most of the time spent in a CDK operation will be in app synthesis, not in starting the CLI. Are you avoiding JVM cold start in some way by doing this?
You didn't specify, so I'm not quite sure what the 99% standard is you are referring to. Is it
The NPM ecosystem supports pinning, but pinning happens at the wrong time. Version pinning doesn't happen when we publish the CLI, pinning happens when you install the CLI. If we publish the CLI with a dependency: // CDK CLI package.json
{
"dependencies": {
"our-dependency": "1.2.3" // Very conscientiously avoiding a ^ or ~ here
}
}
// our-dependency package.json
{
"dependencies": {
"leftpad": "^2.3.16" // latest greatest
}
} Then immediately after the moment we test against In other words, pinning works for website builders (people who have a You might be tempted to say "aha, I know about We asked Yarn to reconsider their position, but they have plans to support shrinkwrapping, leaving us no other choice than to bundle. |
By the way, you should have a look at this PR: #22836 |
@rix0rrr thanks for the explanation and the details. I can understand why you all are trying to keep security a priority and package manipulation/tampering is clearly a concern for a CLI that deals with a companies full infrastructure. However my original issue was with pnpm support for this package. Please correct me if I am wrong but I believe it does clean up some of your security concern by default as Then again if the official stance is simply "using this package as a code dependency is not supported, it is meant to be a CLI only" then I guess that also ends this conversation. This does seem like a roadblock for the community though, clearly the code here is important and building on top of the I also noticed your team distributes a signed zip version of the CDK, I was thinking this seems like a great way to provide a fully secure option to those who want a completely locked down version of the CLI and not use this as a code library. Right now your team is using npm as a kind of "app store" for your cli and just disregarding the fact that most of the community uses it as a way to share code amongst the javascript community. Truth of the matter is anyone using the If the official choice from your team is to not officially support programmatic access to this package I guess our best bet is to provide workarounds in projects like SST for pnpm as mentioned here #23182 (comment) and take this on as a risk of a project expanding on the @thdxr I have no doubt this will be a bit frustrating but if your team doesn't want to move towards the programmatic cli api maybe |
@rix0rrr ah right forgot about the nested dependency scenario thanks for clarifying Performance issues are challenging to list out here but I spent a few months profiling every place SST was slow and needed to reach into cdk directly to get the performance we wanted. It's actually still not what we consider good enough but it's a drastic improvement over spawning the CLI many times through the course of a single command @aphex I'm fairly certain the latest rc of sst doesn't need that pnpm workaround, try removing it and seeing if it's still a problem |
I think that was a minimal reproduction so not a real world scenario let me explain what we're actually doing - it's fairly monstrous so don't judge us too hard! we've forked the following two files from cdk: https://github.com/serverless-stack/sst/tree/sst2/packages/sst/src/cdk these files import directly from effectively we're importing modules that aren't meant to be imported since we want programmatic access to CDK functionality without forking the whole CDK project |
that's definitely a step in the right direction, but we're not sure if just 1:1 access to CLI commands will be enough we need some granular control over what happens (eg suppressing all console output, splitting up asset upload from deploying stacks, etc) we have some specialized CI functionality in https://seed.run/ that coordinates these steps in an efficient way so simply running the CLI probably will lose significant performance |
I'd love to hear these granular control requirements, whenever they pop up for you. No promises obviously. |
cool! we're wrapping up SST v2 and SEED integration and once we've done that we should be able to look back and summarize what exactly we needed to do |
EDIT: it actually didn't work... 😌
"pnpm": {
"packageExtensions": {
"aws-cdk": {
"dependencies": {
"yaml": "1.10.2"
}
}
}
} |
I just ran into both this and the |
@RichiCoder1 Thanks for the report. Can you confirm if you were also using a subpath import like others in the issue? Possibly via a third-party library. |
the issue was from SST as well we're getting an increasing number of people having issues from this so we're likely going to have to fork would really love not to do this |
Describe the bug
When using the CDK with pnpm it is prone to have package hoisting issues as all the packages are declared as
devDependencies
notdependencies
. Looking athttps://unpkg.com/[email protected]/package.json
I am seeing all dependencies have been moved to
devDependencies
however in the code itself it looks like there are normaldependencies
(https://github.com/aws/aws-cdk/blob/main/packages/aws-cdk/package.json#L94).When these are only declared as dev pnpm is not hoisting the dependency (as it is not declared as one that is needed to use the package), which causes
aws-cdk
to load[email protected]
instead of[email protected]
if there is another package in the monorepo that has a hard dependency on[email protected]
.Expected Behavior
Dependencies and devDependencies should be maintained in the released npm package indicating packages needed to use the cdk vs packages just needed when developing it.
Current Behavior
All dependencies are merged into
devDependencies
when releasedReproduction Steps
Create a pnpm workspace where the main
package.json
depends onlint-staged
as well asaws-cdk
. Attmepting to use the cdk will result in yaml errors when trying to useyaml/types
for example.Possible Solution
Maintain dependencies when released.
Additional Information/Context
Workaround for this is to add the following to your pnpm config in
paclage.json
CDK CLI Version
n/a
Framework Version
No response
Node.js Version
16
OS
WSL/Ubuntu
Language
Typescript
Language Version
No response
Other information
No response
The text was updated successfully, but these errors were encountered: