Calling a macro from another macro with mcCntlGcodeExecute/Wait() is not the best practice. You are writing a script that should call script functions where possible. So if M5 called mc.mcSpindleSetDirection(inst, mc.MC_SPINDLE_OFF), then your M30 script should too INSTEAD of calling mcCntlGcodeExecute/Wait(inst, "M5") Why? Because the interpreter is already RUNNING an M code that is backed by a script. Some M codes are built in (no script) and they will run.
So what if you M5 does some multiline complex operation and it is hard to edit EVERYTHING to do that operation? Especially if you made changes to it and want to update everything. This is where code sharing via modules becomes a good idea.
Steve