There are a few options.
One option is to use a "high side switch" Which is (sort of) your schematic put into a single IC, and these often come with built in over current, temperature, over voltage and possibly other protections built in.
Another option is to use an IC which is made for driving mosfets. These resemble an optocoupler, but instead of having a transistor at their output, they generate an (isolated) output voltage fit for driving a mosfet.
But in general, the circuit you drew is simple and with common parts which are easily replaced if they can't be sourced in these weird times.
Gates of FET's are quite sensitive though, and therefore always need some consideration.
For example, if your +12V input can ever generate even short spikes above 20V, then you can violate Ugs max.
A simple way to prevent this is to add a (bipolar) TVS diode between the gate and source, in combination with a series resistor in the gate.
Another simple way to make your circuit a bit more robust is to add a resistor between the emitter of the BC547 and GND.
Output of the ESP32 won't be above 3V3, so the emitter won't rise above 2V7, and with a single added 100 Ohm resistor you've turned your BJT into a 27mA current sink.
This will keep this transistor intact in case the mosfet gets shorted.
I do not consider your mosfet oversized.
It has a quite high Rds(on) of 20mOhm, which results in a dissipation of:
16*16*0.02 = 5.12 Watt.
That fet is from a 25+ year old design, and electronics has improved a lot. Fet's with less than a milli Ohm Rds(on) are common now.
Alternatively, put two of these old fets in parallel.
Each would then only dissipate (approx) 8*8*0.02 = 1.28Watt