At my university in the UK we have two kinds of assessment for programming courses. Pass/fail 'practicals' where students are given programming tasks, and are explicitly allowed to discuss them with each other and search online. When the student is ready to submit their solution a demonstrator will look it over and ask questions etc to make sure the student understands why they wrote the code they wrote. Students don't get a grade for this that counts towards their overall mark for the year, but they are required to 'pass' the practicals in order to pass the year.
Then there are written exams with no computer access. There are questions along the lines of 'write some code that will solve this problem', and also more conceptual 'why is this the case? When would you use that?' questions. For the 'write code' bits, the markers will deduct very few points for simple syntax errors and things like that. The question is not so much 'can the student write a program that will compile on the first try?' as 'can the student come up with a good algorithm which solves the problem and give a reasonable expression of it in code?'. Note that these courses (at my uni) are never for specific languages; they are courses like 'functional programming' or 'object oriented programming' or 'machine learning', which will each use a particular language, but we care more that the student understands the concepts than learns the intricacies of the course's language.
This also encourages students to learn ways of designing and writing provably correct programs: if they can reason about programs on a deeper level than intuition, then writing programs on paper is a better test of this than allowing them to experiment and test until the output 'looks right' for the inputs they've given it.
This seems like a good way to avoid cheating on grades that matter and encourage solid understanding of the important course material. That said, many students hate having to write code on paper without access to S.O. or a compiler!