I think you will have to be very careful with this, to prevent actually editing the user's history. I think adding a cwd request to the control-socket might be preferable, so you aren't overloading non-execution requests on an execution message, and making extra system calls with every user execution.
I thought that the user_expressions capability already handled this so that the history is not affected. I will test this to make sure the history is not affected though. I want to avoid additional calls because i) the only time the cwd can change is in an execute_request and ii) I don't want the extra network requests.
Right, but you are making extra calls - calling getcwd at every execution seems like a bad idea, since you are generating the same information, when <1% of the time it's actually useful. I don't see why you would mash non-execution into an execution request when we have a control-queue model for doing non-execution related requests.
I just realized this whole approach won't work. Having the notebook server follow the cwd of a kernel won't work because different kernels can have different cwd's. There will need to be a separate step that allows the user to select the cwd for the notebook server, which will be like the active "project" for the notebook server.
But, the entire reason we put in the user_expressions capability was to handle cases like this. Originally, I argued that this was a bad idea for exactly the reasons you are describing. But, Fernando and Evan wanted it, so it is there. I am going to close this and open a new issue with the new design reflected.