View project on GitHub
The above filtering uses the following specification (and also strips out style tags):
{ 'span': { 'class': [ 'pull-left', 'pull-right', 'glyphicon', /^glyphicon\-[a-zA-Z0-9\-]+$/, 'label', 'label-default', 'label-primary', 'label-success', 'label-info', 'label-warning', 'label-danger', 'badge', 'badge-default', 'badge-primary', 'badge-success', 'badge-info', 'badge-warning', 'badge-danger' ], 'style': { 'color': 'color', 'background-color': 'color', 'text-decoration': [ 'underline' ] } }, 'section': {}, 'code': {}, 'kbd': {}, 'div': { 'style': { 'color': 'color', 'background-color': 'color' }, 'class': [ 'jumbotron', 'pull-left', 'pull-right', 'center-block', 'clearfix', 'alert', 'alert-success', 'alert-info', 'alert-warning', 'alert-danger', 'progress', 'progress-striped', 'progress-bar', 'progress-bar-success', 'progress-bar-info', 'progress-bar-warning', 'progress-bar-danger', 'active', 'media', 'panel', 'panel-primary', 'panel-success', 'panel-info', 'panel-warning', 'panel-danger', 'panel-default', 'panel-body', 'panel-heading', 'panel-footer', 'well', 'well-lg', 'well-sm' ], 'style': { 'width': 'measurement' } }, 'a': { 'href': 'url', 'target': [ '_blank' ], 'class': [ 'pull-right', 'pull-left', 'btn', 'btn-default', 'btn-primary', 'btn-success', 'btn-info', 'btn-warning', 'btn-danger', 'btn-link', 'btn-lg', 'btn-sm', 'btn-xs', 'btn-block', 'active', 'disabled', 'alert-link' ] }, 'img': { 'src': 'url', 'alt': /^[\w\s]+$/, 'class': [ 'img-responsive', 'img-rounded', 'img-circle', 'img-thumbnail', 'media-object', 'pull-left', 'pull-right' ], 'width': 'measurement', 'height': 'measurement' }, 'p': { 'class': [ 'lead', 'text-left', 'text-center', 'text-right', 'text-justify', 'text-muted', 'text-primary', 'text-success', 'text-info', 'text-warning', 'text-danger', 'bg-primary', 'bg-success', 'bg-info', 'bg-warning', 'bg-danger', 'list-group-item-text' ] }, 'table': { 'summary': /^[\w\s]+$/, 'class': [ 'table', 'table-striped', 'table-bordered', 'table-hover', 'table-condensed', 'table-responsive' ] }, 'thead': {}, 'tbody': {}, 'tfoot': {}, 'tr': { 'class': [ 'active', 'success', 'info', 'warning', 'danger' ] }, 'th': { 'class': [ 'active', 'success', 'info', 'warning', 'danger' ], 'style': { 'text-align': ['left', 'right', 'center', 'justify', 'inherit'] }, 'scope': ['row', 'col', 'rowgroup', 'colgroup'], 'rowspan': /^\d+$/, 'colspan': /^\d+$/ }, 'td': { 'class': [ 'active', 'success', 'info', 'warning', 'danger' ], 'style': { 'text-align': ['left', 'right', 'center', 'justify', 'inherit'] }, 'scope': ['row', 'col', 'rowgroup', 'colgroup'], 'rowspan': /^\d+$/, 'colspan': /^\d+$/ }, 'h1': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'h2': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'h3': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'h4': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'h5': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'h6': { 'class': [ 'media-heading', 'list-group-item-heading', 'panel-title' ] }, 'small': {}, 'strong': {}, 'em': {}, 'abbr': { 'title': /^[\w\s]+$/, 'class': [ 'initialism' ] }, 'address': {}, 'blockquote': { 'class': [ 'blockquote-reverse' ] }, 'footer': {}, 'cite': { 'title': /^[\w\s]+$/ }, 'ul': { 'class': [ 'list-unstyled', 'list-inline', 'media-list', 'list-group' ] }, 'ol': { 'start': 'int', 'type': [ '1', 'A', 'a', 'I', 'i' ] }, 'li': { 'class': [ 'media', 'list-group-item', 'list-group-item-success', 'list-group-item-info', 'list-group-item-warning', 'list-group-item-danger', 'active' ] }, 'dl': { 'class': [ 'dl-horizontal' ] }, 'dt': {}, 'sup': {}, 'sub': {}, 'hr': function(tag_name, tag_stack) { var i, is_inside_p; is_inside_p = false; for (i = 0; i < tag_stack.length; i++) { if (tag_stack[i][0] === 'p') { is_inside_p = true; break; } } if (is_inside_p) { // allow tag, with no attributes return {}; } else { // remove tag and all its contents return false; } // N.B. returning null or undefined will remove the tag, but not its contents }, // aliases 'center': 'p class="text-center"', 'script': 'code', 'b': 'strong', 'i': 'em', 'u': 'span style="text-decoration: underline"' }