435 lines
11 KiB
PHP
435 lines
11 KiB
PHP
<?php
|
|
|
|
/**
|
|
* PRODS class
|
|
* @author Sifang Lu <sifang@sdsc.edu>
|
|
* @copyright Copyright © 2007, TBD
|
|
* @package Prods
|
|
*/
|
|
|
|
require_once("autoload.inc.php");
|
|
|
|
class ProdsStreamer
|
|
{
|
|
/**
|
|
* current position of the file or dir
|
|
*
|
|
* @access private
|
|
*/
|
|
private $position;
|
|
|
|
/**
|
|
* Name of the directory/collection specified in the URI to opendir().
|
|
*
|
|
* @access private
|
|
*/
|
|
private $dir;
|
|
|
|
/**
|
|
* Name of the file specified in the URI to fopen().
|
|
*
|
|
* @access private
|
|
*/
|
|
private $file;
|
|
|
|
|
|
/**
|
|
* url_stat() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function url_stat($path)
|
|
{
|
|
try {
|
|
$file=ProdsDir::fromURI($path);
|
|
$conn = RODSConnManager::getConn($file->account);
|
|
|
|
$stats = $this->stat_file($conn, $file->path_str);
|
|
if (!$stats) {
|
|
$stats = $this->stat_dir($conn, $file->path_str);
|
|
}
|
|
|
|
RODSConnManager::releaseConn($conn);
|
|
|
|
return $stats;
|
|
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* @param $conn
|
|
* @param $file
|
|
* @return mixed
|
|
*/
|
|
private function stat_dir($conn, $path_str) {
|
|
try {
|
|
$irods_stats = $conn->getDirStats($path_str);
|
|
if (!$irods_stats)
|
|
return false;
|
|
$stats = array();
|
|
$stats[0] = $stats['dev'] = 0;
|
|
$stats[1] = $stats['ino'] = 0;
|
|
$stats[2] = $stats['mode'] = octdec('040755');
|
|
$stats[3] = $stats['nlink'] = 1;
|
|
$stats[4] = $stats['uid'] = 0;
|
|
$stats[5] = $stats['gid'] = 0;
|
|
$stats[6] = $stats['rdev'] = -1;
|
|
$stats[7] = $stats['size'] = 0;
|
|
$stats[8] = $stats['atime'] = time();
|
|
$stats[9] = $stats['mtime'] = $irods_stats->mtime;
|
|
$stats[10] = $stats['ctime'] = $irods_stats->ctime;
|
|
$stats[11] = $stats['blksize'] = -1;
|
|
$stats[12] = $stats['blocks'] = -1;
|
|
return $stats;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception: $e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* @param $conn
|
|
* @param $file
|
|
* @return mixed
|
|
*/
|
|
private function stat_file($conn, $path_str) {
|
|
try {
|
|
$irods_stats = $conn->getFileStats($path_str);
|
|
if (!$irods_stats)
|
|
return false;
|
|
$stats = array();
|
|
$stats[0] = $stats['dev'] = 0;
|
|
$stats[1] = $stats['ino'] = 0;
|
|
$stats[2] = $stats['mode'] = octdec('100644');
|
|
$stats[3] = $stats['nlink'] = 1;
|
|
$stats[4] = $stats['uid'] = 0;
|
|
$stats[5] = $stats['gid'] = 0;
|
|
$stats[6] = $stats['rdev'] = -1;
|
|
$stats[7] = $stats['size'] = $irods_stats->size;
|
|
$stats[8] = $stats['atime'] = time();
|
|
$stats[9] = $stats['mtime'] = $irods_stats->mtime;
|
|
$stats[10] = $stats['ctime'] = $irods_stats->ctime;
|
|
$stats[11] = $stats['blksize'] = -1;
|
|
$stats[12] = $stats['blocks'] = -1;
|
|
return $stats;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception: $e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* mkdir() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function mkdir ($url, $mode, $options) {
|
|
try {
|
|
$file=ProdsDir::fromURI($url);
|
|
$conn = RODSConnManager::getConn($file->account);
|
|
$conn->mkdir($file->path_str);
|
|
|
|
RODSConnManager::releaseConn($conn);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* rmdir() handler
|
|
*
|
|
* @param $url
|
|
* @return bool
|
|
*/
|
|
function rmdir ($url) {
|
|
try {
|
|
$file=ProdsDir::fromURI($url);
|
|
$conn = RODSConnManager::getConn($file->account);
|
|
$conn->rmdir($file->path_str);
|
|
|
|
RODSConnManager::releaseConn($conn);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* unlink() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function unlink ($url) {
|
|
try {
|
|
$file=ProdsDir::fromURI($url);
|
|
$conn = RODSConnManager::getConn($file->account);
|
|
if (is_dir($url)) {
|
|
$conn->rmdir($file->path_str, true, true);
|
|
} else {
|
|
$conn->fileUnlink($file->path_str, NULL, true);
|
|
}
|
|
|
|
RODSConnManager::releaseConn($conn);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* rename() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function rename ($url_from, $url_to) {
|
|
try {
|
|
$file_from=ProdsDir::fromURI($url_from);
|
|
$file_to=ProdsDir::fromURI($url_to);
|
|
$conn = RODSConnManager::getConn($file_from->account);
|
|
|
|
if (is_dir($url_from)) {
|
|
$conn->rename($file_from->path_str, $file_to->path_str, 0);
|
|
} else {
|
|
$conn->rename($file_from->path_str, $file_to->path_str, 1);
|
|
}
|
|
|
|
RODSConnManager::releaseConn($conn);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* opendir() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function dir_opendir ($path, $options)
|
|
{
|
|
try {
|
|
$this->dir=ProdsDir::fromURI($path,true);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* readdir() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function dir_readdir()
|
|
{
|
|
try {
|
|
$child = $this->dir->getNextChild();
|
|
if ($child === false) return false;
|
|
return $child->getName();
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fread() and fgets() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function stream_read ($count) {
|
|
if (in_array ($this->file->getOpenMode(), array ('w', 'a', 'x'))) {
|
|
return false;
|
|
}
|
|
try {
|
|
$ret = $this->file->read($count);
|
|
$this->position=$this->file->tell();
|
|
return $ret;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fwrite() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function stream_write ($data) {
|
|
if ($this->file->getOpenMode() =='r') {
|
|
return false;
|
|
}
|
|
try {
|
|
$ret = $this->file->write($data);
|
|
$this->position=$this->file->tell();
|
|
return $ret;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
/**
|
|
* rewinddir() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function dir_rewinddir()
|
|
{
|
|
try {
|
|
$this->dir->rewind();
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* closedir() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function dir_closedir()
|
|
{
|
|
try {
|
|
$this->dir->rewind();
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fopen() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
public function stream_open($path, $mode, $options, &$opened_path)
|
|
{
|
|
|
|
// get rid of tailing 'b', if any.
|
|
if (($mode{strlen($mode) - 1} == 'b') && (strlen($mode) > 1))
|
|
$mode = substr($mode, 0, strlen($mode) - 1);
|
|
try {
|
|
$this->file = ProdsFile::fromURI($path);
|
|
$this->file->open($mode);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fstat() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_stat () {
|
|
|
|
try {
|
|
$stats=$this->file->getStats();
|
|
return array (
|
|
-1, -1, -1, -1, -1, -1, $stats->size, time (), $stats->mtime, $stats->ctime, -1, -1,
|
|
'dev' => -1,
|
|
'ino' => -1,
|
|
'mode' => -1,
|
|
'nlink' => -1,
|
|
'uid' => -1,
|
|
'gid' => -1,
|
|
'rdev' => -1,
|
|
'size' => $stats->size,
|
|
'atime' => time (),
|
|
'mtime' => $stats->mtime,
|
|
'ctime' => $stats->ctime,
|
|
'blksize' => -1,
|
|
'blocks' => -1,
|
|
);
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fclose() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_close () {
|
|
$this->file->close();
|
|
$this->position = 0;
|
|
$this->file = null;
|
|
$this->dir = null;
|
|
}
|
|
|
|
/**
|
|
* ftell() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_tell()
|
|
{
|
|
return $this->position;
|
|
}
|
|
|
|
/**
|
|
* feof() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_eof()
|
|
{
|
|
try {
|
|
$stats = $this->file->getStats();
|
|
return $this->position >= $stats->size;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return true;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fseek() handler.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_seek($offset, $whence)
|
|
{
|
|
try {
|
|
$this->file->seek($offset, $whence);
|
|
return true;
|
|
} catch (Exception $e) {
|
|
trigger_error("Got an exception:$e", E_USER_WARNING);
|
|
return false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* fflush() handler. Please Note: This method must be called for any
|
|
* changes to be committed to the repository.
|
|
*
|
|
* @access private
|
|
*/
|
|
function stream_flush()
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
|
|
stream_wrapper_register('rods', 'ProdsStreamer')
|
|
or die ('Failed to register protocol:rods');
|
|
stream_wrapper_register('rods+ticket', 'ProdsStreamer')
|
|
or die ('Failed to register protocol:rods');
|