php7性能大幅提高,吸引了很多開發者升級,升級面臨的問題很多,mongodb的支持就是其中之一php
php7使用了新的mongdb驅動:git
http://php.net/manual/en/set.mongodb.phpgithub
若是僅僅使用驅動封裝的類及方法很是的不方便,因此還必須藉助另外一個項目:mongodb
http://php.net/manual/en/mongodb.tutorial.library.phpapi
mongo-php-library對應的文檔有:數組
文檔: http://mongodb.github.io/mongo-php-library/php7
API: http://mongodb.github.io/mongo-php-library/api/app
mongo-php-library目前的最新版本是1.0.2,這個版本還不支持gridfs的操做。函數
可是從性能
roadmap上已經指出將支持gridfs,可是發佈日期沒有肯定
Epic
- [PHPLIB-114] - Implement GridFS specification
從Github(https://github.com/mongodb/mongo-php-library)代碼上看,/src/GridFS下一直都有更新
仔細閱讀了一下代碼
爲了在發佈後能很快實現遷移,我想已經徹底能夠進行開發測試了。
通過一番試驗,記錄一些要點以下:
1.既然是遷移,舊代碼對GridFS的調用但願儘量的不用修改,因此能夠封裝一個MongoDB\GridFS\Bucket的子類,在子類裏封裝舊版本GridFS的一些經常使用方法
class MyGridFS extends MongoDB\GridFS\Bucket { //舊驅動有findOne方法,metadata均放在返回對象的file屬性以數組方式存放 function findOne($filename) { $ret = new stdClass(); $file = array(); $o=$this->getCollectionWrapper()->findFileByFilenameAndRevision($filename,0); if ($o==NULL) return NULL; $file['md5'] = $o->md5; $file['length'] = $o->length; $file['filename'] = $o->filename; $file['chunkSize'] = $o->chunkSize; $file['_id'] = $o->_id; $file['uploadDate'] = $o->uploadDate; $ret->file = $file; return $ret; } //舊的驅動能夠將文件字節字符串直接存入gridfs,新的再也不支持,因此變通先存入一個臨時文件,而後再打開臨時文件的stream進行寫入 //爲了提升性能,臨時文件所在目錄最好爲基於內存 function storeBytes($bytes,$metadata) { $filename = $metadata['filename']; if (!$filename) return false; $tmpfile = WORK_TEMP_PATH.md5($filename.time()); file_put_contents($tmpfile,$bytes); $handle = fopen($tmpfile, "r"); $this->uploadFromStream($filename,$handle); @unlink($tmpfile); } function storeFile($filepath,$metadata) { $filename = $metadata['filename']; if (!$filename) return false; $handle = fopen($filepath, "r"); $this->uploadFromStream($filename,$handle); } function getBytes($filename,array $options = []) { $resource = $this->openDownloadStreamByName($filename,$options); return stream_get_contents($resource); } }
2. 實例化grid對象,實際上就是Bucket
$this->grid= new MyGridFS($manage,$dbname,array('bucketName '=>$bucketName));
注意,構造函數第一個參數必須是 MongoDB\Driver\Manager(驅動自帶),不能是mongo-php-library帶的MongoDB\Client,這有點難以理解,可能考慮了GridFS這部分能從mongo-php-library獨立出來吧。
3.findOne裏getCollectionWrapper()->findFileByFilenameAndRevision($filename,0); 返回對象裏的uploadDate已經再也不是MongoDate,而是 MongoDB\BSON\UTCDateTime,因此要取出上傳時的時間戳方法要修改:
$o->file['uploadDate']->sec 修改爲 $o->file['uploadDate']->toDateTime()->getTimestamp()
暫時就這麼多!