Advertisement
stuppid_bot

JavaScript Web Crawler

Oct 18th, 2013
177
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. // https://github.com/hacker1999/asdfgh/blob/master/crawler.js
  2. /**
  3.  * --//--
  4.  *
  5.  * @param {Object} options
  6.  * @param {String} options.startUrl url с которого начинаем обход сайта
  7.  * @param {Function} options.filterUrl = function (url) { ... } дополнительный фильтр
  8.  * @param {Function} options.onMatch = function (url, content) { ... }
  9.  * @param {Function} options.onEnd = function (urls) { ... }
  10.  */
  11. function grabInternalUrls(options) {
  12.     options = options || {};
  13.     var visitedUrls = [];
  14.     var urlCounter = 0;
  15.  
  16.     function parseUrl(url) {
  17.         var obj = {};
  18.         var link = document.createElement('a');
  19.         link.href = url;
  20.         var keys = 'protocol host hostname port pathname search hash href'.split(' ');
  21.         var key;
  22.         for (var i = 0; i < keys.length; ++i) {
  23.             key = keys[i];
  24.             obj[key] = link[key];
  25.         }
  26.         return obj;
  27.     }
  28.  
  29.     var url = options.startUrl == null ? '/' : options.startUrl;
  30.     url = url.replace(/#.*/, '');
  31.     var urlObj = parseUrl(url);
  32.     if (!/^https?:$/.test(urlObj.protocol)) {
  33.         throw 'Протокол не поддерживается';
  34.     }
  35.     if (urlObj.hostname != location.hostname) {
  36.         throw 'URL относится к другому Интернет-ресурсу';
  37.     }
  38.     (function process(curUrl) {
  39.         var xhr = new XMLHttpRequest;
  40.         xhr.open('GET', curUrl.href);
  41.         xhr.onload = function () {
  42.             if (this.status == 200 && this.getResponseHeader('content-type').substr(0, 9) == 'text/html') {
  43.                 var onMatch = options.onMatch;
  44.                 if (typeof onMatch == 'function') {
  45.                     onMatch(curUrl.href, this.response);
  46.                 }          
  47.                 var re = /<a[^>]+href\s*=\s*(?:'([^']+)|"([^"]+)|([^\s>]+))/gi;
  48.                 var matches;
  49.                 var matchedUrl;
  50.                 var nextUrl;
  51.                 while (matches = re.exec(this.response)) {                
  52.                     if (matches[3]) {
  53.                         matchedUrl = matches[3];
  54.                     }
  55.                     else if (matches[2]) {
  56.                         matchedUrl = matches[2];
  57.                     }
  58.                     else if (matches[1]) {
  59.                         matchedUrl = matches[1];
  60.                     }
  61.                     matchedUrl = matchedUrl.replace(/#.*/, '');
  62.                     matchedUrl = matchedUrl.trim(matchedUrl);
  63.                     if (!/^https?:[\\/]{2}/.test(matchedUrl)) {
  64.                         if (/^\w+:/.test(matchedUrl)) {
  65.                             continue;
  66.                         }
  67.                         if (!/^[\\/]/.test(matchedUrl)) {
  68.                             matchedUrl = curUrl.pathname + matchedUrl;
  69.                         }
  70.                     }
  71.                     nextUrl = parseUrl(matchedUrl);
  72.                     if (nextUrl.hostname == location.hostname) {
  73.                         if (visitedUrls.indexOf(nextUrl.href) == -1) {
  74.                             if (typeof options.filterUrl == 'function') {
  75.                                 if (!options.filterUrl(nextUrl.href)) {
  76.                                     continue;
  77.                                 }
  78.                             }
  79.                             process(nextUrl);
  80.                         }
  81.                     }
  82.                 }
  83.             }
  84.             --urlCounter;
  85.             if (urlCounter == 0) {
  86.                 var onEnd = options.onEnd;
  87.                 if (typeof onEnd == 'function') {
  88.                     onEnd(visitedUrls);
  89.                 }
  90.             }      
  91.         };
  92.         xhr.send();
  93.         visitedUrls.push(curUrl.href);      
  94.         ++urlCounter;
  95.     })(urlObj);
  96. }
  97.  
  98.  
  99. grabInternalUrls({
  100.     filterUrl: function (url) {
  101.         // ограничимся первым уровнем
  102.         return /^https?:\/\/[^/]+\/[^/?]+$/.test(url);
  103.     },
  104.     onMatch: function (url, content) {
  105.         // console.log(url);
  106.     },
  107.     onEnd: function (urls) {
  108.         console.log(urls);
  109.     }
  110. });
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement