我有一个 bash 脚本,它应该从中删除一个文件/tmp
。问题:该文件是在导出mysql
期间由我的用户创建的SELECT INTO OUTFILE
。因此,运行脚本的用户不拥有该文件。
但是,我怎样才能删除该文件,而不必将脚本添加到其中sudo crontab
?
我的用户-crontab:
/opt/my_routine.sh
我的程序.sh:
!#/bin/bash
rm -f "/tmp/mysql_export.csv" #FAILS
mysql --user=user --password=rootpw --database=mydb < /opt/export.sql
导出.sql:
SELECT some, fields INTO OUTFILE '/tmp/mysql_export.csv' FROM mytable FIELDS TERMINATED BY ';' ESCAPED BY '' LINES TERMINATED BY '\n';
答案1
问题
重定向 stdout,以便文件由正确的用户创建(例如另一个答案) 是一个不错的想法,但我认为你需要TERMINATED BY
、ESCAPED BY
和LINES TERMINATED BY
。这些需要INTO OUTFILE
。重定向 stdout 的直接解决方案只是省略了INTO OUTFILE
,因此它无法使用TERMINATED BY
等。
尝试INTO OUTFILE
写入标准输出不起作用:
SELECT some, fields INTO OUTFILE '/proc/self/fd/1' FROM mytable FIELDS TERMINATED BY ';' ESCAPED BY '' LINES TERMINATED BY '\n';
它不起作用,因为该文件之前必须不存在;MySQL 必须自行创建它。出于安全原因(例子)。该特殊文件/proc/self/fd/1
由内核提供,因此MySQL拒绝它。
有问题的路径是/tmp/mysql_export.csv
。当您尝试mysql_export.csv
从 中删除时/tmp/
,您对该目录的权限很重要。这/tmp/
通常是这样的:
$ ls -ld /tmp/
drwxrwxrwt 1 root root 1772 Nov 1 19:39 /tmp/
$
小写字母t
表示drwxrwxrwt
“其他”的执行权限和粘性位设置。关于粘性位:
粘性位最常见的用途是用于类 Unix 操作系统文件系统中的目录。设置目录的粘性位后,文件系统会以特殊方式处理此类目录中的文件,因此只有文件所有者、目录所有者或 root 才能重命名或删除该文件。如果不设置粘性位,任何对该目录具有写入和执行权限的用户都可以重命名或删除其中包含的文件,无论文件的所有者是谁。
(来源:维基百科)
您无法删除该文件,因为您既不是 root 用户也不是该文件的所有者。
解决方案
上面的引用只是给了我们一个线索。如果您既不是文件的所有者也不是 root,那么您需要:
- (目录上的粘着位)目录的所有者,或
- (没有粘性位)任何对目录具有写和执行权限的用户。
因此,在某处创建一个目录,允许其他用户在其中创建文件(chmod
,setfacl
),然后调整您的程序以在mysql_export.csv
该目录中创建文件。文件出现后,即使它属于其他用户,您也可以删除它。使用rm -f
。如果没有,-f
您可能会被提示,因为该文件不属于您。
笔记
- 该解决方案不超出普通用户所能做的事情。您不需要
sudo
,也不需要在系统中设置任何额外的组。 - 允许其他用户创建文件在您的目录中删除文件可能不会有好结果。您将能够删除“外部”非目录和空子目录。但要删除非空子目录,您需要先删除其中的所有内容。一般来说,您是否可以从其他人的目录中删除文件并不取决于您,即使它是你的目录的子目录。如果其他用户只是您控制下的正式用户,那么就不必担心这一点。
答案2
您可以从 mysql 转储结果,而不是执行 INTO FILE:
mysql --user=user --password=rootpw --database=mydb < /opt/export.sql > /tmp/mysql_export.csv
然后你的export.sql将会是:
SELECT some, fields FROM mytable;
或者,您也可以使用sudo rm ...
。
答案3
方法有很多,具体取决于您要处理的具体内容。
您可以在创建脚本中使用 umasks 或 chmod 来使文件组/世界可写(并确保两个用户都在该组中)。
您可以以同一用户身份运行这两个脚本。您是否知道 crown allied 指定用户,或者使用用户特定的 crown 作业以该用户身份运行?
(不实用,精神自慰)您可以使用保险丝或一些覆盖文件(或具有挂载权限的文件块设备)/滥用来自原始文件系统的权限,例如 vfat,它没有权限概念,因此您可以在挂载时根据需要强制使用它们。