CFEXECUTE - "Bad file descriptor" or "Permission denied"


#1

Attempting to use cfexecute to run a shell script to back up databases.

This has worked successfully for years and years prior to upgrading to Lucee 5

There are two scripts I can choose from.


SCRIPT 1: automysql backup - an old program that still works

CALL FROM COMMAND LINE: automysqlbackup

For years, I have used this:

<cfexecute name="/usr/local/bin/automysqlbackup" arguments="" timeout="60" />

Lucee says:

/usr/local/bin/automysqlbackup: line 835: 6: Bad file descriptor
/usr/local/bin/automysqlbackup: line 836: 7: Bad file descriptor

Why the line numbers? I have no idea. The CFM file only contains one line (cfexecute)


SCRIPT 2: generic backup script - named it "hello.sh"

CALL FROM COMMAND LINE: ./hello.sh

Here is the complete script, attempting to trigger mysql dump via cfexecute. Permissions in the shell script are set correctly.

If I call the script from the command line, it works no problem. I can give the shell script any permissions needed, but it doesn’t work when called from cfexecute. And I have made sure the script is executable.

The script is at the root of the system simply to make testing easy. So /hello.sh is correct.

<cfexecute name="/hello.sh" arguments="" timeout="15" errorVariable="returnedError"></cfexecute>

Lucee says:

Permission denied mysqldump:

Content of Hello.sh

#!/bin/bash
 
################################################################
##
##   MySQL Database Backup Script 
##   Written By: Rahul Kumar
##   URL: https://tecadmin.net/bash-script-mysql-database-backup/
##   Last Update: Jan 05, 2019
##
################################################################
 
export PATH=/bin:/usr/bin:/usr/local/bin
TODAY=`date +20%y%m%d-%H%M%S`
 
################################################################
################## Update below values  ########################
 
DB_BACKUP_PATH='/path/to/my/backups/dbname'
MYSQL_HOST='127.0.0.1'
MYSQL_PORT='3306'
MYSQL_USER='user'
MYSQL_PASSWORD='password'
DATABASE_NAME='dbname'
BACKUP_RETAIN_DAYS=30   ## Number of days to keep local backup copy
 
#################################################################
 
#mkdir -p ${DB_BACKUP_PATH}/${TODAY}
echo "Backup started for database - ${DATABASE_NAME}"
 
 
mysqldump -h ${MYSQL_HOST} \
   -P ${MYSQL_PORT} \
   -u ${MYSQL_USER} \
   -p${MYSQL_PASSWORD} \
   ${DATABASE_NAME} | gzip > ${DB_BACKUP_PATH}/${DATABASE_NAME}-${TODAY}.sql.gz
 
if [ $? -eq 0 ]; then
  echo "Database backup successfully completed"
else
  echo "Error found during backup"
fi
 
 
##### Remove backups older than {BACKUP_RETAIN_DAYS} days  #####
 
DBDELDATE=`date +"%d%b%Y" --date="${BACKUP_RETAIN_DAYS} days ago"`
 
if [ ! -z ${DB_BACKUP_PATH} ]; then
      cd ${DB_BACKUP_PATH}
      if [ ! -z ${DBDELDATE} ] && [ -d ${DBDELDATE} ]; then
            rm -rf ${DBDELDATE}
      fi
fi
 
### End of script ####

#2

If you don’t execute a binary , use bash or cmd.exe (for windows) as the command and the script as argument for the shell interpreter.

cfexecute( name="bash" arguments="/opt/jq.sh #cmdArgs#", variable="standardOut" , errorVariable="errorOut" , timeout="10");

#3

Thank you! This did not work initially. But, it did give me a different error and I was able to eventually solve the problem.

The issue appears to have been that the directory where I was writing the mysql backups needed to be owned by tomcat.

Solution:

chown -R tomcat:root /backup/directory

I find that very strange.

And I have to wonder if my basic understanding of permissions is flawed or if this particular install of Tomcat is either a) wrong or b) very different from past installs.

I suspect that before upgrading the system, I was running Tomcat as root inside of /usr/local/tomcat

Now, after my upgrade I am running Tomcat in /opt/tomcat as user tomcat.

Questions for you if you have a moment:

  1. I’ve been away from development for a while. I never used CFSCRIPT to do many things before. But I know that a lot of developers like to. Is there some advantage to using CFSCRIPT for this type of job (CFEXECUTE) instead of the <CFEXECUTE> tag?

  2. Does anyone run Tomcat as root? Seems like a big security problem to me. But then agin, if someone can access root then you have so many other things to worry about. So?


#4

Tomcat needs only write access to the target directory (must not be the owner).
You start the backup process in the context of the tomcat user (cfexecute spawns a java process)

  1. No, it’s only a matter of taste. cfscript is normally less verbose than the TAG versions.

  2. you should never run tomcat (or any other service as a rule of thumb) as root. And of course security makes it much more complicated…