'use strict';

var util = require('util');
var Transform = require('readable-stream/transform');


function Finder (file, markers) {
    Transform.call(this);
    this.markers = markers;
    this.file = file;
}

util.inherits(Finder, Transform);

// this directly manipulates the markers object.
// TODO abstract it away?
// TODO this could be a read stream except this allows
// option to replace on same pass as find.
Finder.prototype._transform = function (chunk, enc, done) {
    var content = chunk.toString('utf8');
    var m = this.markers.m;
    var tags = this.markers.getMarkerTags();
    var file = this.file;

    tags.forEach(function (tag) {
        var matches = content.match(m[tag].regexgm);

        if (matches) {
            if (!m[tag].files[file.path]) {
                m[tag].files[file.path] = {};
            }
            // TODO I don't think the groups are needed except for debugging
            var decoded = matches.map(match => {
                var res = m[tag].regexm.exec(match);
                return {match: res[0], groups: res.slice(1)};
            });
            m[tag].files[file.path] = decoded;
        }
    });
    // no transform, but maybe will be
    done(null, content);
}

function Replacer (file, markers) {
    Transform.call(this);
    this.markers = markers;
    this.file = file;
}

util.inherits(Replacer, Transform);

Replacer.prototype._transform = function (chunk, enc, done) {
    var content = chunk.toString('utf8');
    var m = this.markers.m;
    var tags = this.markers.getMarkerTags();
    var file = this.file;


    // go through each tag using the supplied regex with the 'gm'
    // flags so RegExp.exec can be used to iterate over each match
    // in this file.
    tags.forEach(function (tag) {
        // if this tag wants access to the file information pass it
        // as the first argument (in front of string.replace arguments).
        var context = {
            tag: tag,
            data: m[tag].data,
            file: {cwd: file.cwd, base: file.base, path: file.path}
        };
        var replacer;
        if (typeof m[tag].replace === 'string') {
            replacer = m[tag].replace;
        } else {
            replacer = function() {
                var args = Array.prototype.slice.call(arguments);
                args.unshift(context);
                return m[tag].replace.apply(null, args);
            }
        }

        content = content.replace(m[tag].regexgm, replacer);
    });

    done(null, content);
}

module.exports = {Finder: Finder, Replacer: Replacer};

@@ -114,32 +114,39 @@
 r (file, markers
+, debug
 ) %7B%0A    Transfor
@@ -201,32 +201,56 @@
 is.file = file;%0A
+    this.debug = debug;%0A
 %7D%0A%0Autil.inherits
@@ -645,16 +645,78 @@
 s.file;%0A
+    var debug = this.debug;%0A%0A    // find matches for each tag.
 %0A    tag
@@ -1176,24 +1176,72 @@
         %7D);%0A
+            // use the source regex as the hash%0A
             
@@ -1263,16 +1263,27 @@
 le.path%5D
+%5Bm%5Btag%5D.re%5D
  = decod
@@ -1308,46 +1308,42 @@
 %7D);%0A
+%0A
     // 
-no transform, but maybe will be
+return unmodified content.
 %0A   

Store per-file matches correctly. Add debug option.