<commit_before>
  basis.require('basis.dom.event');
  basis.require('basis.l10n');
  basis.require('basis.template');
  basis.require('basis.template.htmlfgen');


 /**
  * @namespace basis.template.html
  */

  var namespace = this.path;


  //
  // import names
  //

  var document = global.document;
  var domEvent = basis.dom.event;
  var arrayFrom = basis.array.from;
  var camelize = basis.string.camelize;
  var l10nToken = basis.l10n.token;
  var getFunctions = basis.template.htmlfgen.getFunctions;

  var TemplateSwitchConfig = basis.template.TemplateSwitchConfig;
  var TemplateSwitcher = basis.template.TemplateSwitcher;
  var Template = basis.template.Template;

  var TYPE_ELEMENT = basis.template.TYPE_ELEMENT;
  var TYPE_ATTRIBUTE = basis.template.TYPE_ATTRIBUTE;
  var TYPE_TEXT = basis.template.TYPE_TEXT;
  var TYPE_COMMENT = basis.template.TYPE_COMMENT;

  var TOKEN_TYPE = basis.template.TOKEN_TYPE;
  var TOKEN_BINDINGS = basis.template.TOKEN_BINDINGS;
  var TOKEN_REFS = basis.template.TOKEN_REFS;

  var ATTR_NAME = basis.template.ATTR_NAME;
  var ATTR_VALUE = basis.template.ATTR_VALUE;
  var ATTR_NAME_BY_TYPE = basis.template.ATTR_NAME_BY_TYPE;

  var ELEMENT_NAME = basis.template.ELEMENT_NAME;

  var TEXT_VALUE = basis.template.TEXT_VALUE;
  var COMMENT_VALUE = basis.template.COMMENT_VALUE;



  //
  // main part
  //

  var eventAttr = /^event-(.+)+/;
  var basisTemplateIdMarker = 'basisTemplateId_' + basis.genUID();

  // dictionaries
  var tmplEventListeners = {};
  var templates = {};

  var namespaceURI = {
    svg: 'http://www.w3.org/2000/svg'
  };

  // events
  var afterEventAction = {};
  var insideElementEvent = {};
  var MOUSE_ENTER_LEAVE_SUPPORT = 'onmouseenter' in document.documentElement;
  var CAPTURE_FALLBACK = !document.addEventListener && '__basisTemplate' + parseInt(1e9 * Math.random());
  if (CAPTURE_FALLBACK)
    global[CAPTURE_FALLBACK] = function(eventName, event){
       // trigger global handlers proceesing
      domEvent.fireEvent(document, eventName);

      // prevent twice global handlers processing
      event.returnValue = true;

      var listener = tmplEventListeners[eventName];
      if (listener)
        listener(new domEvent.Event(event));
    };

  // test for browser (IE) normalize text nodes during cloning
  var CLONE_NORMALIZATION_TEXT_BUG = (function(){
    var element = document.createElement('div');
    element.appendChild(document.createTextNode('a'));
    element.appendChild(document.createTextNode('a'));
    return element.cloneNode(true).childNodes.length == 1;
  })();

  // test for class attribute set via setAttribute bug (IE7 and lower)
  var SET_CLASS_ATTRIBUTE_BUG = (function(){
    var element = document.createElement('div');
    element.setAttribute('class', 'a');
    return !element.className;
  })();

  // test for style attribute set via setAttribute bug (IE7 and lower)
  var SET_STYLE_ATTRIBUTE_BUG = (function(){
    var element = document.createElement('div');
    element.setAttribute('style', 'position:absolute');
    return element.style.position != 'absolute';
  })();

  // test set style properties doesn't throw an error (IE8 and lower)
  var IS_SET_STYLE_SAFE = !!(function(){
    try {
      return document.documentElement.style.color = 'x';
    } catch(e) {}
  })();

  // old Firefox has no Node#contains method (Firefox 8 and lower)
  if (typeof Node != 'undefined' && !Node.prototype.contains)
    Node.prototype.contains = function(child){
      return !!(this.compareDocumentPosition(child) & 16); // Node.DOCUMENT_POSITION_CONTAINED_BY = 16
    };


  // l10n
  var l10nTemplates = {};
  function getL10nTemplate(token){
    var template = basis.template.getL10nTemplate(token);
    var id = template.templateId;
    var htmlTemplate = l10nTemplates[id];

    if (!htmlTemplate)
      htmlTemplate = l10nTemplates[id] = new HtmlTemplate(template.source);

    return htmlTemplate;
  }


  //
  // Constructs dom structure
  //

 /**
  * @func
  */
  function createEventHandler(attrName){
   /**
    * @param {basis.dom.event.Event} event
    */
    return function(event){

      // don't process right click - generaly FF problem
      if (event.type == 'click' && event.which == 3)
        return;

      var bubble = insideElementEvent[event.type] || (event.type != 'mouseenter' && event.type != 'mouseleave');
      var attrCursor = event.sender;
      var attr;

      // search for nearest node with event-{eventName} attribute
      // Note: IE events may have no event source, nothing to do in this case
      while (attrCursor)
      {
        attr = attrCursor.getAttribute && attrCursor.getAttribute(attrName);

        if (!bubble || typeof attr == 'string')
          break;

        attrCursor = attrCursor.parentNode;
      }

      // attribute found
      if (typeof attr == 'string')
      {
        // search for nearest node with basis template marker
        var cursor = attrCursor;
        var actionTarget = cursor;
        var refId;
        var tmplRef;

        if (insideElementEvent[event.type])
        {
          var relTarget = event.relatedTarget;
          if (relTarget && (cursor === relTarget || cursor.contains(relTarget)))
            cursor = null;  // prevent action processing
        }

        while (cursor)
        {
          refId = cursor[basisTemplateIdMarker];
          if (typeof refId == 'number')
          {
            // if node found, return it
            if (tmplRef = resolveInstanceById(refId))
              break;
          }
          cursor = cursor.parentNode;
        }

        if (tmplRef && tmplRef.action)
        {
          var actions = attr.trim().split(/\s+/);
          event.actionTarget = actionTarget;
          for (var i = 0, actionName; actionName = actions[i++];)
            tmplRef.action.call(tmplRef.context, actionName, event);
        }
      }

      if (event.type in afterEventAction)
        afterEventAction[event.type](event, attrCursor);
    };
  }
<commit_msg>basis.template: build-in actions to manage events `prevent-default` and `stop-propagation`<commit_after>
  basis.require('basis.dom.event');
  basis.require('basis.l10n');
  basis.require('basis.template');
  basis.require('basis.template.htmlfgen');


 /**
  * @namespace basis.template.html
  */

  var namespace = this.path;


  //
  // import names
  //

  var document = global.document;
  var domEvent = basis.dom.event;
  var arrayFrom = basis.array.from;
  var camelize = basis.string.camelize;
  var l10nToken = basis.l10n.token;
  var getFunctions = basis.template.htmlfgen.getFunctions;

  var TemplateSwitchConfig = basis.template.TemplateSwitchConfig;
  var TemplateSwitcher = basis.template.TemplateSwitcher;
  var Template = basis.template.Template;

  var TYPE_ELEMENT = basis.template.TYPE_ELEMENT;
  var TYPE_ATTRIBUTE = basis.template.TYPE_ATTRIBUTE;
  var TYPE_TEXT = basis.template.TYPE_TEXT;
  var TYPE_COMMENT = basis.template.TYPE_COMMENT;

  var TOKEN_TYPE = basis.template.TOKEN_TYPE;
  var TOKEN_BINDINGS = basis.template.TOKEN_BINDINGS;
  var TOKEN_REFS = basis.template.TOKEN_REFS;

  var ATTR_NAME = basis.template.ATTR_NAME;
  var ATTR_VALUE = basis.template.ATTR_VALUE;
  var ATTR_NAME_BY_TYPE = basis.template.ATTR_NAME_BY_TYPE;

  var ELEMENT_NAME = basis.template.ELEMENT_NAME;

  var TEXT_VALUE = basis.template.TEXT_VALUE;
  var COMMENT_VALUE = basis.template.COMMENT_VALUE;



  //
  // main part
  //

  var eventAttr = /^event-(.+)+/;
  var basisTemplateIdMarker = 'basisTemplateId_' + basis.genUID();

  // dictionaries
  var tmplEventListeners = {};
  var templates = {};

  var namespaceURI = {
    svg: 'http://www.w3.org/2000/svg'
  };

  // events
  var afterEventAction = {};
  var insideElementEvent = {};
  var MOUSE_ENTER_LEAVE_SUPPORT = 'onmouseenter' in document.documentElement;
  var CAPTURE_FALLBACK = !document.addEventListener && '__basisTemplate' + parseInt(1e9 * Math.random());
  if (CAPTURE_FALLBACK)
    global[CAPTURE_FALLBACK] = function(eventName, event){
       // trigger global handlers proceesing
      domEvent.fireEvent(document, eventName);

      // prevent twice global handlers processing
      event.returnValue = true;

      var listener = tmplEventListeners[eventName];
      if (listener)
        listener(new domEvent.Event(event));
    };

  // test for browser (IE) normalize text nodes during cloning
  var CLONE_NORMALIZATION_TEXT_BUG = (function(){
    var element = document.createElement('div');
    element.appendChild(document.createTextNode('a'));
    element.appendChild(document.createTextNode('a'));
    return element.cloneNode(true).childNodes.length == 1;
  })();

  // test for class attribute set via setAttribute bug (IE7 and lower)
  var SET_CLASS_ATTRIBUTE_BUG = (function(){
    var element = document.createElement('div');
    element.setAttribute('class', 'a');
    return !element.className;
  })();

  // test for style attribute set via setAttribute bug (IE7 and lower)
  var SET_STYLE_ATTRIBUTE_BUG = (function(){
    var element = document.createElement('div');
    element.setAttribute('style', 'position:absolute');
    return element.style.position != 'absolute';
  })();

  // test set style properties doesn't throw an error (IE8 and lower)
  var IS_SET_STYLE_SAFE = !!(function(){
    try {
      return document.documentElement.style.color = 'x';
    } catch(e) {}
  })();

  // old Firefox has no Node#contains method (Firefox 8 and lower)
  if (typeof Node != 'undefined' && !Node.prototype.contains)
    Node.prototype.contains = function(child){
      return !!(this.compareDocumentPosition(child) & 16); // Node.DOCUMENT_POSITION_CONTAINED_BY = 16
    };


  // l10n
  var l10nTemplates = {};
  function getL10nTemplate(token){
    var template = basis.template.getL10nTemplate(token);
    var id = template.templateId;
    var htmlTemplate = l10nTemplates[id];

    if (!htmlTemplate)
      htmlTemplate = l10nTemplates[id] = new HtmlTemplate(template.source);

    return htmlTemplate;
  }


  //
  // Constructs dom structure
  //

 /**
  * @func
  */
  function createEventHandler(attrName){
   /**
    * @param {basis.dom.event.Event} event
    */
    return function(event){

      // don't process right click - generaly FF problem
      if (event.type == 'click' && event.which == 3)
        return;

      var bubble = insideElementEvent[event.type] || (event.type != 'mouseenter' && event.type != 'mouseleave');
      var attrCursor = event.sender;
      var attr;

      // search for nearest node with event-{eventName} attribute
      // Note: IE events may have no event source, nothing to do in this case
      while (attrCursor)
      {
        attr = attrCursor.getAttribute && attrCursor.getAttribute(attrName);

        if (!bubble || typeof attr == 'string')
          break;

        attrCursor = attrCursor.parentNode;
      }

      // attribute found
      if (typeof attr == 'string')
      {
        // search for nearest node with basis template marker
        var cursor = attrCursor;
        var actionTarget = cursor;
        var refId;
        var tmplRef;

        if (insideElementEvent[event.type])
        {
          var relTarget = event.relatedTarget;
          if (relTarget && (cursor === relTarget || cursor.contains(relTarget)))
            cursor = null;  // prevent action processing
        }

        while (cursor)
        {
          refId = cursor[basisTemplateIdMarker];
          if (typeof refId == 'number')
          {
            // if node found, return it
            if (tmplRef = resolveInstanceById(refId))
              break;
          }
          cursor = cursor.parentNode;
        }

        if (tmplRef && tmplRef.action)
        {
          var actions = attr.trim().split(/\s+/);
          event.actionTarget = actionTarget;
          for (var i = 0, actionName; actionName = actions[i++];)
            switch (actionName)
            {
              case 'prevent-default':
                event.preventDefault();
                break;
              case 'stop-propagation':
                event.stopPropagation();
                break;
              default:
                tmplRef.action.call(tmplRef.context, actionName, event);
            }
        }
      }

      if (event.type in afterEventAction)
        afterEventAction[event.type](event, attrCursor);
    };
  }

{'fraction_non_alphanumeric': 0.11703847397348852, 'fraction_numerical': 0.005819592628516004, 'mean_word_length': 2.795398773006135, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7629165', 'n_tokens_mistral': 3777, 'n_tokens_neox': 3626, 'n_words': 849}