Closed roblourens closed 3 years ago
Let us know if there's anything you need. Thanks
First, what are we trying to do by observing workspace trust?
node_modules/typescript/...
.There are currently 2 thought models on workspace trust and explicit actions.
At present, one is not chosen over the other, but hopefully this scopes the discussion.
The question is, outside of that case, is there any reason for vscode to prevent a renderer from running in an untrusted workspace where it is loading data (
Renderer code can send messages outside of the webview which gives it a potential real impact, but still it seems like the responsibility is on the renderer - if it's going to send a message which could result in a bad impact based on data in the output, it should check workspace trust.
Renderer code can send messages outside of the webview which gives
Ideally those messages go straight to the extension host and aren't rerouted via the renderer. I believe there was some exploration to use message channels that enables that.
@lszomoru for awareness
Talked to @sbatten, the current plan is that for explicit user actions like debugging or running a command that requires trust, a dialog will show asking the user to "continue" and trust the workspace, or "cancel" and not trust it. For notebooks, we can hook into the same system to show a dialog when you first run a cell.
You could argue that the extension should be involved in this rather than vscode enforcing it, because trust doesn't matter for some notebooks. For example, I don't care about running a github issues query from an untrusted workspace. But most notebooks are not like that, and this is so similar to debugging, and it will be much simpler to have vscode handle it in the same way.
Then also, given the discussion above, I think that we should not automatically block outputs/renderers from loading in an untrusted workspace. The extension can require workspace trust if it is necessary for that extension (like if it is loading and executing code in the workspace) and it's the responsibility of the extension to determine that. cc @connor4312 and @DonJayamanne do you think that's acceptable?
@roblourens Thanks this makes a lot of sense, and from what I can tell, there's no need to implement a custom trust model in Jupyter extension.
I guess the only question for Jupyter extension is whether we display the output or not (when not trusted).
@claudiaregio @greazer /cc
Jupyter extension can ask the user to trust the workspace, if they trust it, we let them run the notebook, else nothing happens (cell does not run)
VS Code will handle this part of it, the extension doesn't have to do it.
Jupyter extension to decide whether we render the output or not
Yes, and we can discuss this more. I'm not sure there is really any need to do anything with output renderers but it probably needs more thinking.
👍 for allowing renderers through. We just need to be aware that any of the FromWebview
messages may be coming from a untrusted (or, malicious) context. Looking at what we have today, the worst an extension could do it mess up layout/focus and show a 'save' dialog. Arguably the latter could be dangerous if users blindly allow saving, but I don't think there's a way around that.
You could argue that the extension should be involved in this rather than vscode enforcing it, because trust doesn't matter for some notebooks. For example, I don't care about running a github issues query from an untrusted workspace. But most notebooks are not like that, and this is so similar to debugging, and it will be much simpler to have vscode handle it in the same way.
Sounds like a kernel property to me, like a kernel can say if it requires trust
@roblourens Hi Rob, right now the Jupyter extension prompts the user to trust a notebook if not created on the user's machine (ex. they download it). What happens in this scenario where a user opens a stand-alone notebook where it did not come from a trusted workspace? (ex. opened from downloads folder)
@sbatten how does trust work in a window that doesn't have a folder open? Or for files that are not in the current workspace?
Current implementation is that empty workspaces (no folder) are trusted by default. However, opening files in an empty workspace will be treated as the "loose file" scenario. If the loose file is not from a known trusted path, we prompt the user once to inform them that they are bringing untrusted content into a trusted workspace. From then on, any additional untrusted content will not receive a prompt for the remainder of the session.
Command links in outputs and markdown cells could pose a threat in untrusted workspaces. We implemented this in https://github.com/microsoft/vscode/issues/98100. Is the Jupyter extension still relying on these in outputs and markdown cells?
We'd like to think about removing them since they are a vscode-only feature. Or, we have to either
Jupyter extension still relying on these in outputs and markdown cells?
Yes.
or just disable all rich outputs in untrusted workspaces
I'd think this is preferred.
or disable scripts in outputs in untrusted workspaces
If we can have this, that's even better, but can we guarantee that this will not be open to exploits in some form? At the end of the day the requirement is to protect the user from malicious content running without the users consent.
We decided to hide rich outputs in an untrusted workspace, and show some placeholder output
What would be shown in this scenario for a simple webpage GET in a REST Book? https://github.com/tanhakabir/rest-book/issues/90
I think it would be easier to explore this with concrete custom notebook extensions and renderers, perhaps kernels too, and not just Jupyter notebooks.
They wouldn't be shown, but you wouldn't be able to run the cell anyway in an untrusted workspace.
@RandomFractals
You probably don't know this, hence the reason for your response. The author or restbook is a PM in VS Code team . They are using concrete custom notebook extensions and renderers, perhaps kernels too,
. they are working closely with a number of external teams extension authors.
stop making assumptions
and if downvoting someone make some suggestions instead, be constructive
@kaimatrix19821 I know that the author of rest book extension is a PM who works with vscode team. Why I picked it to beta test custom notebooks api, renderers and UX. I think you are the one who is making a lot of assumptions there.
I downvoted that response because I don't think it's a good solution to just not show the notebook or disallow to run code cells, especially simple GET queries in that specific case for untrusted workspaces.
I am also aware that vscode dev team is working with other teams at Microsoft on that native notebooks api and UX.
The feedback I provide here and in other linked tickets for this feature is constructive and includes screens and description of disconnects I am seeing so far, or at least what I would expect to see there as extension developer who is planning to use that notebooks api to create other custom notebook extensions when it is released.
Perhaps, you should not comment with anon. github handle and look up my work and why I am interested in this.
@RandomFractals Can you tell me why you would open a workspace, explicitly tell us that you don't trust the content/author of this workspace, but then want to make a request to a web endpoint (specified by code that you don't trust) and render the result?
I want to understand more about who would be working in an untrusted workspace and what they would expect to work, because in my mind, I would expect a very basic safe mode.
I would rather see a notebook view with code cells, and have a warning after I review a cell code and decide to run it.
I also think your new trusted workspaces concept with the current implementation would give users a false sense of security. I don't trust any code but my own, sometimes not even that. I believe most seasoned IT professional don't trust any code by default. However, after a review they might decide to run it.
Security researchers might want to load notebooks in untrusted workspaces and pick and choose what to run, which I think is a bit better than not being able to see or run any code cell and being forced into marking a workspace or a notebook as trusted to evaluate how different parts of the notebook run and see the results they produce. Very real world scenario.
& if you are just looking to add on/off basic safe mode to vscode as you mention, then just call it that.
To be honest, I'd rather see you add permissions and extensions, notebooks, renderers, and projects request and get granted permissions to access different parts of the vscode apis, interact with workspace fs, cam, etc. Then from extension authoring standpoint it would be transparent what we need access to, and what would run in extensions or notebooks, even for untrusted workspaces, and let users decide what to run with some warnings. I believe that is a more granular approach and supported by many systems out there today.
I hope that helps. Thanks!
I would rather see a notebook view with code cells, and have a warning after I review a cell code and decide to run it.
That's exactly what the plan is, and is already implemented. Maybe this thread doesn't have full context.
Security researchers might want to load notebooks in untrusted workspaces and pick and choose what to run
Cells do not run unless you click run. But really in this case of working with known-malicious code, I think you want to work in a VM or another real sandbox, rather than rely on this feature as your only line of defense.
To be honest, I'd rather see you add permissions and extensions, notebooks, renderers, and projects request and get granted permissions to access different parts of the vscode apis, interact with workspace fs, cam, etc.
Fair request, we could work in that direction, the workspace trust feature is only focused on this one aspect of secure development.
@roblourens thank you for providing more context info on this. I'll check it out with this feature setting you shared in another ticket and rest book extension to see how it works. I think some screens or walk through gif as a quick demo of a feature like this would really help to visualize the workflow you are implementing next time.
@roblourens looks like there's a lot going on here. Can you write some verification steps, please?
I've verified almost all of the points above except for the last one. I'm not familiar with how rich html output works, and how one writes a notebook to produce that output, though, so I'm unable to tell when the output switches from a rich html one to a simple one.
@rzhao271 you can try it with a restbook ... https://github.com/tanhakabir/rest-book/issues/90#issuecomment-828863431
@roblourens why should not I see previously generated rich html output in a loaded notebook? I think you are taking this 'untrusted' workspaces a bit too far.
If I had a renderer that generated a chart as a cell output and saved it. Are you saying I should not be able to see it with your notion of an untrusted workspace? I most certainly disagree with you and your teams decisions on this.
Custom renderers should still work in an untrusted workspace. HTML outputs don't. Even though they are "sandboxed" in an iframe, the iframe has special privileges such that we believe it isn't safe to run explicitly untrusted scripts in it. In the html output case, this is untrusted content from the document, not from an extension.
I believe Google collab and jupyter run something that scrapes out javascript from any html outputs by default. Might we be able to do something similar?
I don't see why we would show a possibly broken output. And I don't really trust any html parsing code I write for security purposes. There might be a fallback output mimetype.
Wouldn't custom renderers be the same thing? The data is json that drives the custom renderer. It could potentially be a security risk too?
I think the only truly safe output would be text/plain. Although I still think you could remove script tags pretty easy. Everything else is potentially running code on the output.
I switched the workspace to untrusted, and then opened up a notebook that renders an HTML output. The HTML output seemed to still be there, but the only option when it came to switching renderers was plain text:
close, but I think you should still show built-in html render and render it. not sure I like the stripping out of js idea either. do it if you must.
Those cell outputs run in an iframe in a notebook webview and is already sandboxed with CSP and rest that comes with it. what attack vectors are you trying to prevent there?
Sounds like premature optimization to me at this point until we have some more rich output renders to play with and finalize this.
@connor4312 this regressed in https://github.com/microsoft/vscode/commit/d6d9200832af59b997adb9b3c6f0ba173786daf7#diff-54b1e3297f88bd6925ca5fe088edaf93b8aa1832936da6350d69fec68375504eL54 where we pick mimetype 0, even if it's not trusted. I don't quite follow, can you take a look?
Thanks @connor4312.
@rchiodo it's the difference between html that comes from workspace content and html that comes from extensions.
@RandomFractals an example is that html outputs can have links that trigger vscode commands
ok. I did likes and dislikes on this feature implementation, ideas, and proposed approaches with my thumbs up and down.
Please view them as agree or disagree. Thanks!
The json in the outputs that drives the html from the renderer can be anything though. And the renderer could theoretically be doing anything possible in a renderer (like say sending messages back to the extension to run a cell). That's why I think any json (read by a renderer, or causes code execution) in an untrusted notebook should be deemed malicious.
Continuing the discussion from https://github.com/microsoft/vscode/issues/106747