zoukankan      html  css  js  c++  java
  • HTML5文件系统API和资料整理

      来着火狐开发网络的官方文档:点我打开 ;

      W3C的官方文档: 点我打开 ;

      园友的博客:  点我打开

      浏览器兼容性, 好了就chrome支持, 我刚刚更新的火狐37也不支持, nice, 太nice了:

      如果我们在http://localhost/下使用文件系统api创建了虚拟文件, 那么通过一下地址可以访问文件系统filesystem:http://localhos1/persistent/ ;

      如果没有文件系统没有本地文件, 那么应该是一个错误界面:

      

      就chrome支持本地文件系统, 所以兼容完全不用管那么多了, 我们先通过 requestFileSystem获取文件句柄, 第一个参数为临时文件系统,还是永久文件系统; 第二个参数为请求的空间大小; 第三个是回调函数; 

                //window.TEMPORARY 是 0 , window.PERSISTENT是1;
                storeType = storeType === 0 ? window.TEMPORARY : window.PERSISTENT;
                window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
                window.requestFileSystem(storeType, 5 * 1024 * 1024, function (fs) {
                    console.log(fs);//文件系统根目录句柄(root);
                }, errorHandler);        

      上面回调函数会返回一个参数fs,这个参数“fs”很重要, fs下面有很多方法, 主要是操作文件或者目录

      getDirectory是在对象上面的方法, 这个主要是处理目录,比如打开目录, 或者新建目录

    ParameterTypeNullableOptionalDescription
    path DOMString Either an absolute path or a relative path from this DirectoryEntry to the directory to be looked up or created. It is an error to attempt to create a directory whose immediate parent does not yet exist.
    options Flags
    • If create and exclusive are both true and the path already exists, getDirectory MUST fail.
    • If create is true, the path doesn't exist, and no other error occurs, getDirectory MUST create and return a corresponding DirectoryEntry.
    • If create is not true and the path doesn't exist, getDirectory MUST fail.
    • If create is not true and the path exists, but is a file, getDirectory MUST fail.
    • Otherwise, if no other error occurs, getDirectory MUST return a DirectoryEntry corresponding to path.
    successCallback EntryCallback A callback that is called to return the DirectoryEntry selected or created.
    errorCallback ErrorCallback A callback that is called when errors happen.

       

      getFile这个是获取文件, 作用是打开文件或者新建文件

    ParameterTypeNullableOptionalDescription
    path DOMString Either an absolute path or a relative path from this DirectoryEntry to the file to be looked up or created. It is an error to attempt to create a file whose immediate parent does not yet exist.
    options Flags
    • If create and exclusive are both true, and the path already exists, getFile MUST fail.
    • If create is true, the path doesn't exist, and no other error occurs, getFile MUST create it as a zero-length file and return a corresponding FileEntry.
    • If create is not true and the path doesn't exist, getFile MUST fail.
    • If create is not true and the path exists, but is a directory, getFile MUST fail.
    • Otherwise, if no other error occurs, getFile MUST return a FileEntry corresponding to path.
    successCallback EntryCallback A callback that is called to return the File selected or created.
    errorCallback ErrorCallback A callback that is called when errors happen.

        通过上面的方法,我们就获取到了文件句柄啦, 那么可以通过FileReader对象读取文件, 通过Blob对象创建二进制流, 把数据保存到文件,以及FileWriter也很重要;

        FileReader的API;

        Blob的API;

        FileWriter的API;

      

      通过 getFile 可以获取到fileEntry对象,fileEntry就是这个文件的对象,我们可以操作文件了哦, 方法如下:createWriter  file 

      通过createWriter这个的回调参数我们可以得到操作这个二进制文件的方法

      createWriter

    Creates a new FileWriter associated with the file that this FileEntry represents.

    ParameterTypeNullableOptionalDescription
    successCallback FileWriterCallback A callback that is called with the new FileWriter.
    errorCallback ErrorCallback A callback that is called when errors happen.
    Return type: void
     
      通过file方法,我们就获取到了文件数据, 这个file就是 file类型的input  中获取到的文件对象:
      file

    Returns a File that represents the current state of the file that this FileEntry represents.

    ParameterTypeNullableOptionalDescription
    successCallback FileCallback A callback that is called with the File.
    errorCallback ErrorCallback A callback that is called when errors happen.
    Return type: void
     
     
    文件上提供了remove
    文件夹上提供了removeremoveRecursively方法;
    以及moveto方法
    copyto的方法;
    但是没有提供rename,所以我们要自己通过moveto方法写一个rename方法;
     
      我通过API封装了一个在本地文件系统中文本文件的读写的小库,经测试, 可以新建文件文件夹,复制文件文件夹,读写text的文本文件(prependText,appendText),重写文件, 重命名文件等基本的功能, 可以作为学习的参考哇:
        var FS = (function () {
            /**
             * FF火狐不支持fileSystem ;http://dev.w3.org/2009/dap/file-system/file-dir-sys.html
             *
             * */
            var _FS = function() {};
            var p = _FS.prototype;
    
            //init应该创建一个文件系统,可以是临时或者是永久的;
            p.init = function (storeType) {
                var $df = $.Deferred();
                //window.TEMPORARY 是 0 , window.PERSISTENT是1;
                storeType = storeType === 0 ? window.TEMPORARY : window.PERSISTENT;
                window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
                window.requestFileSystem(storeType, 5 * 1024 * 1024, function (fs) {
                    //把这个fs句柄绑定到实例的原型上;
                    p.fs = fs;
                    $df.resolve(p);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @param "hehe/xxx/dir" 新建一个目录,如果目录存在就把目录打开;
             * @return Deferred , @param dirEntry, @this_prototpe;
             * */
            p.createDir = function (folders) {
                var $df = $.Deferred();
                if(folders === "/" || folders === "./") {
                    $df.resolve(p.fs.root, p);
                    return $df;
                };
                /**
                 * @param 文件夹的数组["hehe","wawa", "lala", "dudu"]
                 * @param 要创建文件的目录
                 * */
                var createDir = function (folders, entry) {
                    entry.getDirectory(folders.shift(), {create: true}, function (dirEntry) {
                        //如果folder还有目录就调用自己,继续新建目录; 否则就resolve;
                        var testLength = folders.length;
                        if (testLength) {
                            createDir(folders, dirEntry);
                        } else {
                            $df.resolve(dirEntry, p);
                        }
                        ;
                    }, errorHandler);
                };
                createDir(folders.split("/"), p.fs.root);
                return $df;
            };
    
            /**
             * @desc 新建文件;
             * @param fileName 要新建的文件名字;
             * @param entry 文件目录入口
             * @return 延迟对象, 该延迟对象的实际参数为 @文件句柄, @这个实例的原型;
             * */
            p.createFile = function (fileName, entry) {
                $df = $.Deferred();
                try {
                    ;
                    //如果文件存在就直接返回存在的文件;
                    entry.getFile(fileName, {create: false, exclusive: true}, function (fileEntry) {
                        $df.resolve(fileEntry, p);
                    }, function (ex) {
                        if (ex.name === "NotFoundError") {
                            //否则就新建文件并返回;
                            entry.getFile(fileName, { create: true, exclusive: true }, function (fileEntry) {
                                $df.resolve(fileEntry, p);
                            }, errorHandler);
                        } else {
                            alert("文件创建错误!");
                        }
                        ;
                    });
                } catch (ex) {
                    alert("文件打开或者创建错误!");
                }
                ;
                return $df;
            };
    
            /**
             * @desc 打开文件
             * @param fileName 要新建的文件名字;
             * @param entry 文件目录入口
             * @return 延迟对象, 该延迟对象的实际参数为 @文件句柄, @这个实例的原型;
             * */
            p.getFile = function (fileName, entry) {
                $df = $.Deferred();
                entry.getFile(fileName, { create: false, exclusive: true }, function (fileEntry) {
                    $df.resolve(fileEntry, p);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 对文件进行重写;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p.writeText = function(text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    fileEntry.file(function(file){
                        fileWriter.onwriteend = function(){
                            this.truncate(this.position);
                            $df.resolve(text);
                        };
                        //chrome,ff中BlobBuilder已经不支持了;
                        fileWriter.write(new Blob([text], { type: "text/plain" }));
                    });
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 在文件最前头添加text数据;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p .prePendText = function (text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    fileEntry.file(function(file){
                        var reader = new FileReader(file);
                        reader.onloadend = function (e) {
                            //webkit的BlobBuilder已经不支持了;
                            fileWriter.write(new Blob([text+this.result], { type: "text/plain" }));
                            $df.resolve(text);
                        };
                        reader.readAsText(file);
                    });
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 在文件末尾添加text;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p.appendText = function(text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    //我们可以通过fileWrite对文件进行写入, 也可以通过file方法先获取到file对象, 然后通过FileReader对文件进行写入;
                    fileWriter.seek(fileWriter.length);
                    fileWriter.write( new Blob([text]), {type : "text/plasin"});
                    fileWriter.onwriteend = function() {
                        $df.resolve(text);
                    }
                    /*
                    fileEntry.file(function(file){
                        var reader = new FileReader(file);
                        reader.onloadend = function (e) {
                            //webkit的BlobBuilder已经不支持了;
                            fileWriter.write(new Blob([this.result + text], { type: "text/plain" }));
                            $df.resolve(text);
                        };
                        reader.readAsText(file);
                    });
                    */
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 直接通过fileEntry获取文件text;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为text文本;
             * */
            p.getText = function (fileEntry) {
                var $df = $.Deferred();
                fileEntry.file(function (file) {
                    var reader = new FileReader();
                    reader.onloadend = function (e) {
                        $df.resolve( this.result );
                    };
                    reader.readAsText(file);
                });
                return $df;
            };
    
            /**
             * @desc 复制文件或者复制文件夹;
             * @param file文件或者文件夹来源
             * @param to文件或者文件夹要复制到的目录
             * @param 新的文件名字
             * @return 延迟对象,参数为新文件的entry文本;
             * */
            p.copy = function(file, to, name) {
                var $df = $.Deferred();
                //如果不是文件或者文件夹类型就报错;
                isDic(file);
                isDic(to);
                file.copyTo(to, name ,function( newEntry ) {
                    $df.resolve(newEntry);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 移动文件或者目录;
             * @param 文件路径或者文件夹路径
             * @param 文件夹或者文件要复制到的地方
             * @param Optional 新文件的名字
             * */
            p.move = function(url, to, newName) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName;
                if(url.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
    
                p.createDir(dir).then(function(entry, p) {
                    if(fileName) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            p.createDir(to).done(function(destEntry) {
                                newName ? fileEntry.moveTo(destEntry, newName):fileEntry.moveTo(destEntry);
                            })
                        });
                    }else{
                        p.createDir(to).done(function(dirEntry) {
                            newName?entry.moveTo(dirEntry, newName):entry.moveTo(dirEntry);
                        });
                    }
                });
                return $df;
            };
    
            /**
            * @param 直接调用move接口;
            * @param fileUrl原来文件的名字;
            * @param newName 新文件的名字;
            * */
            p.rename = function(fileUrl, newName) {
                var $df = $.Deferred();
                var dir = fileUrl.split("/");
                var fileName;
                if(fileUrl.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                if(fileName) {
                    p.move(fileUrl,dir,newName);
                }else{
                    //是文件夹要单独处理
                    fs.createDir(fileUrl).done(function(dirEntry, p) {
                        dirEntry.getParent(function(parentEntry) {
                            p.move(fileUrl, parentEntry.fullPath,newName);
                        });
                    });
                };
    
            };
    
            /**
             * @desc  删除文件
             * @param 要删除的文件夹或者文件;
             * @return 成功就返回success;
             * */
            p.remove = function(fileUrl) {
                var $df = $.Deferred();
                var dir = fileUrl.split("/");
                var fileName;
                if(fileUrl.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                    dir = dir.join("/").replace(/^/*|/*$/gi,"");
                    p.createDir(dir).then(function(entry, p) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            fileEntry.remove(function(){
                                $df.resolve("success");
                            },errorHandler);
                        });
                    });
                }else{
                    dir = dir.join("/").replace(/^/*|/*$/gi,"");
                    p.createDir(dir).then(function(entry, p) {
                        entry.removeRecursively(function(){
                            $df.resolve("success");
                        },errorHandler);
                    });
                };
                return $df;
            };
    
            /**
            * @param dirEntry
            * @return Deferred [] dirEntry
            */
            p.list = function(dirEntry) {
                var $df = $.Deferred();
                if( !dirEntry.createReader ) alert("不是目录类型");
                var reader = dirEntry.createReader();
                reader.readEntries(handleSuccess, errorHandler);
                function handleSuccess(entries) {
                    var len = entries.length;
                    var list = [];
                    for(var i=0; i<len; i++) {
                        list.push(entries[i].name);
                    };
                    $df.resolve(list);
                };
                return $df;
            }
    
            /**
             *
             * */
            p.re =  function() {};
    
            var fs  = new _FS;
            var FS = function() {};
            //继承一下;
            FS.prototype = fs;
    
            /*
             * @desc 可以是复制文件或者目录;
             * @param 文件路径或者文件夹路径
             * @param 文件夹或者文件要复制到的地方
             * @param Optional 新文件的名字
             * */
            FS.prototype.copy = function(url, to, newName) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName;
                if(url.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
    
                p.createDir(dir).then(function(entry, p) {
                    if(fileName) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            p.createDir(to).done(function(destEntry) {
                                p.copy(fileEntry, destEntry, newName);
                            })
                        });
                    }else{
                        p.createDir(to).done(function(dirEntry) {
                            p.copy(entry, dirEntry, newName);
                        });
                    }
                });
                return $df;
            };
    
            /**
             * @desc 直接读取text文件并发挥数据
             * @param 文件地址;
             * @param root,文件系统的根目录;
             * @return 延迟对象 参数为text文本;
             * */
            FS.prototype.readTextFile = function(url) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName = dir.pop();
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                if(fileName.indexOf(".txt") === -1) {
                    fileName += ".txt";
                };
                p.createDir( dir  ).done(function (dirEntry) {
                    p.getFile( fileName , dirEntry).then(function (fileEntry) {
                        p.getText(fileEntry).done(function(text) {
                            $df.resolve(text);
                        });
                    });
                });
                return $df;
            };
    
            /**
             * @desc 新建或者往已经存在的txt写信息;
             * @param "nono/hehe/xx/xx.txt"  //文件的目录;
             * @param text 要添加的文本text;
             * @return $Deferred;
             * */
            FS.prototype.writeTextFile = function(url, text) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName = dir.pop();
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                p.createDir( dir  ).done(function (dirEntry) {
                    p.createFile(fileName,dirEntry).done(function(fileEntry) {
                        p.writeText( text , fileEntry).then(function () {
                            $df.resolve(text);
                        });
                    });
                });
                return $df;
            };
            return FS;
    
            function isDic (entry) {
                if( entry.filesystem && entry.fullPath && entry.name )
                    return true;
                else
                    throw new Error("参数应该为 DicEntry 或者fileEntry类型");
            };
    
            function errorHandler(err) {
                var msg = 'An error occured: ';
    
                switch (err.code) {
                    case FileError.NOT_FOUND_ERR:
                        msg += 'File or directory not found';
                        break;
    
                    case FileError.NOT_READABLE_ERR:
                        msg += 'File or directory not readable';
                        break;
    
                    case FileError.PATH_EXISTS_ERR:
                        msg += 'File or directory already exists';
                        break;
    
                    case FileError.TYPE_MISMATCH_ERR:
                        msg += 'Invalid filetype';
                        break;
    
                    default:
                        msg += 'Unknown Error';
                        break;
                };
                console.log(msg);
            };
        })();
    View Code

       API以及测试代码也全部给粗来, chrome下也( •̀ ω •́ )y可直接调试:

    <html>
    <head>
        <meta charset="utf-8"/>
        <title>file system</title>
    </head>
    <script src="http://cdn.bootcss.com/jquery/1.8.2/jquery.js"></script>
    <pre>
    
        //实现之前我们要先实例化该组件对象;
        var fs = new FS();
    
        //因为是文件系统api是异步的,我们需要用到延迟对象,让流程清晰一点;
        这个是在根目录下新建4-19这个文件夹
         fs.init().then(function() {
            return fs.createDir("4-19");
         })
    
        
         init完毕以后, 直接写文件到txt,如果文件夹或者文件不存在,会自动创建;
         fs.init().then(function () {
         往文件写入txt文本数据;
             fs.writeTextFile("/4-19/hehe1.txt","ddd").done(function(text){
                console.log(text);
             });
         });
         
    
        
         init完毕以后, 直接读取文件的text并作为返回;
         fs.init().then(function () {
         往文件写入txt文本数据;
             fs.readTextFile("/4-19/hehe1.txt").done(function(text){
                console.log("读取文件----/4-19/hehe.txt");
                console.log(text);
             });
         });
         
    
        
         往目录/4-19/的文件hehe.txt 添加(append)文本;
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.prePendText("hehenono", fileEntry);
             });
         });
         
    
        往目录/4-19/的文件hehe.txt的前面添加(prePendText)文本;
        
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.prePendTexfst("hehenono", fileEntry);
             });
         });
         
    
        
         //往后面添加文本
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.appendText("sssss", fileEntry);
             });
         });
         
    
        从文件夹"/4-19/hehe.txt"复制文件到copycat_hehe的目录;
        
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
            fs.copy("/4-19/hehe.txt","copycat_hehe","copy_hehe.txt");
         });
         
    
        删除copycat_hehe/copy_hehe.txt这个文件
        
         fs.init().then(function() {
         }).then(function () {
            fs.remove("copycat_hehe/copy_hehe.txt");
         });
         
    
        复制当前的文件到,4-19-c, 没有复制子文件或者只目录;
         fs.init().then(function() {
         }).then(function () {
            fs.move("4-19 ","4-19-c");
         });
         
    
        只有复制文件,没有复制文件内容
         fs.init().then(function() {
         }).then(function () {
            fs.move("reName--4-19/hehe1.txt ","reHehe");
         });
         
    
       
         删除文件或者是删除文件夹;
         fs.init().then(function() {
        }).then(function () {
            fs.remove("nono");
        });
         
       
          重新命名,可以是文件或者文件夹
         fs.init().then(function() {
        }).then(function () {
            fs.rename("4-19","reName--4-19")
        });
         
    
         
         通过fs.list方法获取根目录的目录结构;
        fs.init().then(function () {
            return fs.createDir("./");
        }).then(function (entry) {
            return fs.list(entry)
        }).done(function(list) {
            console.log(list);
        });
         
         //新建一个叫做nono的目录;
        fs.init().then(function () {
            return fs.createDir("nono/");
        }).done(function (entry) {
        });
    
    </pre>
    <body>
    <script>
        var FS = (function () {
            /**
             * FF火狐不支持fileSystem ;http://dev.w3.org/2009/dap/file-system/file-dir-sys.html
             *
             * */
            var _FS = function() {};
            var p = _FS.prototype;
    
            //init应该创建一个文件系统,可以是临时或者是永久的;
            p.init = function (storeType) {
                var $df = $.Deferred();
                //window.TEMPORARY 是 0 , window.PERSISTENT是1;
                storeType = storeType === 0 ? window.TEMPORARY : window.PERSISTENT;
                window.requestFileSystem = window.requestFileSystem || window.webkitRequestFileSystem;
                window.requestFileSystem(storeType, 5 * 1024 * 1024, function (fs) {
                    //把这个fs句柄绑定到实例的原型上;
                    p.fs = fs;
                    $df.resolve(p);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @param "hehe/xxx/dir" 新建一个目录,如果目录存在就把目录打开;
             * @return Deferred , @param dirEntry, @this_prototpe;
             * */
            p.createDir = function (folders) {
                var $df = $.Deferred();
                if(folders === "/" || folders === "./") {
                    $df.resolve(p.fs.root, p);
                    return $df;
                };
                /**
                 * @param 文件夹的数组["hehe","wawa", "lala", "dudu"]
                 * @param 要创建文件的目录
                 * */
                var createDir = function (folders, entry) {
                    entry.getDirectory(folders.shift(), {create: true}, function (dirEntry) {
                        //如果folder还有目录就调用自己,继续新建目录; 否则就resolve;
                        var testLength = folders.length;
                        if (testLength) {
                            createDir(folders, dirEntry);
                        } else {
                            $df.resolve(dirEntry, p);
                        }
                        ;
                    }, errorHandler);
                };
                createDir(folders.split("/"), p.fs.root);
                return $df;
            };
    
            /**
             * @desc 新建文件;
             * @param fileName 要新建的文件名字;
             * @param entry 文件目录入口
             * @return 延迟对象, 该延迟对象的实际参数为 @文件句柄, @这个实例的原型;
             * */
            p.createFile = function (fileName, entry) {
                $df = $.Deferred();
                try {
                    ;
                    //如果文件存在就直接返回存在的文件;
                    entry.getFile(fileName, {create: false, exclusive: true}, function (fileEntry) {
                        $df.resolve(fileEntry, p);
                    }, function (ex) {
                        if (ex.name === "NotFoundError") {
                            //否则就新建文件并返回;
                            entry.getFile(fileName, { create: true, exclusive: true }, function (fileEntry) {
                                $df.resolve(fileEntry, p);
                            }, errorHandler);
                        } else {
                            alert("文件创建错误!");
                        }
                        ;
                    });
                } catch (ex) {
                    alert("文件打开或者创建错误!");
                }
                ;
                return $df;
            };
    
            /**
             * @desc 打开文件
             * @param fileName 要新建的文件名字;
             * @param entry 文件目录入口
             * @return 延迟对象, 该延迟对象的实际参数为 @文件句柄, @这个实例的原型;
             * */
            p.getFile = function (fileName, entry) {
                $df = $.Deferred();
                entry.getFile(fileName, { create: false, exclusive: true }, function (fileEntry) {
                    $df.resolve(fileEntry, p);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 对文件进行重写;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p.writeText = function(text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    fileEntry.file(function(file){
                        fileWriter.onwriteend = function(){
                            this.truncate(this.position);
                            $df.resolve(text);
                        };
                        //chrome,ff中BlobBuilder已经不支持了;
                        fileWriter.write(new Blob([text], { type: "text/plain" }));
                    });
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 在文件最前头添加text数据;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p .prePendText = function (text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    fileEntry.file(function(file){
                        var reader = new FileReader(file);
                        reader.onloadend = function (e) {
                            //webkit的BlobBuilder已经不支持了;
                            fileWriter.write(new Blob([text+this.result], { type: "text/plain" }));
                            $df.resolve(text);
                        };
                        reader.readAsText(file);
                    });
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 在文件末尾添加text;
             * @param text 要写入的文本数据;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为写入的text文本;
             * */
            p.appendText = function(text, fileEntry) {
                $df = $.Deferred();
                fileEntry.createWriter(function (fileWriter) {
                    //我们可以通过fileWrite对文件进行写入, 也可以通过file方法先获取到file对象, 然后通过FileReader对文件进行写入;
                    fileWriter.seek(fileWriter.length);
                    fileWriter.write( new Blob([text]), {type : "text/plasin"});
                    fileWriter.onwriteend = function() {
                        $df.resolve(text);
                    }
                    /*
                    fileEntry.file(function(file){
                        var reader = new FileReader(file);
                        reader.onloadend = function (e) {
                            //webkit的BlobBuilder已经不支持了;
                            fileWriter.write(new Blob([this.result + text], { type: "text/plain" }));
                            $df.resolve(text);
                        };
                        reader.readAsText(file);
                    });
                    */
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 直接通过fileEntry获取文件text;
             * @param fileEntry 文件的句柄;
             * @return 延迟对象,参数为text文本;
             * */
            p.getText = function (fileEntry) {
                var $df = $.Deferred();
                fileEntry.file(function (file) {
                    var reader = new FileReader();
                    reader.onloadend = function (e) {
                        $df.resolve( this.result );
                    };
                    reader.readAsText(file);
                });
                return $df;
            };
    
            /**
             * @desc 复制文件或者复制文件夹;
             * @param file文件或者文件夹来源
             * @param to文件或者文件夹要复制到的目录
             * @param 新的文件名字
             * @return 延迟对象,参数为新文件的entry文本;
             * */
            p.copy = function(file, to, name) {
                var $df = $.Deferred();
                //如果不是文件或者文件夹类型就报错;
                isDic(file);
                isDic(to);
                file.copyTo(to, name ,function( newEntry ) {
                    $df.resolve(newEntry);
                }, errorHandler);
                return $df;
            };
    
            /**
             * @desc 移动文件或者目录;
             * @param 文件路径或者文件夹路径
             * @param 文件夹或者文件要复制到的地方
             * @param Optional 新文件的名字
             * */
            p.move = function(url, to, newName) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName;
                if(url.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
    
                p.createDir(dir).then(function(entry, p) {
                    if(fileName) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            p.createDir(to).done(function(destEntry) {
                                newName ? fileEntry.moveTo(destEntry, newName):fileEntry.moveTo(destEntry);
                            })
                        });
                    }else{
                        p.createDir(to).done(function(dirEntry) {
                            newName?entry.moveTo(dirEntry, newName):entry.moveTo(dirEntry);
                        });
                    }
                });
                return $df;
            };
    
            /**
            * @param 直接调用move接口;
            * @param fileUrl原来文件的名字;
            * @param newName 新文件的名字;
            * */
            p.rename = function(fileUrl, newName) {
                var $df = $.Deferred();
                var dir = fileUrl.split("/");
                var fileName;
                if(fileUrl.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                if(fileName) {
                    p.move(fileUrl,dir,newName);
                }else{
                    //是文件夹要单独处理
                    fs.createDir(fileUrl).done(function(dirEntry, p) {
                        dirEntry.getParent(function(parentEntry) {
                            p.move(fileUrl, parentEntry.fullPath,newName);
                        });
                    });
                };
    
            };
    
            /**
             * @desc  删除文件
             * @param 要删除的文件夹或者文件;
             * @return 成功就返回success;
             * */
            p.remove = function(fileUrl) {
                var $df = $.Deferred();
                var dir = fileUrl.split("/");
                var fileName;
                if(fileUrl.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                    dir = dir.join("/").replace(/^/*|/*$/gi,"");
                    p.createDir(dir).then(function(entry, p) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            fileEntry.remove(function(){
                                $df.resolve("success");
                            },errorHandler);
                        });
                    });
                }else{
                    dir = dir.join("/").replace(/^/*|/*$/gi,"");
                    p.createDir(dir).then(function(entry, p) {
                        entry.removeRecursively(function(){
                            $df.resolve("success");
                        },errorHandler);
                    });
                };
                return $df;
            };
    
            /**
            * @param dirEntry
            * @return Deferred [] dirEntry
            */
            p.list = function(dirEntry) {
                var $df = $.Deferred();
                if( !dirEntry.createReader ) alert("不是目录类型");
                var reader = dirEntry.createReader();
                reader.readEntries(handleSuccess, errorHandler);
                function handleSuccess(entries) {
                    var len = entries.length;
                    var list = [];
                    for(var i=0; i<len; i++) {
                        list.push(entries[i].name);
                    };
                    $df.resolve(list);
                };
                return $df;
            }
    
            /**
             *
             * */
            p.re =  function() {};
    
            var fs  = new _FS;
            var FS = function() {};
            //继承一下;
            FS.prototype = fs;
    
            /*
             * @desc 可以是复制文件或者目录;
             * @param 文件路径或者文件夹路径
             * @param 文件夹或者文件要复制到的地方
             * @param Optional 新文件的名字
             * */
            FS.prototype.copy = function(url, to, newName) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName;
                if(url.lastIndexOf(".") !== -1) {
                    fileName = dir.pop();
                };
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
    
                p.createDir(dir).then(function(entry, p) {
                    if(fileName) {
                        p.createFile(fileName, entry).then(function(fileEntry) {
                            p.createDir(to).done(function(destEntry) {
                                p.copy(fileEntry, destEntry, newName);
                            })
                        });
                    }else{
                        p.createDir(to).done(function(dirEntry) {
                            p.copy(entry, dirEntry, newName);
                        });
                    }
                });
                return $df;
            };
    
            /**
             * @desc 直接读取text文件并发挥数据
             * @param 文件地址;
             * @param root,文件系统的根目录;
             * @return 延迟对象 参数为text文本;
             * */
            FS.prototype.readTextFile = function(url) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName = dir.pop();
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                if(fileName.indexOf(".txt") === -1) {
                    fileName += ".txt";
                };
                p.createDir( dir  ).done(function (dirEntry) {
                    p.getFile( fileName , dirEntry).then(function (fileEntry) {
                        p.getText(fileEntry).done(function(text) {
                            $df.resolve(text);
                        });
                    });
                });
                return $df;
            };
    
            /**
             * @desc 新建或者往已经存在的txt写信息;
             * @param "nono/hehe/xx/xx.txt"  //文件的目录;
             * @param text 要添加的文本text;
             * @return $Deferred;
             * */
            FS.prototype.writeTextFile = function(url, text) {
                var $df = $.Deferred();
                var dir = url.split("/");
                var fileName = dir.pop();
                dir = dir.join("/").replace(/^/*|/*$/gi,"");
                p.createDir( dir  ).done(function (dirEntry) {
                    p.createFile(fileName,dirEntry).done(function(fileEntry) {
                        p.writeText( text , fileEntry).then(function () {
                            $df.resolve(text);
                        });
                    });
                });
                return $df;
            };
            return FS;
    
            function isDic (entry) {
                if( entry.filesystem && entry.fullPath && entry.name )
                    return true;
                else
                    throw new Error("参数应该为 DicEntry 或者fileEntry类型");
            };
    
            function errorHandler(err) {
                var msg = 'An error occured: ';
    
                switch (err.code) {
                    case FileError.NOT_FOUND_ERR:
                        msg += 'File or directory not found';
                        break;
    
                    case FileError.NOT_READABLE_ERR:
                        msg += 'File or directory not readable';
                        break;
    
                    case FileError.PATH_EXISTS_ERR:
                        msg += 'File or directory already exists';
                        break;
    
                    case FileError.TYPE_MISMATCH_ERR:
                        msg += 'Invalid filetype';
                        break;
    
                    default:
                        msg += 'Unknown Error';
                        break;
                };
                console.log(msg);
            };
        })();
    </script>
    <script> 
    
        //实现之前我们要先实例化该组件对象;
        var fs = new FS();
    
        //因为是文件系统api是异步的,我们需要用到延迟对象,让流程清晰一点;
        /*这个是在根目录下新建4-19这个文件夹
         fs.init().then(function() {
            return fs.createDir("4-19");
         })
    
        /*
         //init完毕以后, 直接写文件到txt,如果文件夹或者文件不存在,会自动创建;
         fs.init().then(function () {
         //往文件写入txt文本数据;
             fs.writeTextFile("/4-19/hehe1.txt","ddd").done(function(text){
                console.log(text);
             });
         });
         */
    
        /*
         //init完毕以后, 直接读取文件的text并作为返回;
         fs.init().then(function () {
         //往文件写入txt文本数据;
             fs.readTextFile("/4-19/hehe1.txt").done(function(text){
                console.log("读取文件----/4-19/hehe.txt");
                console.log(text);
             });
         });
         */
    
        /*
         //往目录/4-19/的文件hehe.txt 添加(append)文本;
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.prePendText("hehenono", fileEntry);
             });
         });
         */
    
        //往目录/4-19/的文件hehe.txt的前面添加(prePendText)文本;
        /*
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.prePendTexfst("hehenono", fileEntry);
             });
         });
         */
    
        /*
         //往后面添加文本
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
             fs.createFile("hehe.txt", entry).then(function (fileEntry, p) {
                fs.appendText("sssss", fileEntry);
             });
         });
         */
    
        //从文件夹"/4-19/hehe.txt"复制文件到copycat_hehe的目录;
        /*
         fs.init().then(function() {
         return fs.createDir("4-19");
         }).then(function (entry) {
            fs.copy("/4-19/hehe.txt","copycat_hehe","copy_hehe.txt");
         });
         */
    
        //删除copycat_hehe/copy_hehe.txt这个文件
        /*
         fs.init().then(function() {
         }).then(function () {
            fs.remove("copycat_hehe/copy_hehe.txt");
         });
         */
    
        /*复制当前的文件到,4-19-c, 没有复制子文件或者只目录;
         fs.init().then(function() {
         }).then(function () {
            fs.move("4-19 ","4-19-c");
         });
         */
    
        /*只有复制文件,没有复制文件内容
         fs.init().then(function() {
         }).then(function () {
            fs.move("reName--4-19/hehe1.txt ","reHehe");
         });
         */
    
        /**
         * 删除文件或者是删除文件夹;
         fs.init().then(function() {
        }).then(function () {
            fs.remove("nono");
        });
         * */
        /**
         * 重新命名,可以是文件或者文件夹
         fs.init().then(function() {
        }).then(function () {
            fs.rename("4-19","reName--4-19")
        });
         * */
    
         /**
         *通过fs.list方法获取根目录的目录结构;
        fs.init().then(function () {
            return fs.createDir("./");
        }).then(function (entry) {
            return fs.list(entry)
        }).done(function(list) {
            console.log(list);
        });
         */
         //新建一个叫做nono的目录;
        fs.init().then(function () {
            return fs.createDir("nono/");
        }).done(function (entry) {
        });
        /**
         * https://github.com/ebidel/filer.js/blob/master/src/filer.js
         * */
    </script>
    </body>
    </html>

       火狐官方的404太可爱了, 眼睛会动;

      

      老外写的filesystem库, 托管在github上面哦, 可以参考学习,点击带我飞吧

    作者: NONO
    出处:http://www.cnblogs.com/diligenceday/
    QQ:287101329 

  • 相关阅读:
    go语言中通过http访问需要认证的api
    Mysql两个time类型计算时间相减
    gorm中数据库datetime类型的映射和time.Time的格式化
    最详细的六种装饰器写法,学不会你找我!
    深度学习中的四种激活函数
    看完这篇文章,相信我,你已经掌握正则表达式了!
    新手还在问学Python应该看什么书,老手已经进来下载了(附100本pdf电子书下载)
    Python轻松实现一个毕业生信息管理系统!
    Python一键搞定批量合成PDF
    网易云10万+音乐竟然能用Python一键下载!
  • 原文地址:https://www.cnblogs.com/diligenceday/p/4435693.html
Copyright © 2011-2022 走看看