I'm afraid your code is too long for me to be able to answer your main questions, but here are some general suggestions:
- instead of sprinkling DBI::errstrs all over your code, just set RaiseError=>1,PrintError=>0 in you connection which will automatically do the the error checking and reporting.
- Instead of $sth->fetchrow_array, use $sth->fetchrow_hashref or bind_columns() to put your results in a hash since you want a hash, not an array
- Do not pass your user input directly into the SQL the way you are doing now, read about placeholders, and always use them.