doctype html html
head meta[http-equiv="Content-Type" content="text/html; charset=UTF-8"] link[href="http://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css" rel="stylesheet"] link[href="http://maxcdn.bootstrapcdn.com/font-awesome/4.1.0/css/font-awesome.min.css" rel="stylesheet"] script[src="https://code.jquery.com/jquery-2.1.4.js"] script[src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.js"] script[src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.5/angular.js"] /script[src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.5/angular.min.js"] /script[src="https://code.jquery.com/jquery-2.1.4.min.js"] /script[src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"] /script[src="https://cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.4/ui-bootstrap.min.js"] /script[src="https://cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.4/ui-bootstrap.js"] /script[src="https://cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.4/ui-bootstrap-tpls.min.js"] /script[src="https://cdnjs.cloudflare.com/ajax/libs/angular-ui-bootstrap/0.13.4/ui-bootstrap-tpls.js"] title | Blinkr meta[content="width=device-width, initial-scale=1" name="viewport"] body div[ng-controller="ErrorCtrl"] .container h1 | Blinkr p.lead | Blackbox testing for websites h2 ' Pages .label.label-default> | {{numPages}} ' Errors .label.label-default | {{report.total}} .panel.panel-default .panel-heading h4 a#control-filters[data-toggle="collapse" href="#filters"] i.fa.fa-caret-square-o-down | Filters #filters.panel-collapse.collapse.in .panel-body form.row #severities.col-md-2 .panel.panel-default .panel-heading .checkbox label ' Severity .panel-body[ng-repeat="(key, value) in filters.severities"] .checkbox label> input.type>[ng-model="filters.severities[key].enabled" type="checkbox"] ' {{key}} div[class="label label-{{key}}"] ' {{value.count}} #category.col-md-5[style="padding-left:20px; border-left: 1px solid #ccc;"] .row .col-md-12 .panel.panel-default .panel-heading .checkbox label ' Category .panel-body[ng-repeat="(key, value) in filters.categories"] .checkbox label> input.type[ng-model="filters.categories[key].enabled" type="checkbox"] ' {{key}} .label.label-default | {{value.count}} #types.col-md-5[style="padding-left:20px; border-left: 1px solid #ccc;"] .row .col-md-12 .panel.panel-default .panel-heading .checkbox label> ' Type .panel-body[ng-repeat="(key, value) in filters.types"] .checkbox label> input.type[ng-model="filters.types[key].enabled" type="checkbox"] | {{key}} .label.label-default | {{value.count}} .text-center button.btn.btn-default.btn-lg[ng-disabled="currentPage == 0" ng-click="currentPage = currentPage - 1"] Previous ' {{currentPage + 1}} / {{numberOfPages()}} button.btn.btn-default.btn-lg[ng-disabled="currentPage >= numberOfPages() - 1" ng-click="currentPage = currentPage + 1"] Next br br .page[ng-repeat="page in report.pages | showPage:filters | startFrom:currentPage * limitSize | limitTo:limitSize"] div[class="panel panel-{{page.max_severity}}"] .panel-heading .panel-title ul.list-inline li a>[data-toggle="collapse" href="#"] i.fa.fa-caret-square-o-right | {{page.url}} ({{page.errors.length}} total errors) li a[href="{{page.url}}" target="_blank"] i.fa.fa-external-link li a[href="{{page.url}}" target="_blank"] i.fa.fa-file-code-o .panel-body.collapse.panel-collapse ul li.list-group-item.error[ng-repeat="(i,page_error) in page.errors | displayError:filters"] i.fa.fa-2x.fa-bookmark-o.pull-left div[class="pull-right label label-{{page_error.severity}}"] | {{page_error.code}} {{page_error.message}} div ' {{page_error.title}} a[href="{{page_error.title}}" target="_blank" ng-if="page_error.title.startsWith('http')"] i.fa.fa-external-link pre | {{page_error.snippet}} javascript: var blinkr = angular.module('blinkr', []); blinkr.factory('report', function reportFactory() { return #{{errors}}; }); blinkr.controller("ErrorCtrl", ['$scope', 'report', function ($scope, report) { $scope.report = report; $scope.filters = {severities: {}, categories: {}, types: {}}; $scope.report = report; $scope.numPages = report.pages.length; $scope.filteredNumPages = 0; $scope.currentPage = 0; $scope.limitSize = 25; window.scope = $scope; Object.keys($scope.report.severity).forEach(function (s) { $scope.filters.severities[s] = {enabled: false, count: report.severity[s].count}; }); Object.keys($scope.report.category).forEach(function (c) { $scope.filters.categories[c] = {enabled: false, count: report.category[c].count}; }); Object.keys($scope.report.type).forEach(function (t) { $scope.filters.types[t] = {enabled: false, count: report.type[t].count}; }); $scope.numberOfPages = function () { return Math.ceil($scope.filteredNumPages / $scope.limitSize); } }]); blinkr.filter('startFrom', function () { return function (input, start) { start = +start; //parse to int return input.slice(start); } }); blinkr.filter('displayError', function () { return function (errors, filters) { var returned_errors = []; errors.forEach(function (error) { if (showError(error, filters)) { returned_errors.push(error); } }); panelBind(); return returned_errors; } }); blinkr.filter('showPage', function () { return function (all_pages, filters) { var pages = []; all_pages.forEach(function (page) { if ($.arrayIntersect(enabledFilters(filters, 'categories'), page.categories).length > 0) { pages.push(page); } else if ($.arrayIntersect(enabledFilters(filters, 'types'), page.types).length > 0) { pages.push(page); } else if ($.arrayIntersect(enabledFilters(filters, 'severities'), page.severities).length > 0) { pages.push(page); } }); scope.filteredNumPages = pages.length; return pages; } }); function enabledFilters(filters, filterName) { var enabled = []; Object.keys(filters[filterName]).forEach(function (f) { if (filters[filterName][f].enabled) { enabled.push(f); } }); return enabled; } function showError(error, filters) { var categories = enabledFilters(filters, 'categories'), severities = enabledFilters(filters, 'severities'), types = enabledFilters(filters, 'types'), possibleReturn = false; if (categories.length > 0 && categories.indexOf(error.category) > -1) { possibleReturn = true; } if (possibleReturn) { if (severities.length > 0) { possibleReturn = severities.indexOf(error.severity) > -1; } } else { if (severities.length > 0) { possibleReturn = severities.indexOf(error.severity) > -1; } } if (possibleReturn) { if (types.length > 0) { possibleReturn = !!(types.length > 0 && types.indexOf(error.type) > -1); } } else { if (types.length > 0) { possibleReturn = !!(types.length > 0 && types.indexOf(error.type) > -1); } } return possibleReturn; } window.panelBind = function () { $('.panel-title').find('a[data-toggle=collapse]').on('click', function (e) { e.preventDefault(); var target = $(this).parents('.panel').find('.panel-collapse'); target.collapse('toggle'); }); $('.page').find('panel-collapse').collapse({toggle: false}); }; angular.element(document).ready(function () { panelBind(); }); $.arrayIntersect = function (a, b) { return $.grep(a, function (i) { return $.inArray(i, b) > -1; }); };