Jelajahi Sumber

Replaced DOMqueriesWithoutResults by queriesWithoutResults to include jQuery queries

Gaël Métais 10 tahun lalu
induk
melakukan
33621af3ad

+ 11 - 0
front/src/js/app.js

@@ -22,6 +22,17 @@ yltApp.run(['$rootScope', '$location', function($rootScope, $location) {
     $rootScope.isTouchDevice = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(window.navigator.userAgent);
     $rootScope.isTouchDevice = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(window.navigator.userAgent);
     $rootScope.loadedRunId = null;
     $rootScope.loadedRunId = null;
 
 
+    var oldHash;
+
+    // We don't want the hash to be kept between two pages
+    $rootScope.$on('$locationChangeStart', function(param1, param2, param3, param4){
+        var newHash = $location.hash();
+        if (newHash === oldHash) {
+            $location.hash(null);
+        }
+        oldHash = newHash;
+    });
+
     // Google Analytics
     // Google Analytics
     $rootScope.$on('$routeChangeSuccess', function(){
     $rootScope.$on('$routeChangeSuccess', function(){
         ga('send', 'pageview', {'page': $location.path()});
         ga('send', 'pageview', {'page': $location.path()});

+ 28 - 8
front/src/js/controllers/timelineCtrl.js

@@ -4,14 +4,6 @@ timelineCtrl.controller('TimelineCtrl', ['$scope', '$rootScope', '$routeParams',
     $scope.runId = $routeParams.runId;
     $scope.runId = $routeParams.runId;
     $scope.Menu = Menu.setCurrentPage('timeline', $scope.runId);
     $scope.Menu = Menu.setCurrentPage('timeline', $scope.runId);
 
 
-    $scope.warningsFilterOn = false;
-    $scope.warningsFilters = {
-        queryWithoutResults: true,
-        jQueryCallOnEmptyObject: true,
-        eventNotDelegated: true,
-        jsError: true
-    };
-
     function loadResults() {
     function loadResults() {
         // Load result if needed
         // Load result if needed
         if (!$rootScope.loadedResult || $rootScope.loadedResult.runId !== $routeParams.runId) {
         if (!$rootScope.loadedResult || $rootScope.loadedResult.runId !== $routeParams.runId) {
@@ -27,12 +19,40 @@ timelineCtrl.controller('TimelineCtrl', ['$scope', '$rootScope', '$routeParams',
     }
     }
 
 
     function render() {
     function render() {
+        initFilters();
         initScriptFiltering();
         initScriptFiltering();
         initExecutionTree();
         initExecutionTree();
         initTimeline();
         initTimeline();
         $timeout(initProfiler, 100);
         $timeout(initProfiler, 100);
     }
     }
 
 
+    function initFilters() {
+        var hash = $location.hash();
+        var filter = null;
+        
+        if (hash.indexOf('filter=') === 0) {
+            filter = hash.substr(7);
+        }
+
+        $scope.warningsFilterOn = (filter !== null);
+        $scope.warningsFilters = {
+            queryWithoutResults: (filter === null || filter === 'queryWithoutResults'),
+            jQueryCallOnEmptyObject: (filter === null || filter === 'jQueryCallOnEmptyObject'),
+            eventNotDelegated: (filter === null || filter === 'eventNotDelegated'),
+            jsError: (filter === null || filter === 'jsError')
+        };
+
+        // If a filter is defined in the hash (ie: "/result/xxxxx/timeline#filter=queryWithoutResults")
+        var hash = $location.hash();
+        if (hash.indexOf('filter=') === 0) {
+            var filter = hash.substr(7);
+            $scope.warningsFilterOn = true;
+            for (var key in $scope.warningsFilter) {
+
+            }
+        }
+    }
+
     function initScriptFiltering() {
     function initScriptFiltering() {
         var offenders = $scope.result.rules.jsCount.offendersObj.list;
         var offenders = $scope.result.rules.jsCount.offendersObj.list;
         $scope.scripts = [];
         $scope.scripts = [];

+ 6 - 5
front/src/views/rule.html

@@ -30,10 +30,6 @@
                     <div ng-if="policyName === 'DOMidDuplicated'">
                     <div ng-if="policyName === 'DOMidDuplicated'">
                         <b>{{offender.id}}</b>: {{offender.occurrences}} occurrences
                         <b>{{offender.id}}</b>: {{offender.occurrences}} occurrences
                     </div>
                     </div>
-                    
-                    <div ng-if="policyName === 'DOMqueriesWithoutResults'">
-                        <b>{{offender.query}}</b> (in <dom-element-button obj="offender.context"></dom-element-button>) using {{offender.fn}}
-                    </div>
 
 
                     <div ng-if="policyName === 'DOMqueriesAvoidable'">
                     <div ng-if="policyName === 'DOMqueriesAvoidable'">
                         <b>{{offender.query}}</b> (in <dom-element-button obj="offender.context"></dom-element-button>) using {{offender.fn}}: <b>{{offender.count}} queries</b>
                         <b>{{offender.query}}</b> (in <dom-element-button obj="offender.context"></dom-element-button>) using {{offender.fn}}: <b>{{offender.count}} queries</b>
@@ -214,10 +210,15 @@
     </div>
     </div>
 
 
     <div ng-if="policyName === 'DOMaccesses'">
     <div ng-if="policyName === 'DOMaccesses'">
-        <h3>Offenders</h3>
+        <h3>{{rule.value}} offenders</h3>
         Please open the <a href="/result/{{runId}}/timeline">JS timeline</a>
         Please open the <a href="/result/{{runId}}/timeline">JS timeline</a>
     </div>
     </div>
 
 
+    <div ng-if="policyName === 'queriesWithoutResults'">
+        <h3>{{rule.value}} offenders</h3>
+        Please open the <a href="/result/{{runId}}/timeline#filter=queryWithoutResults">JS timeline, filtered by "Queries without results"</a>
+    </div>
+
     <div ng-if="!rule && rule !== null" class="notFound">
     <div ng-if="!rule && rule !== null" class="notFound">
         <h2>404</h2>
         <h2>404</h2>
         Rule "{{policyName}}"" not found
         Rule "{{policyName}}"" not found

+ 6 - 27
lib/metadata/policies.js

@@ -73,37 +73,16 @@ var policies = {
         "isOkThreshold": 50,
         "isOkThreshold": 50,
         "isBadThreshold": 1500,
         "isBadThreshold": 1500,
         "isAbnormalThreshold": 3000,
         "isAbnormalThreshold": 3000,
-        "hasOffenders": true
+        "hasOffenders": false
     },
     },
-    "DOMqueriesWithoutResults": {
-        "tool": "phantomas",
-        "label": "DOM queries without result",
-        "message": "<p>Number of queries that return no result.</p><p>It suggests the query is not used on the page, probably because it is some dead code.</p><p>Or maybe the code is trying to find an HTML block that is not always here. Look at the JS Timeline to see if the scripts correctly figures out the HTML block is not here and immediatly stops interacting further with the DOM.</p>",
+    "queriesWithoutResults": {
+        "tool": "jsExecutionTransformer",
+        "label": "Queries without result",
+        "message": "<p>Number of queries that return no result. Both native and jQuery DOM requests are counted.</p><p>It suggests the query is not used on the page, probably because it is some dead code.</p><p>Or maybe the code is trying to find an HTML block that is not always here. Look at the JS Timeline to see if the scripts correctly figures out the HTML block is not here and immediatly stops interacting further with the DOM.</p>",
         "isOkThreshold": 0,
         "isOkThreshold": 0,
         "isBadThreshold": 100,
         "isBadThreshold": 100,
         "isAbnormalThreshold": 200,
         "isAbnormalThreshold": 200,
-        "hasOffenders": true,
-        "offendersTransformFn": function(offenders) {
-            return {
-                count: offenders.length,
-                list: offenders.map(function(offender) {
-                    var parts = /^(.*) ?\(in ?(.*)\) ?using ?(.*)$/.exec(offender);
-
-                    if (!parts) {
-                        debug('DOMqueriesWithoutResults offenders transform function error with "%s"', offender);
-                        return {
-                            parseError: offender
-                        };
-                    }
-
-                    return {
-                        query: parts[1],
-                        context: offendersHelpers.domPathToDomElementObj(parts[2]),
-                        fn: parts[3]
-                    };
-                })
-            };
-        }
+        "hasOffenders": false
     },
     },
     "DOMqueriesAvoidable": {
     "DOMqueriesAvoidable": {
         "tool": "phantomas",
         "tool": "phantomas",

+ 1 - 1
lib/metadata/scoreProfileGeneric.json

@@ -13,7 +13,7 @@
             "label": "DOM manipulations",
             "label": "DOM manipulations",
             "policies": {
             "policies": {
                 "DOMaccesses": 3,
                 "DOMaccesses": 3,
-                "DOMqueriesWithoutResults": 1,
+                "queriesWithoutResults": 1,
                 "DOMqueriesAvoidable": 1
                 "DOMqueriesAvoidable": 1
             }
             }
         },
         },