Is there a way to use fs sync functions with browserify?

我怕爱的太早我们不能终老 提交于 2019-12-25 09:11:59

问题


I already tried the brfs transformation, but I got the following error message:

08 03 2016 16:50:14.894:ERROR [framework.browserify]: bundle error
08 03 2016 16:50:14.894:ERROR [framework.browserify]: Error: tried to statically call { readFile: [Function: readFile], readFileSync: [Function: readFileSync], readdir: [Function: readdir], readdirSync: [Function: readdirSync] } as a function while parsing file
...
PhantomJS 1.9.8 (Windows 7 0.0.0) ERROR
  You need to include some adapter that implements __karma__.start method!

when I try to use var fs = require("fs"); console.log(fs.readFileSync) in my code. Is there a way to use sync fs functions with browserify?

I want to process some non-js files which are served but no included by karma and not preprocessed by browserify. So what I need is glob and read. Any other idea how to process these files? The ideal solution would be to do it with nodejs, but I am not sure how to send the data from nodejs to the browser by using karma.


回答1:


I did not manage to make the brfs work. I created a simple fs shim instead, which supports the following features:

  • existsSync(path) -> true/false
  • readdirSync(path) -> basename[]
  • statSync(path) -> {isDirectory}
  • readFileSync(path,"utf8") -> string

It uses path-browserify, so you need to replace the require("path") dependency if you use it in a non-browserify environment. Be aware that this fs shim uses window.__karma__.files, to build a directory and file tree, so it won't work without Karma. You can use the same logic if you are able to collect the file paths from browserify. I guess you need to write a browserify plugin for that.

module.exports = (function () {

    var path = require("path");

    function absolutePath(relativePath) {
        return path.resolve(path.normalize(relativePath.split("\\").join("/")));
    }

    var KarmaFileSystem = function () {
        this.registry = new KarmaPathRegistry();
        this.converter = new KarmaUriPathConverter("/base/", "/");
        this.reader = new KarmaFileReader(this.converter);

        var servedUris = Object.keys(window.__karma__.files);
        var servedFiles = this.converter.parseUris(servedUris);
        servedFiles.forEach(this.registry.addFile, this.registry);
    };
    KarmaFileSystem.prototype = {
        constructor: KarmaFileSystem,
        workingDirectory: "/",
        existsSync: function (path) {
            return this.registry.exists(path);
        },
        readdirSync: function (path) {
            return this.registry.getContent(path);
        },
        statSync: function (path) {
            return {
                isDirectory: function () {
                    return this.registry.isDirectory(path);
                }.bind(this)
            };
        },
        readFileSync: function (file, encoding) {
            if (encoding !== "utf8")
                throw new Error("This fs.readFileSync() shim does not support other than utf8 encoding.");
            if (!this.registry.isFile(file))
                throw new Error("File does not exist: " + file);
            return this.reader.readFile(file);
        }
    };

    var KarmaPathRegistry = function KarmaPathRegistry() {
        this.paths = {};
    };

    KarmaPathRegistry.prototype = {
        constructor: KarmaPathRegistry,
        addFile: function (file) {
            file = absolutePath(file);
            this.paths[file] = KarmaPathRegistry.TYPE_FILE;
            var parentDirectory = path.dirname(file);
            this.addDirectory(parentDirectory);
        },
        addDirectory: function (directory) {
            directory = absolutePath(directory);
            this.paths[directory] = KarmaPathRegistry.TYPE_DIRECTORY;
            var parentDirectory = path.dirname(directory);
            if (parentDirectory != directory)
                this.addDirectory(parentDirectory);
        },
        isFile: function (file) {
            file = absolutePath(file);
            return this.exists(file) && this.paths[file] === KarmaPathRegistry.TYPE_FILE;
        },
        isDirectory: function (directory) {
            directory = absolutePath(directory);
            return this.exists(directory) && this.paths[directory] === KarmaPathRegistry.TYPE_DIRECTORY;
        },
        exists: function (node) {
            node = absolutePath(node);
            return this.paths.hasOwnProperty(node);
        },
        getContent: function (directory) {
            if (!this.isDirectory(directory))
                throw new Error("Not a directory: " + directory);
            directory = absolutePath(directory);
            return Object.keys(this.paths).filter(function (node) {
                if (node === directory)
                    return false;
                var parentDirectory = path.dirname(node);
                return parentDirectory === directory;
            }, this).map(function (node) {
                return path.basename(node);
            });
        }
    };

    KarmaPathRegistry.TYPE_FILE = 0;
    KarmaPathRegistry.TYPE_DIRECTORY = 1;

    var KarmaUriPathConverter = function KarmaUriPathConverter(baseUri, workingDirectory) {
        this.workingDirectory = workingDirectory;
        this.workingDirectoryPattern = this.patternFromBase(workingDirectory);
        this.baseUri = baseUri;
        this.baseUriPattern = this.patternFromBase(baseUri);
    };

    KarmaUriPathConverter.prototype = {
        constructor: KarmaUriPathConverter,
        patternFromBase: function (string, flags) {
            var pattern = "^" + string.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&');
            return new RegExp(pattern, flags);
        },
        parseUris: function (uris) {
            return uris.filter(function (uri) {
                return this.baseUriPattern.test(uri)
            }, this).map(function (uri) {
                return uri.replace(this.baseUriPattern, this.workingDirectory);
            }, this);
        },
        buildUri: function (file) {
            file = absolutePath(file);
            if (!this.workingDirectoryPattern.test(file))
                throw new Error("Path is not in working directory: " + file);
            return file.replace(this.workingDirectoryPattern, this.baseUri);
        }
    };

    var KarmaFileReader = function KarmaFileReader(converter) {
        this.converter = converter;
    };

    KarmaFileReader.prototype = {
        constructor: KarmaFileReader,
        readFile: function (file) {
            var uri = this.converter.buildUri(file);
            var xhr = new XMLHttpRequest();
            xhr.open("get", uri, false);
            xhr.send();
            return xhr.responseText;
        }
    };

    return new KarmaFileSystem();
})();


来源:https://stackoverflow.com/questions/35871783/is-there-a-way-to-use-fs-sync-functions-with-browserify

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!