If I understand correctly, there is also one other reason, not mentioned clearly in the article, why the defragmentation daemon needs some support from the kernel space.
The "put the newly defragmented version in the place of the old one" part must be done by updating the inode of the original or you would end up having to hunt and update all the directory entries pointing to the file.