为什么由Windows Task Scheduler触发的PHP脚本在手动和自动触发时会产生不同的结果?

时间:2019-05-28 23:37:31

标签: php windows caching scheduled-tasks

我在Windows 10 Home 上安装了 XAMPP ,并且运行了PHP脚本,该脚本每5分钟在本地文件夹中生成一个具有常量名称的新数据文件(覆盖以前的文件),并且然后将其上传到服务器。 PHP脚本是通过 Windows Task Scheduler (WTS)触发的。我的观察是:

1)当我手动触发WTS任务时,PHP脚本始终会上传新文件。

2)当自动触发同一WTS任务时(基于任务计划),PHP脚本会上传一些非常旧的文件,尽管会生成一个新文件并将其保存在本地文件夹中。

3)当我每次更改PHP脚本以使用不同的文件名生成文件时,两种触发方法均按预期方式工作(上传了新文件)。

有人可以解释这里发生了什么吗?看起来像是一种缓存机制,具体取决于WTS触发方法(禁用了PHP opcache)。

编辑:根据要求添加了一些相关代码。

主要的PHP例程:

$filename = PATH::CACHE . '/dostawca-subiekt-produkty.dat.txt';

$dataFile = new File($filename);

$elements = json_encode($elements);
$dataFile->save($elements);

$destination = $config->apiUrl . "/save.php?time=" . time();
$postData = [
    'apiKey' => $config->apiKey,
    'dataSource' => 'subiekt',
];

$response = $dataFile->uploadTo($destination, "subiekt", $postData);

路径配置:

abstract class PATH
{
    const ABS =     __DIR__;
    const LOG =     PATH::ABS . '/logs';
    const CACHE =   PATH::ABS . '/cache';
}

文件类的上传方法:

public function uploadTo($url, $filePostFiledName = 'file', $optionalPostFields = [], $options = [])
{
    $result = FALSE;

    if (!is_string($url) || empty($url) || !self::isValidUrl($url)) return FALSE;

    $filePath = $this->localPath;
    $fileName = $this->getName();
    if (!($fileMimeType = $this->getMimeType())) $fileMimeType = 'application/octet-stream';

    // Create a CURLFile object
    $curlFile = curl_file_create($filePath, $fileMimeType, $fileName); // procedural method
    //$curl_file = new CURLFile($filePath, $fileMimetype, $fileName); // oop method

    // Assign POST data
    $postFields = ["{$filePostFiledName}[0]" => $curlFile];

    // Add optional POST data
    if (!is_array($optionalPostFields)) $optionalPostFields = ['unnamed' => (string)$optionalPostFields];
    if ($optionalPostFields) $postFields = $postFields + $optionalPostFields;

    // Setup default cURL options
    $defaultOptions = [
        CURLOPT_URL => $url,
        CURLOPT_POST => TRUE, 
        CURLOPT_POSTFIELDS => $postFields,
        CURLOPT_RETURNTRANSFER => TRUE,
        CURLOPT_FRESH_CONNECT => TRUE,
        CURLOPT_FORBID_REUSE => TRUE,
        CURLOPT_TIMEOUT => 10*60, // The maximum number of seconds to allow cURL functions to execute.

        CURLOPT_SSL_VERIFYPEER => FALSE, // Stop verifying certificate
        CURLOPT_FOLLOWLOCATION => TRUE, // if any redirection after upload

        CURLOPT_HEADER => ['Cache-Control: no-cache, must-revalidate', 'Expires: 0'],
        //CURLOPT_HEADER => FALSE,
        //CURLOPT_HTTPHEADER => ['User-Agent: Opera/9.80 (Windows NT 6.2; Win64; x64) Presto/2.12.388 Version/12.15', 'Referer: http://someaddress.tld', 'Content-Type: multipart/form-data'],
        //CURLOPT_USERAGENT => 'Opera/9.80 (Windows NT 6.2; Win64; x64) Presto/2.12.388 Version/12.15',         
    ];

    if(!is_array($options)) $options = [];

    // Start uploading
    $curl = curl_init();        
    curl_setopt_array($curl, ($defaultOptions + $options));         
    $result = curl_exec($curl);
    if (curl_errno($curl)) $result = ['error' => curl_error($curl), 'response' => $result];
    curl_close($curl);

    return $result;
}

1 个答案:

答案 0 :(得分:0)

最后,我已经用名为System Scheduler的免费软件替换了 Windows Task Scheduler ,现在一切正常,一切正常(其他没有改变)。

不幸的是,我找不到WTS为什么“正在缓存”上传文件的原因。我尝试了WTS选项的所有组合(不同的帐户,隐藏的任务,不同的系统等),然后遍历Windows Sysinternals Process Monitor跟踪以找到线索,但没有成功。在CMD或WTS任务中手动调用PHP脚本很好。根据时间表触发相同的WTS任务总是错误的(旧的缓存文件总是上载)。