在未修改的安装中,如何配置Quercus使PHP文件函数使用Apache Commons VFS访问文件?
这是相当多的开发!这里的答案太多了。总之,这里有两个主要的障碍需要克服:
- 在PHP中实现使用VFS I/O而不是常规I/O的函数
- 将标准文件函数(fopen/fread/fwrite/fclose)替换为上述函数。
实现Quercus模块相当简单——你定义了在php中可用的函数。该模块的主要工作是提供VFS的接口。
class VFSModule extends AbstractQuercusModule
{
FileSystemManager fsManager = VFS.getManager();
public Object vfs_fopen(String filename, String mode) {
FileObject file = fsManager.resolveFile(filename);
if (mode.equals("r"))
return file.getContent().getInputStream();
else if (mode.equals("w"))
return file.getContent().getOutputStream();
throw new IllegalArgumentException("unsupported mode; "+mode);
}
function String vfs_fread(Object stream, int length) {
InputStream in = (InputStream)stream;
byte[] buffer = new byte[length];
int read = in.read(buffer);
// todo - handle smaller than length reads
return buffer;
}
function void vfs_fwrite(Object stream, int length, byte[] data) {
OutputStream out = (OutputStream)stream;
out.write(data);
}
}
(省略IOException处理以避免混乱。)
模块编码完成后,作为完整性测试,编写一些php脚本,从该模块调用自定义vfs函数。
由于您可以直接从PHP调用java(和vfs),因此您可以通过在PHP中编写等效的vfs调用而无需模块即可完成此操作。
$mgr = org.apache.commons.vfs2.VFS.getManager();
function vfs_open($filename, $mode) {
if ($mode=="r") {
return $mgr->resolveFile($filename)->content->getInputStream();
}
else if ($mode=="w") {
return $mgr->resolveFile($filename)->content->getOutputStream();
}
// todo - handle other mode combinations
}
function vfs_read($resource, $length) {
$buf = str_repeat(" ", 1024);
$lenRead = $resource->read($buf, 0, 1024);
if ($lenRead<0) return "";
return substr($buf, 0, $lenRead);
}
下一部分是将这些函数映射到标准php文件函数。这可以通过几种方式实现,如重新定义内置php函数中所述。