I code against both Django and Tornado. My Tornado based HTTP servers call C extension while they're handling GETs and POSTs. And that's why I'm staying on 2.7.8 until a customer pays me to port to 3.
2.7.8 was the latest 2.x when I built the current codebase. Currently I'm testing before a cloud launch. Fixing bugs in my product's functionality is a higher priority than porting to the latest 2.7
2 years is not an unusual time between starting product development and seeing any sort of major customer uptake, and if you're in that time period, your priority really should be getting the customers rather than futzing with code migrations.
It's still the case that a bad call was made when the codebase was started, picking a language version that was already on its way out. It's like starting a new project now with Java 7 o .Net 2.0.
Of all the bad calls you can make when starting a business, picking a bad language or platform is a relatively minor one. Google was originally on Python 1.6 (or technically Java 1.02, if you go back to when it was Larry's dissertation project), Facebook chose PHP (!!), basically every Android app is forced to use Java 7, and a good number of iOS apps are still in Objective-C.
Is really not that hard to make C extension support Python 3, you're either using an extension that is no longer maintained, or its author(s) are stubborn, which is a different kind of problem.
Making code compatible with python2.7 onward means that you can't use any new features from 3+ and the code is plain ugly, I don't know if you wrote 2/3 compatible code, it is not as enjoyable to do.
I think Django's approach where the LTS will still work on 2.7 (and LTS is for 3 years, which is until python2 itself stop being maintained) is fair.
You still have 3 years to fix things and if you want to use latest Django and be cutting edge, you probably should use latest Python as well.
There are a couple #if PY3K, but not much, really.
I ported a bunch of extension modules, total a couple thousand LOC, and it was pretty much a matter of reading the docs (see guide at https://docs.python.org/3/howto/cporting.html ) and adding a few #ifs. Total time maybe an hour or two.
My experience is that it is drastically easier to port C extensions than to port python code itself - the C API hasn't really changed a lot and it's usually very easy to reason about C code due to it being more strongly typed than python.
The only reason why it might be hard is you are unfamiliar with the extension's code and/or C